2

I need to make recursive evm message calls. Based on my understanding of how solidity works, calls within the same contract don't trigger an evm message. But for my use case I want each of these recursive calls to be evm message calls. It's a fibonacci contract. Here's the normal version

contract Fibonacci {
    function fibonacci(uint32 n) public pure returns(uint32) {
        if (n == 0 || n == 1) {
            return n;
        }
    
        return fibonacci(n - 1) + fibonacci(n - 2);
    }
}

In the above the recursive calls of fibonacci don't trigger an evm chain call as they happen within the same contract. To call code of one smart contract from another, you need the address of the contract you want to call. So I used the same idea to force evm recursive chain calls(or so I think). Here's the implementation

contract Fibonacci {
    function fibonacciIndirect(uint32 n) public view returns(uint32) {
        if (n == 0 || n == 1) {
            return n;
        }
        uint32 n1;
        uint32 n2;
        n1 = Fibonacci(this).fibonacciIndirect(n - 1);
        n2 = Fibonacci(this).fibonacciIndirect(n - 2);
        return n1 + n2;
    }
}

So I'm using this as the address of the Fibonacci contract and use that to trigger an evm chain call. My tests show that the function correctly computes the nth value of the fibonacci sequence and also consumes more gas compared to the normal version but because I didn't see this on the documentation, I'm not really sure if its the right way to do that. Yes I'm aware that more evm calls mean more gas and no one will pick the second implementation of fibonacci over the first for this reason. But as part of my tests, I need to be able to force recursive evm message calls.

Stylishcoder
  • 1,142
  • 1
  • 11
  • 21

1 Answers1

0

You can force an "external call" (i.e. a CALL instead of a JUMP) to the function foo in Solidity by calling your function using this.foo(). This is detailed in the documentation here. This is what you used in your second example. Of course, you should not use that in production or only if you have a very good reason to do so.

Valentin
  • 149
  • 5