Skip to content

Commit

Permalink
Update initial mcpl
Browse files Browse the repository at this point in the history
  • Loading branch information
ignasirv committed Jan 30, 2024
1 parent 8a7b3cd commit 77a642b
Show file tree
Hide file tree
Showing 4 changed files with 45 additions and 36 deletions.
9 changes: 5 additions & 4 deletions src/processor-utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -374,14 +374,15 @@ async function computeL2TxHash(tx, returnEncoded = false) {
}
// Add value
hash += `${formatL2TxHashParam(tx.value, 32)}`;
let data = tx.data;

Check failure on line 377 in src/processor-utils.js

View workflow job for this annotation

GitHub Actions / build (16.x)

Use object destructuring
// Compute data length
if (tx.data.startsWith('0x')) {
tx.data = tx.data.slice(2);
if (data.startsWith('0x')) {
data = data.slice(2);
}
const dataLength = Math.ceil(tx.data.length / 2);
const dataLength = Math.ceil(data.length / 2);
hash += `${formatL2TxHashParam(dataLength.toString(16), 3)}`;
if (dataLength > 0) {
hash += `${formatL2TxHashParam(tx.data, dataLength)}`;
hash += `${formatL2TxHashParam(data, dataLength)}`;
}
// Add chainID
if (typeof tx.chainID !== 'undefined') {
Expand Down
9 changes: 5 additions & 4 deletions src/processor.js
Original file line number Diff line number Diff line change
Expand Up @@ -360,7 +360,7 @@ module.exports = class Processor {
* finally pay all the fees to the sequencer address
*/
async _processTx() {
this.vcm.setSMTLevels((2 ** this.smt.maxLevel + 250000).toString(2).length);
this.vcm.setSMTLevels((2 ** this.smt.maxLevel + 50000).toString(2).length);
// Compute init processing counters
this.vcm.computeFunctionCounters('batchProcessing', { batchL2DataLength: (this.rawTxs.join('').length - this.rawTxs.length * 2) / 2 });
// Compute rlp parsing counters
Expand All @@ -385,10 +385,10 @@ module.exports = class Processor {
}
for (let i = 0; i < this.decodedTxs.length; i++) {
/**
* Set vcm poseidon levels. Maximum (theorical) levels that can be added in a tx is 250k.
* We count how much can the smt increase in a tx and compute the virtual poseidons with this worst case scenario.
* Set vcm poseidon levels. Maximum (theoretical) levels that can be added in a tx is 50k poseidons.
* We count how much can the smt increase in a tx and compute the virtual poseidons with this worst case scenario. This is a tx full of SSTORE (20000 gas), max gas in a tx is 30M so we can do 1.5k sstore in a tx. Assuming tree already has 0 leafs, increases to 2**11. 11*1.5k = 22.5k * 2 (go up and down in the tree) = 45k poseidon, we round up to 50k for safety reasons.
*/
const maxLevelPerTx = (2 ** this.smt.maxLevel + 250000).toString(2).length;
const maxLevelPerTx = (2 ** this.smt.maxLevel + 50000).toString(2).length;
this.vcm.setSMTLevels(maxLevelPerTx);
const currentDecodedTx = this.decodedTxs[i];

Expand Down Expand Up @@ -682,6 +682,7 @@ module.exports = class Processor {
* We re run the batch with a new maxLevel value at the smt
*/
if (this.smt.maxLevel > maxLevelPerTx) {
console.log('WARNING: smt levels increased more than expected, re running batch with new smt levels');
this._rollbackBatch();
i = 0;
}
Expand Down
1 change: 1 addition & 0 deletions src/virtual-counters-manager-utils.js
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ function expectedModExpCounters(lenB, lenE, lenM, B, E, M) {
counters[key] = a[key] + nTimesEven * b[key] + nTimesOdd * c[key];
}

return counters;
// console.log(JSON.stringify(counters, null, 2));
function computeLenThisBase(x) {
if (x === 0n) return 1;
Expand Down
62 changes: 34 additions & 28 deletions src/virtual-counters-manager.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,9 @@
/* eslint-disable prefer-destructuring */

const totalSteps = 2 ** 23;
// Maximum counters poseidon level when interacting with a small smt (blockInfoTree, touchedAccountsTree..), is constant
const MCPL = 23;
// Maximum counters poseidon level when interacting with a big smt (stateTree), is variable and can be updated
let MCP = 128;
const { Scalar, F1Field } = require('ffjavascript');
const { expectedModExpCounters } = require('./virtual-counters-manager-utils');
Expand Down Expand Up @@ -96,6 +98,7 @@ module.exports = class VirtualCountersManager {
return this.getSnapshotConsumption();
} catch (e) {
this._verbose(`Error computing counters for function ${this.calledFunc}`);
console.log(e);
this._verbose(e);
this._throwError(e);
}
Expand Down Expand Up @@ -320,11 +323,13 @@ module.exports = class VirtualCountersManager {
this._multiCall('_mStoreX', 2);
this._multiCall('_preModExpLoop', Math.floor(input.calldataLength / 32));
this._multiCall('_preModExpLoop', Math.floor(input.returnDataLength / 32));
this._modexp(input.bLen, input.mLen, input.eLen, input.base, input.exponent, input.modulus);
if (input.modulus > 0) {
this._modexp(input.bLen, input.mLen, input.eLen, input.base, input.exponent, input.modulus);
}
}

_modexp(bLen, mLen, eLen, base, exponent, modulus) {
const modexpCounters = expectedModExpCounters(bLen / 32, mLen / 32, eLen / 32, base, exponent, modulus);
const modexpCounters = expectedModExpCounters(Math.ceil(bLen / 32), Math.ceil(mLen / 32), Math.ceil(eLen / 32), base, exponent, modulus);
this._reduceCounters(modexpCounters.steps, 'S');
this._reduceCounters(modexpCounters.binaries, 'B');
this._reduceCounters(modexpCounters.ariths, 'A');
Expand Down Expand Up @@ -507,7 +512,7 @@ module.exports = class VirtualCountersManager {
this._checkInput(input, ['inputSize']);
this._reduceCounters(100, 'S');
this._reduceCounters(2, 'B');
this._saveMem({length: input.inputSize});
this._saveMem({ length: input.inputSize });
this._offsetUtil();
this._multiCall('_opCalldataCopyLoop', Math.floor(input.inputSize / 32));
this._readFromCalldataOffset();
Expand Down Expand Up @@ -544,7 +549,7 @@ module.exports = class VirtualCountersManager {
this._reduceCounters(2 * MCP + Math.ceil(input.bytecodeLen / 56), 'P');
this._reduceCounters(Math.ceil(input.bytecodeLen / 56), 'D');
this._multiCall('_divArith', 2);
this._saveMem({length: input.inputSize});
this._saveMem({ length: input.inputSize });
this._mulArith();
this._reduceCounters(input.inputSize, 'M');
this._multiCall('_opCodeCopyLoop', input.inputSize);
Expand All @@ -559,7 +564,7 @@ module.exports = class VirtualCountersManager {
} else {
this._reduceCounters(40, 'S');
this._reduceCounters(3, 'B');
this._saveMem({length: input.inputSize});
this._saveMem({ length: input.inputSize });
this._divArith();
this._mulArith();
this._multiCall('_opCodeCopyLoop', input.inputSize);
Expand All @@ -584,7 +589,7 @@ module.exports = class VirtualCountersManager {
this._checkInput(input, ['inputSize']);
this._reduceCounters(50, 'S');
this._reduceCounters(2, 'B');
this._saveMem({length: input.inputSize});
this._saveMem({ length: input.inputSize });
this._divArith();
this._mulArith();
this._multiCall('_returnDataCopyLoop', Math.floor(input.inputSize / 32));
Expand Down Expand Up @@ -705,11 +710,11 @@ module.exports = class VirtualCountersManager {

opCreate(input) {
this._opcode(input);
this._checkInput(input, ['bytesNonceLength','inLength']);
this._checkInput(input, ['bytesNonceLength', 'inLength']);
this._reduceCounters(70, 'S');
this._reduceCounters(3, 'B');
this._reduceCounters(3 * MCP, 'P');
this._saveMem({length: input.inLength});
this._saveMem({ length: input.inLength });
this._getLenBytes({ lenBytesInput: input.bytesNonceLength });
this._computeGasSendCall();
this._saveCalldataPointer();
Expand All @@ -723,8 +728,8 @@ module.exports = class VirtualCountersManager {
this._reduceCounters(80, 'S');
this._reduceCounters(5, 'B');
this._maskAddress();
this._saveMem({length: input.inLength});
this._saveMem({length: input.outLength});
this._saveMem({ length: input.inLength });
this._saveMem({ length: input.outLength });
this._isColdAddress();
this._isEmptyAccount();
this._computeGasSendCall();
Expand All @@ -739,8 +744,8 @@ module.exports = class VirtualCountersManager {
this._reduceCounters(80, 'S');
this._reduceCounters(5, 'B');
this._maskAddress();
this._saveMem({length: input.inLength});
this._saveMem({length: input.outLength});
this._saveMem({ length: input.inLength });
this._saveMem({ length: input.outLength });
this._isColdAddress();
this._computeGasSendCall();
this._saveCalldataPointer();
Expand All @@ -753,8 +758,8 @@ module.exports = class VirtualCountersManager {
this._checkInput(input, ['inLength', 'outLength']);
this._reduceCounters(80, 'S');
this._maskAddress();
this._saveMem({length: input.inLength});
this._saveMem({length: input.outLength});
this._saveMem({ length: input.inLength });
this._saveMem({ length: input.outLength });
this._isColdAddress();
this._computeGasSendCall();
this._saveCalldataPointer();
Expand All @@ -767,8 +772,8 @@ module.exports = class VirtualCountersManager {
this._checkInput(input, ['inLength', 'outLength']);
this._reduceCounters(80, 'S');
this._maskAddress();
this._saveMem({length: input.inLength});
this._saveMem({length: input.outLength});
this._saveMem({ length: input.inLength });
this._saveMem({ length: input.outLength });
this._isColdAddress();
this._computeGasSendCall();
this._saveCalldataPointer();
Expand All @@ -778,11 +783,11 @@ module.exports = class VirtualCountersManager {

opCreate2(input) {
this._opcode(input);
this._checkInput(input, ['bytesNonceLength','inLength']);
this._checkInput(input, ['bytesNonceLength', 'inLength']);
this._reduceCounters(80, 'S');
this._reduceCounters(4, 'B');
this._reduceCounters(2 * MCP, 'P');
this._saveMem({length: input.inLength});
this._saveMem({ length: input.inLength });
this._divArith();
this._getLenBytes({ lenBytesInput: input.bytesNonceLength });
this._computeGasSendCall();
Expand All @@ -793,10 +798,10 @@ module.exports = class VirtualCountersManager {

opReturn(input) {
this._opcode(input);
this._checkInput(input, ['isCreate', 'isDeploy','returnLength']);
this._checkInput(input, ['isCreate', 'isDeploy', 'returnLength']);
this._reduceCounters(30, 'S');
this._reduceCounters(1, 'B');
this._saveMem({length: input.returnLength});
this._saveMem({ length: input.returnLength });
if (input.isCreate || input.isDeploy) {
if (input.isCreate) {
this._reduceCounters(25, 'S');
Expand Down Expand Up @@ -826,7 +831,7 @@ module.exports = class VirtualCountersManager {
this._reduceCounters(1, 'B');
this._revertTouched();
this._revertBlockInfoTree();
this._saveMem({length: input.revertSize});
this._saveMem({ length: input.revertSize });
this._multiCall('_opRevertLoop', Math.floor(input.revertSize / 32));
this._mLoadX();
this._mStoreX();
Expand Down Expand Up @@ -903,7 +908,7 @@ module.exports = class VirtualCountersManager {
this._checkInput(input, ['inputSize']);
this._reduceCounters(40, 'S');
this._reduceCounters(Math.ceil((input.inputSize + 1) / 32), 'K');
this._saveMem({length: input.inputSize});
this._saveMem({ length: input.inputSize });
this._multiCall('_divArith', 2);
this._mulArith();
this._multiCall('_opSha3Loop', Math.floor(input.inputSize / 32));
Expand Down Expand Up @@ -976,7 +981,7 @@ module.exports = class VirtualCountersManager {
this._opcode(input);
this._checkInput(input, ['inputSize']);
this._reduceCounters(30 + 8 * 4, 'S'); // Count steps as if topics is 4
this._saveMem({length: input.inputSize});
this._saveMem({ length: input.inputSize });
this._mulArith();
this._divArith();
this._reduceCounters(Math.ceil(input.inputSize / 56) + 4, 'P');
Expand Down Expand Up @@ -1295,23 +1300,23 @@ module.exports = class VirtualCountersManager {
opMLoad(input) {
this._opcode(input);
this._reduceCounters(8, 'S');
this._saveMem({length: 32});
this._saveMem({ length: 32 });
this._mLoad32();
}

opMStore(input) {
this._opcode(input);
this._reduceCounters(22, 'S');
this._reduceCounters(1, 'M');
this._saveMem({length: 32});
this._saveMem({ length: 32 });
this._offsetUtil();
}

opMStore8(input) {
this._opcode(input);
this._reduceCounters(13, 'S');
this._reduceCounters(1, 'M');
this._saveMem({length: 1});
this._saveMem({ length: 1 });
this._offsetUtil();
}

Expand Down Expand Up @@ -1527,9 +1532,10 @@ module.exports = class VirtualCountersManager {

_saveMem(input) {
this._checkInput(input, ['length']);
if(input.length === 0) {
if (input.length === 0) {
this._reduceCounters(12, 'S');
this._reduceCounters(1, 'B');

return;
}
this._reduceCounters(50, 'S');
Expand Down Expand Up @@ -1632,7 +1638,7 @@ module.exports = class VirtualCountersManager {
this._reduceCounters(Math.ceil((input.bytecodeLength + 1) / 56), 'P');
this._reduceCounters(Math.ceil((input.bytecodeLength + 1) / 56), 'D');
// This arith is used to compute the keccaks consumption so its bytecodeLength / 56, in case bytecodeLength < 56, no ariths are used
if(input.bytecodeLength >= 56) {
if (input.bytecodeLength >= 56) {
this._divArith();
}
}
Expand Down

0 comments on commit 77a642b

Please sign in to comment.