drizzle icon indicating copy to clipboard operation
drizzle copied to clipboard

VM Exception while processing transaction: out of gas

Open caseyjkey opened this issue 4 years ago • 10 comments

  • [x] I've asked for help in the Truffle Gitter before filing this issue.

Issue

Calling cacheSend without gas specified causes this error:

Error: Returned error: VM Exception while processing transaction: out of gas

If I am using Buidler EVM for my testnet, both functions work fine without gas specified. However, when I go to use truffle's testnet, truffle develop, I start getting the out of gas errors. It seems like Drizzle's automatic gas estimation is broken. I'd like this to work as it will add more complexity to explicitly estimate cost for every cacheSend.

I'd like to get Truffle working because my team is used to it, and Truffle has a more comfortable development process than Buidler.

Steps to Reproduce

  1. Clone this repo https://github.com/caseykey/the-payment-pals/.
  2. Checkout the branch 'buidler-evm'
  3. Run npm install && cd app && npm install && cd ..
  4. Run truffle develop then enter migrate
  5. In a new terminal, open the repository and run cd app && npm run start
  6. Click "Add Friend"
  7. Enter a name, i.e. Casey, and address, i.e. 0x47d0e9f0fde14b48ea9223f2e94bf2aea4ffbeaa
  8. Click "Send"

A new friend shouldn't show up, and the error should be present in the Developer Console.

The specific call is this one: await this.props.drizzle.contracts.PaymentHub.methods["addFriend"].cacheSend({ name: this.state.name, balance: 0, addy: this.state.address }, this.props.groupId);

A similar call was fixed by explicitly allowing enough gas for the transaction: drizzle.contracts.PaymentHub.methods["transaction"].cacheSend(addresses, amountsTemp, gid, {gas: 140000})

Expected behavior

The transaction succeeds and a Friend is added to the list of Friends.

Environment

Truffle versions:

Truffle v5.1.10 (core: 5.1.10)
Solidity v0.5.16 (solc-js)
Node v10.16.3
Web3.js v1.2.1

caseyjkey avatar May 04 '20 20:05 caseyjkey

truffle develop uses Ganache under the hood and Web3.js for calling methods. It sounds like this is an issue of Web3.js' default gas as well as Ganache.

adrianmcli avatar May 04 '20 20:05 adrianmcli

truffle develop uses Ganache under the hood and Web3.js for calling methods. It sounds like this is an issue of Web3.js' default gas as well as Ganache.

You're right, it is a Ganache setting, but I don't know how to fix it. I read here that "[Drizzle] will fall back to values set by your wallet, like MetaMask, or the client (geth, parity, etc.)." but then he goes on to say, "...the gas settings in the truffle.js file only affect migrations."

I only have truffle-config.js so I'm confused on how I can change the values of Ganache provided by truffle develop.

caseyjkey avatar May 04 '20 20:05 caseyjkey

Should I be estimating the cost of the transaction within my dApp, and then pass that estimation as the gas limit for the transaction?

Example:

let estimate = web3.estimate....
...cacheSend(arg1, arg2, {gas: estimate});

caseyjkey avatar May 05 '20 06:05 caseyjkey

I had the same issue but now its fixed. When using web3 the default gas usage is set to 90000 which is not enough for some transaction. This can be conquered by setting the gas while sending transaction.

For eg. await this.state.instance.methods. cacheSend().send({ from : this.state.account, gas : 1000000})

maasoomraj avatar May 30 '20 00:05 maasoomraj

I had the same issue but now its fixed. When using web3 the default gas usage is set to 90000 which is not enough for some transaction. This can be conquered by setting the gas while sending transaction.

For eg. await this.state.instance.methods. cacheSend().send({ from : this.state.account, gas : 1000000})

Yup, this is what I ended up doing as well. However, does this override any estimation provided by the wallet provider, i.e. metamask?

I am worried because I set a hard limit for a dynamic transaction. For example, my transaction method loops through the addresses provided as an argument, making changes to the blockchain for each account. To implement the fix, I set the gas limit manually while testing 4 addresses.

The user may provide more than 4 addresses and then there wouldn't be enough gas. How do I make the gas limit large enough to accommodate the number of addresses provided by a user?

caseyjkey avatar Jun 06 '20 21:06 caseyjkey

@caseyjkey, as you said, I have written a code that estimate the gas used with the web3 instance injected into the drizzle prop.

  handleSubmit(event) {
    event.preventDefault();
    const { drizzle, drizzleState } = this.props;
    const contract = drizzle.contracts.MyContract;

    const instance = new drizzle.web3.eth.Contract(contract.abi, contract.address);
    instance.methods.createGame(
// insert contract function parameters here 
)
    .estimateGas()
    .then(gasAmount => {
      const stackId = contract.methods.createGame.cacheSend(
// insert contract function parameters here 
        { from: drizzleState.accounts[0], gas: gasAmount }
      );
      // save the `stackId` for later reference
      this.setState({ stackId });
    })
    .catch(error => {
        console.log(47, error);
    });
  }

I had the same problem and this solution solve it.

Thykof avatar Jul 14 '20 07:07 Thykof

@caseyjkey, as you said, I have written a code that estimate the gas used with the web3 instance injected into the drizzle prop.

  handleSubmit(event) {
    event.preventDefault();
    const { drizzle, drizzleState } = this.props;
    const contract = drizzle.contracts.MyContract;

    const instance = new drizzle.web3.eth.Contract(contract.abi, contract.address);
    instance.methods.createGame(
// insert contract function parameters here 
)
    .estimateGas()
    .then(gasAmount => {
      const stackId = contract.methods.createGame.cacheSend(
// insert contract function parameters here 
        { from: drizzleState.accounts[0] }
      );
      // save the `stackId` for later reference
      this.setState({ stackId });
    })
    .catch(error => {
        console.log(47, error);
    });
  }

I had the same problem and this solution solve it.

I was expecting you would use the gasAmount within the following object: { from: drizzleState.accounts[0] }, but you didn't. Where do you use the estimated gas amount?

caseyjkey avatar Jul 20 '20 04:07 caseyjkey

Right, my bad, I have edited the comment.

Thykof avatar Jul 20 '20 17:07 Thykof

Hello ! i'm new to ethereum and i'm having this problem ! RPCError: got code -32000 with msg "VM Exception while processing transaction: out of gas". Any Solutions ?!!

kader46 avatar May 30 '21 17:05 kader46

increase gas value works for me, better using Remix suggested value: image

mx51damon avatar Dec 30 '21 07:12 mx51damon