-
Notifications
You must be signed in to change notification settings - Fork 50
/
Copy pathidentity.zkasm
99 lines (85 loc) · 3.53 KB
/
identity.zkasm
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
/**
* @link [https://www.evm.codes/precompiled#0x04?fork=berlin]
* @zk-counters
* - dynamic steps: 100
* - dynamic binary: 1
* @process-precompiled
* - stack input: [data]
* - stack output: [data]
*/
IDENTITY:
%MAX_CNT_STEPS - STEP - 100 :JMPN(outOfCountersStep)
%MAX_CNT_BINARY - CNT_BINARY - 1 :JMPN(outOfCountersBinary)
; Move balances if value > 0 just before executing the contract CALL
$ => B :MLOAD(txValue)
0 => A
zkPC+2 => RR
$ :LT, JMPC(moveBalances)
GAS - %IDENTITY_GAS => GAS :JMPN(outOfGas)
$ => C :MLOAD(txCalldataLen)
;(C+31)/32 => A
C + 31 => A
A :MSTORE(arithA)
32 :MSTORE(arithB), CALL(divARITH); in: [arithA, arithB] out: [arithRes1: arithA/arithB, arithRes2: arithA%arithB]
$ => A :MLOAD(arithRes1)
GAS - %IDENTITY_WORD_GAS*A => GAS :JMPN(outOfGas)
0 => E, D :MSTORE(retDataOffset)
C :MSTORE(retDataLength)
32 :MSTORE(readXFromCalldataLength)
IDENTITYloop:
%MAX_CNT_STEPS - STEP - 100 :JMPN(outOfCountersStep)
; Copy from calldata to memory
C :JMPZ(IDENTITYreturn)
C - 32 :JMPN(IDENTITYfinal)
D :MSTORE(readXFromCalldataOffset), CALL(readFromCalldataOffset); in: [readXFromCalldataOffset: offset value, readXFromCalldataLength: length value], out: [readXFromCalldataResult: result value]
$ => A :MLOAD(readXFromCalldataResult)
D + 32 => D
A :MSTORE(bytesToStore), CALL(MSTORE32); in: [bytesToStore, E: offset] out: [E: new offset]
C - 32 => C :JMP(IDENTITYloop)
IDENTITYfinal:
C :MSTORE(readXFromCalldataLength)
D :MSTORE(readXFromCalldataOffset), CALL(readFromCalldataOffset); in: [readXFromCalldataOffset: offset value, readXFromCalldataLength: length value], out: [readXFromCalldataResult: result value]
$ => A :MLOAD(readXFromCalldataResult)
A :MSTORE(bytesToStore), CALL(MSTOREX); in: [bytesToStore, E: offset, C: length] out: [E: new offset]
IDENTITYreturn:
; handle CTX
$ => A :MLOAD(originCTX), JMPZ(handleGas)
; set retDataCTX
$ => B :MLOAD(currentCTX)
A => CTX
B :MSTORE(retDataCTX)
B => CTX
%MAX_CNT_BINARY - CNT_BINARY - 1 :JMPN(outOfCountersBinary)
; Copy from memory current CTX to memory origin CTX
0 => E
$ => B :MLOAD(retCallLength)
; Get lower between retCallLength and
$ => A :MLOAD(retDataLength)
$ :LT, JMPC(IDENTITYreturn2)
B => C
$ => B :MLOAD(retCallOffset), JMP(IDENTITYreturnLoop)
IDENTITYreturn2:
A => C
$ => B :MLOAD(retCallOffset)
IDENTITYreturnLoop:
%MAX_CNT_STEPS - STEP - 200 :JMPN(outOfCountersStep)
C :JMPZ(IDENTITYend)
C - 32 :JMPN(IDENTITYreturnFinal)
:CALL(MLOAD32)
E => D
$ => CTX :MLOAD(originCTX)
B => E
A :MSTORE(bytesToStore), CALL(MSTORE32); in: [bytesToStore, E: offset] out: [E: new offset]
E => B
D => E
C - 32 => C
$ => CTX :MLOAD(currentCTX), JMP(IDENTITYreturnLoop)
IDENTITYreturnFinal:
:CALL(MLOADX)
$ => CTX :MLOAD(originCTX)
B => E
A :MSTORE(bytesToStore), CALL(MSTOREX)
$ => CTX :MLOAD(currentCTX)
IDENTITYend:
$ => CTX :MLOAD(originCTX)
CTX :MSTORE(currentCTX), JMP(preEnd)