对于动态调用数据数组,坚实的文档会这样说:
对于动态调用数据数组,可以使用
x.offset和x.length访问它们的回调数据偏移量(以字节为单位)和长度(元素数)。
但他们没有提供任何例子。
在这种情况下,“抵消”意味着什么?
发布于 2023-02-16 14:10:10
offset是调用数据中开始数组的实际数据的位置,即第一个数组元素所在的位置。让我们举一个例子:
contract Foo {
function getOffset(uint256[] calldata arr) external pure returns (uint256 offset) {
assembly {
offset := arr.offset
}
}
}将[1,2,3]作为此函数的输入传递将返回68:

现在,让我们在函数中定义另一个参数,在arr之前:
function getOffset (uint256 param, uint256[] calldata arr) external pure returns (uint256 offset) {
assembly {
offset := arr.offset
}
}将0,[1,2,3]作为输入传递现在将返回100而不是68,因为在arr之前还有另一个EVM单词,并且EVM单词有32字节长:

发布于 2023-05-01 22:21:25
假设我们有这样的功能:
contract Foo {
function getOffset(uint256[] calldata arr) external pure returns (uint256 offset) {
assembly {
offset := arr.offset
}
}
}将[1, 2, 3]作为此函数的输入传递将返回68。
但它是如何计算68的呢?
基于文档,我们可以找到编码的参数,对于这个输入和函数参数,它将是:
0x1fe457d7 - function signature
0000000000000000000000000000000000000000000000000000000000000020 - offset of [1,2,3]
0000000000000000000000000000000000000000000000000000000000000003 - count for [1,2,3]
0000000000000000000000000000000000000000000000000000000000000001 - encoding of 1
0000000000000000000000000000000000000000000000000000000000000002 - encoding of 2
0000000000000000000000000000000000000000000000000000000000000003 - encoding of 3如果计算从function signature行(4个字节)到开始数组的实际数据的行encoding of 1开头的字节数,您将发现有68个字节。
https://ethereum.stackexchange.com/questions/145043
复制相似问题