0

I'm playing Ethernaut (https://ethernaut.openzeppelin.com/).

I'm currently on level 3 (Coin Flip).

This is the Coin Flip contract:

// SPDX-License-Identifier: MIT
pragma solidity ^0.6.0;

import '@openzeppelin/contracts/math/SafeMath.sol';

contract CoinFlip {

  using SafeMath for uint256;
  uint256 public consecutiveWins;
  uint256 lastHash;
  uint256 FACTOR = 57896044618658097711785492504343953926634992332820282019728792003956564819968;

  constructor() public {
    consecutiveWins = 0;
  }

  function flip(bool _guess) public returns (bool) {
    uint256 blockValue = uint256(blockhash(block.number.sub(1)));

    if (lastHash == blockValue) {
      revert();
    }

    lastHash = blockValue;
    uint256 coinFlip = blockValue.div(FACTOR);
    bool side = coinFlip == 1 ? true : false;

    if (side == _guess) {
      consecutiveWins++;
      return true;
    } else {
      consecutiveWins = 0;
      return false;
    }
  }
}

I deployed this code in the Remix IDE.

However, whenever I call flip(), I get:

transact to CoinFlip.flip errored: NotFoundError: Key not found in database [h n]

I searched for this problem online, but most related questions involve Web3, Ganache, RPCs or something of the sort. And the answers aren't really what I'm looking for.

I tried:

  • flip()
  • flip(0)
  • flip(1)
  • flip(false)
  • flip(true)
  • flip("false")
  • flip("true")
  • increasing the gasLimit
  • refreshing the page

Nothing fixed it. Same error gets thrown.

Am I doing something wrong? Is the problem in the Smart Contract? Or is it in Remix?

Secondary Question: What's the proper way to pass in a bool parameter to a function?

0 and 1? false and true? "false" and "true"?

Thanks.

0

I encountered the same error when solving the same Ethernaut level. I'm using Remix IDE. When I changed from deploying with JavaScript VM to deploying with Injected Web3 (there's a dropdown menu in DEPLOY & RUN TRANSACTIONS in Remix and you need MetaMask to deploy this way), the error disappeared.

I added the following function to the contract:

  function blockValue() view public returns (uint256) {
      return uint256(blockhash(block.number - 1));
  }

and it was still throwing the error when calling blockValue instead of flip. So I think the reason is that the simulation of blocks in JavaScript VM isn't realistic enough for blockhash to work properly.

Answer to secondary question: I passed true and it incremented consecutiveWins, so true and false should be correct.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.