Skip to content

Commit f7b0cd4

Browse files
vm: fix EIP 2565 implementation
vm: modexp precompile: fix return length bug if result is 0
1 parent 3064b8e commit f7b0cd4

File tree

2 files changed

+9
-32
lines changed

2 files changed

+9
-32
lines changed

packages/vm/lib/evm/precompiles/05-modexp.ts

Lines changed: 8 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -22,36 +22,9 @@ function multComplexity(x: BN): BN {
2222
}
2323
}
2424

25-
function calculateGasEIP2565(
26-
baseLength: BN,
27-
modulusLength: BN,
28-
exponentLength: BN,
29-
exponent: BN
30-
): BN {
31-
console.log(
32-
baseLength.toNumber(),
33-
modulusLength.toNumber(),
34-
exponentLength.toNumber(),
35-
exponent.toNumber()
36-
)
37-
const maxLength = BN.max(baseLength, modulusLength)
38-
const words = maxLength.divn(8)
39-
// Ceil operation
40-
if (maxLength.mod(new BN(8)).gtn(0)) {
41-
words.iaddn(1)
42-
}
43-
const multiplicationComplexity = words.pow(new BN(2))
44-
let iterationCount
45-
if (exponentLength.lten(32) && exponent.eqn(0)) {
46-
iterationCount = new BN(0)
47-
} else if (exponentLength.lten(32)) {
48-
iterationCount = new BN(exponent.bitLength() - 1)
49-
} else {
50-
const expMask = exponent.and(new BN(Buffer.alloc(32, 0xff)))
51-
iterationCount = new BN(8).mul(exponentLength.subn(32)).addn(expMask.bitLength() - 1)
52-
}
53-
iterationCount = BN.max(new BN(1), iterationCount)
54-
return BN.max(new BN(200), multiplicationComplexity.mul(iterationCount).divn(3))
25+
function multComplexityEIP2565(x: BN): BN {
26+
const words = x.addn(7).divn(8)
27+
return words.mul(words)
5528
}
5629

5730
function getAdjustedExponentLength(data: Buffer): BN {
@@ -145,7 +118,10 @@ export default function (opts: PrecompileInput): ExecResult {
145118
if (!opts._common.eips().includes(2565)) {
146119
gasUsed = adjustedELen.mul(multComplexity(maxLen)).divn(Gquaddivisor)
147120
} else {
148-
gasUsed = calculateGasEIP2565(bLen, eLen, mLen, E)
121+
gasUsed = adjustedELen.mul(multComplexityEIP2565(maxLen)).divn(Gquaddivisor)
122+
if (gasUsed.ltn(200)) {
123+
gasUsed = new BN(200)
124+
}
149125
}
150126

151127
if (opts.gasLimit.lt(gasUsed)) {
@@ -155,7 +131,7 @@ export default function (opts: PrecompileInput): ExecResult {
155131
if (bLen.isZero()) {
156132
return {
157133
gasUsed,
158-
returnValue: new BN(0).toArrayLike(Buffer, 'be', 1),
134+
returnValue: new BN(0).toArrayLike(Buffer, 'be', mLen.toNumber()),
159135
}
160136
}
161137

packages/vm/tests/api/EIPs/eip-2565-modexp-gas-cost.spec.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ tape('EIP-2565 ModExp gas cost tests', (t) => {
3737
}
3838

3939
if (!result.execResult.returnValue.equals(Buffer.from(test.Expected, 'hex'))) {
40+
console.log(result.execResult.returnValue.toString('hex'))
4041
st.fail(`[${testName}]: Return value not the expected value`)
4142
continue
4243
}

0 commit comments

Comments
 (0)