Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

return msg.sender.balance; returns unexpected value #2325

Closed
o0ragman0o opened this issue May 30, 2017 · 10 comments
Closed

return msg.sender.balance; returns unexpected value #2325

o0ragman0o opened this issue May 30, 2017 · 10 comments
Labels
waiting for more input Issues waiting for more input by the reporter

Comments

@o0ragman0o
Copy link

o0ragman0o commented May 30, 2017

I'm raising this first as a Solidity issue but maybe a deeper issue present.

This was raised on SE yesterday and I have confirmed unexpected behaviour with a contract on Rinkeby

I'm using MetaMask to connect to Rinkeby and I'm deploying the contracts via Remix. When I call the function returnsenderbalance it returns

115792089237316195423570985008687907853269984665640564039456084007913129639935
rather than my balance in Wei. The code is below:

pragma solidity ^0.4.11;

contract returnbalance{
    function returnsenderbalance() constant returns (uint){
        return msg.sender.balance;  
    }
}

The return value of msg.sender.balance appears to be a unit cast negative value unassociated with the actual account balance.

Behaviour is present in Geth.
Behaviour not present in the JavascriptVM which works as expected.
Have not tested on Parity.

@axic
Copy link
Member

axic commented May 30, 2017

This is translated into this (with 0.4.12-develop.2017.5.30+commit.64f76b30.Darwin.appleclang
):

        /* "rb.sol":78:82  uint */
      0x0
        /* "rb.sol":100:110  msg.sender */
      caller
        /* "rb.sol":100:118  msg.sender.balance */
      0xffffffffffffffffffffffffffffffffffffffff
      and
      balance
        /* "rb.sol":93:118  return msg.sender.balance */
      swap1
      pop
        /* "rb.sol":29:127  function returnsenderbalance() constant returns (uint){... */

This seems to be correct. Does it work properly with on-chain transactions? It only fails with eth_call on geth?

@axic axic added the waiting for more input Issues waiting for more input by the reporter label Jun 27, 2017
@kieranelby
Copy link

FWIW, I've also seen this (and been very confused by it), in my case using MetaMask to call a constant contract function that returns the balance of an address - about 50% of the time I get the correct result, other times I get 115792089237316195423570985008687907853269984665640564039455084007913129639935. Perhaps a geth/MetaMask issue - never seen with JavascriptVM.

@axic
Copy link
Member

axic commented Aug 16, 2017

@o0ragman0o @kieranelby since it is not present on ethereumjs-vm, but both of you have seen it with geth, please open an issue on go-ethereum.

@o0ragman0o
Copy link
Author

I've realised that msg.sender itself does not make sense in a constant function. The following function returns garbage under different clients.

contract ReturnSender {
    function retSenderAddr() public constant returns (address)
    {
        return msg.sender;
    }
}

@axic
Copy link
Member

axic commented Aug 17, 2017

From Solidity's perspective it still makes sense, it is part of the state and constant functions can read the state, just they cannot modify it.

Since this flag is also populated in the ABI JSON, certain tools (such as web3.js) will consider those functions can be executed via eth_call, which is true, but it still requires proper values. However, they can also be executed by other contract functions, so it doesn't make sense disallowing msg.sender.

I'm not sure why sender would be omitted in eth_call though.

@o0ragman0o
Copy link
Author

I'm not aware enough of how eth_call works. I'll raise this as a Geth issue as suggested. However, now I can't reproduce the bad behaviour returning msg.sender with other clients (local Remix may have been corrupted and I've been trying to stabilise all morning).

@mr-robek
Copy link

i'm experiencing the same behavior. my smartcontract looks like this:
function balanceOfEther(address user) public constant returns (uint256) { return user.balance; }
i deployed it to main network and every time i call it using metamask i get the same big number 11579...
caling it from etherscan "read smart contract" feature works well.
any workarounds/solution since august?

@axic
Copy link
Member

axic commented Dec 10, 2017

This is still doesn't look a Solidity bug. Please report it to Metamask or any other client you are using.

@axic
Copy link
Member

axic commented Apr 17, 2018

Closing this as the generated code seemed to be correct.

@diegobes
Copy link

diegobes commented Aug 9, 2018

This is related to:

eth/api_backend.go

func (b *EthAPIBackend) GetEVM(ctx context.Context, msg core.Message, state *state.StateDB, header *types.Header, vmCfg vm.Config) (*vm.EVM, func() error, error) {
===> state.SetBalance(msg.From(), math.MaxBig256)
vmError := func() error { return nil }
context := core.NewEVMContext(msg, header, b.eth.BlockChain(), nil)
return vm.NewEVM(context, state, b.eth.chainConfig, vmCfg), vmError, nil
}

math.MaxBig256 == 115792089237316195423570985008687907853269984665640564039455084007913129639935

Is a constant in Geth( common/math/big.go)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
waiting for more input Issues waiting for more input by the reporter
Projects
None yet
Development

No branches or pull requests

5 participants