I'm trying to write a contract that contains a fallback function which would pass-through the call to another destination contract. This would allow for future upgrades/bug-fixes to the destination contract by updating the destination contract address in the contract which contains the pass-through fallback function.
Caller calling Do() -> Pass-Through function () -> Destination implements Do()
The problem is the fallback function can't return anything. Worse, if the caller to a contract with a fallback function is expecting a return value, they will receive what I believe is msg.data instead of the expected value.
- Is there a way to return data from a fallback function (assembly okay) ?
- Is the current behavior dangerous (e.g. corrupting the caller's stack)?
Here's the example code:
pragma solidity ^0.4.10;
contract Real
{
function Do() public constant returns (uint256) { return 12345; }
}
contract Blank
{
function () public { }
}
// Client contract address: 0x7C2F875a9D5Ba712A6cdF35E537651ea89779802
contract Client
{
function Run() public constant returns (uint256 result1, uint256 result2)
{
Real real = Real(0xd64dE830995C7407b09CF96EC59f76701D4DBcF9); // This is the address of Real
result1 = real.Do();
Real blank = Real(0x068c8D804Fab87B3d2cF3f02914eF2bE6b199436); // This is the address of Blank
result2 = blank.Do();
}
}
// result1 = 12345
// result2 = 0xDDFAE52900000000000000000000000000000000000000000000000000000000
// bytes4(sha3("Do()")) = 0xDDFAE529. This is why I think result2 is msg.data
Best Answer
As outlined here by chriseth (who created Solidity):
It does look like your
result2
value is themsg.data
value. That said, you have not outlined how you are calling the client function - it is possible that returning msg.data is a fallback of the library/tooling that you are using.