mirror of
https://github.com/logos-storage/plonky2.git
synced 2026-01-08 08:43:06 +00:00
initial work on blake precompile
This commit is contained in:
parent
c0ced26f5e
commit
5f564b6782
@ -1,3 +1,55 @@
|
||||
global precompile_blake2_f:
|
||||
// TODO
|
||||
PANIC
|
||||
// stack: address, retdest, new_ctx, kexit_info, ret_offset, ret_size
|
||||
%pop2
|
||||
// stack: new_ctx, kexit_info, ret_offset, ret_size
|
||||
DUP1
|
||||
SET_CONTEXT
|
||||
// stack: (empty)
|
||||
PUSH 0x100000000 // = 2^32 (is_kernel = true)
|
||||
// stack: kexit_info
|
||||
|
||||
// get various inputs out of SEGMENT_CALLDATA
|
||||
|
||||
// charge gas (based on rounds)
|
||||
|
||||
// Copy the call data to the kernel general segment (blake2b expects it there) and call blake2b.
|
||||
%calldatasize
|
||||
GET_CONTEXT
|
||||
// stack: ctx, size
|
||||
|
||||
// TODO: change
|
||||
// The next block of code is equivalent to the following %stack macro call
|
||||
// (unfortunately the macro call takes too long to expand dynamically).
|
||||
//
|
||||
// %stack (ctx, size) ->
|
||||
// (
|
||||
// 0, @SEGMENT_KERNEL_GENERAL, 1, // DST
|
||||
// ctx, @SEGMENT_CALLDATA, 0, // SRC
|
||||
// size, blake2_f, // count, retdest
|
||||
// 0, size, blake2_f_contd // blake2b input: virt, num_bytes, retdest
|
||||
// )
|
||||
//
|
||||
PUSH 0
|
||||
PUSH blake2_f
|
||||
DUP4
|
||||
PUSH 0
|
||||
PUSH @SEGMENT_CALLDATA
|
||||
PUSH blake2_f_contd
|
||||
SWAP7
|
||||
SWAP6
|
||||
PUSH 1
|
||||
PUSH @SEGMENT_KERNEL_GENERAL
|
||||
PUSH 0
|
||||
|
||||
%jump(memcpy)
|
||||
|
||||
blake2_f_contd:
|
||||
// stack: hash, kexit_info
|
||||
// Store the result hash to the parent's return data using `mstore_unpacking`.
|
||||
|
||||
|
||||
|
||||
%mstore_parent_context_metadata(@CTX_METADATA_RETURNDATA_SIZE, 32)
|
||||
%mload_context_metadata(@CTX_METADATA_PARENT_CONTEXT)
|
||||
%stack (parent_ctx, hash) -> (parent_ctx, @SEGMENT_RETURNDATA, 0, hash, 32, pop_and_return_success)
|
||||
%jump(mstore_unpacking)
|
||||
|
||||
@ -23,6 +23,7 @@ global precompile_sha256:
|
||||
// Copy the call data to the kernel general segment (sha2 expects it there) and call sha2.
|
||||
%calldatasize
|
||||
GET_CONTEXT
|
||||
// stack: ctx, size
|
||||
|
||||
// The next block of code is equivalent to the following %stack macro call
|
||||
// (unfortunately the macro call takes too long to expand dynamically).
|
||||
|
||||
145
evm/src/cpu/kernel/asm/hash/blake2b/blake2_f.asm
Normal file
145
evm/src/cpu/kernel/asm/hash/blake2b/blake2_f.asm
Normal file
@ -0,0 +1,145 @@
|
||||
global blake2_f:
|
||||
// stack: rounds, h0...h7, m0...m15, t0, t1, flag, retdest
|
||||
|
||||
// Store the hash values.
|
||||
%blake2b_hash_value_addr
|
||||
// stack: addr, rounds, h0...h7, m0...m15, t0, t1, flag, retdest
|
||||
%rep 8
|
||||
// stack: addr, rounds, h_i, ...
|
||||
%stack (addr, rounds, h_i) -> (addr, h_i, addr, rounds)
|
||||
// stack: addr, h_i, addr, rounds, ...
|
||||
%mstore_kernel_general
|
||||
%increment
|
||||
%endrep
|
||||
|
||||
// stack: addr, rounds, m0...m15, t0, t1, flag, retdest
|
||||
POP
|
||||
// stack: rounds, m0...m15, t0, t1, flag, retdest
|
||||
|
||||
// Save the message to the message working space.
|
||||
%blake2b_message_addr
|
||||
// stack: message_addr, rounds, m0...m15, t0, t1, flag, retdest
|
||||
%rep 16
|
||||
// stack: message_addr, rounds, m_i, ...
|
||||
%stack (message_addr, rounds, m_i) -> (message_addr, m_i, message_addr, rounds)
|
||||
// stack: message_addr, m_i, message_addr, rounds, ...
|
||||
%mstore_kernel_general
|
||||
%increment
|
||||
%endrep
|
||||
|
||||
// stack: message_addr, rounds, t0, t1, flag, retdest
|
||||
POP
|
||||
// stack: rounds, t0, t1, flag, retdest
|
||||
|
||||
|
||||
|
||||
|
||||
%blake2b_hash_value_addr
|
||||
%add_const(7)
|
||||
%rep 8
|
||||
// stack: addr, ...
|
||||
DUP1
|
||||
// stack: addr, addr, ...
|
||||
%mload_kernel_general
|
||||
// stack: val, addr, ...
|
||||
SWAP1
|
||||
// stack: addr, val, ...
|
||||
%decrement
|
||||
%endrep
|
||||
// stack: addr, h_0, ..., h_7, rounds, t0, t1, flag, retdest
|
||||
POP
|
||||
// stack: h_0, ..., h_7, rounds, t0, t1, flag, retdest
|
||||
|
||||
// Store the initial 16 values of the internal state.
|
||||
%blake2b_internal_state_addr
|
||||
// stack: start, h_0, ..., h_7, rounds, t0, t1, flag, retdest
|
||||
|
||||
// First eight words of the internal state: current hash value h_0, ..., h_7.
|
||||
%rep 8
|
||||
SWAP1
|
||||
DUP2
|
||||
%mstore_kernel_general
|
||||
%increment
|
||||
%endrep
|
||||
// stack: start + 8, rounds, t0, t1, flag, retdest
|
||||
|
||||
// Next four values of the internal state: first four IV values.
|
||||
PUSH 0
|
||||
// stack: 0, start + 8, rounds, t0, t1, flag, retdest
|
||||
%rep 4
|
||||
// stack: i, loc, ...
|
||||
DUP1
|
||||
// stack: i, i, loc, ...
|
||||
%blake2b_iv
|
||||
// stack: IV_i, i, loc, ...
|
||||
DUP3
|
||||
// stack: loc, IV_i, i, loc, ...
|
||||
%mstore_kernel_general
|
||||
// stack: i, loc, ...
|
||||
%increment
|
||||
SWAP1
|
||||
%increment
|
||||
SWAP1
|
||||
// stack: i + 1, loc + 1,...
|
||||
%endrep
|
||||
// stack: 4, start + 12, rounds, t0, t1, flag, retdest
|
||||
POP
|
||||
// stack: start + 12, rounds, t0, t1, flag, retdest
|
||||
SWAP4
|
||||
// stack: flag, rounds, t0, t1, start + 12, retdest
|
||||
%mul_const(0xFFFFFFFFFFFFFFFF)
|
||||
// stack: invert_if_flag, rounds, t0, t1, start + 12, retdest
|
||||
%stack (inv, r, t0, t1, s) -> (4, s, t0, t1, inv, 0, r)
|
||||
// stack: 4, start + 12, t0, t1, invert_if_flag, 0, rounds, retdest
|
||||
|
||||
|
||||
// Last four values of the internal state: last four IV values, XOR'd with
|
||||
// the values (t0, t1, invert_if_flag, 0).
|
||||
%rep 4
|
||||
// stack: i, loc, val, next_val,...
|
||||
DUP1
|
||||
// stack: i, i, loc, val, next_val,...
|
||||
%blake2b_iv
|
||||
// stack: IV_i, i, loc, val, next_val,...
|
||||
DUP4
|
||||
// stack: val, IV_i, i, loc, val, next_val,...
|
||||
XOR
|
||||
// stack: val ^ IV_i, i, loc, val, next_val,...
|
||||
DUP3
|
||||
// stack: loc, val ^ IV_i, i, loc, val, next_val,...
|
||||
%mstore_kernel_general
|
||||
// stack: i, loc, val, next_val,...
|
||||
%increment
|
||||
// stack: i + 1, loc, val, next_val,...
|
||||
SWAP2
|
||||
// stack: val, loc, i + 1, next_val,...
|
||||
POP
|
||||
// stack: loc, i + 1, next_val,...
|
||||
%increment
|
||||
// stack: loc + 1, i + 1, next_val,...
|
||||
SWAP1
|
||||
// stack: i + 1, loc + 1, next_val,...
|
||||
%endrep
|
||||
// stack: 8, start + 16, rounds, retdest
|
||||
%pop2
|
||||
// stack: rounds, retdest
|
||||
|
||||
// Run rounds of G functions.
|
||||
PUSH g_functions_return
|
||||
// stack: g_functions_return, rounds, retdest
|
||||
SWAP1
|
||||
// stack: rounds, g_functions_return, retdest
|
||||
%blake2b_internal_state_addr
|
||||
// stack: start, rounds, g_functions_return, retdest
|
||||
%jump(run_rounds_g_function)
|
||||
g_functions_return:
|
||||
// Finalize hash value.
|
||||
// stack: retdest
|
||||
PUSH hash_generate_return
|
||||
// stack: hash_generate_return, retdest
|
||||
%jump(blake2b_generate_all_hash_values)
|
||||
hash_generate_return:
|
||||
// stack: h_0', h_1', h_2', h_3', h_4', h_5', h_6', h_7', retdest
|
||||
%stack (h: 8, retdest) -> (retdest, h)
|
||||
// stack: retdest, h_0', h_1', h_2', h_3', h_4', h_5', h_6', h_7'
|
||||
JUMP
|
||||
@ -187,9 +187,10 @@ compression_loop:
|
||||
// Run 12 rounds of G functions.
|
||||
PUSH g_functions_return
|
||||
// stack: g_functions_return, cur_block, retdest
|
||||
PUSH 12
|
||||
%blake2b_internal_state_addr
|
||||
// stack: start, g_functions_return, cur_block, retdest
|
||||
%jump(run_12_rounds_g_function)
|
||||
// stack: start, 12, g_functions_return, cur_block, retdest
|
||||
%jump(run_rounds_g_function)
|
||||
g_functions_return:
|
||||
// Finalize hash value.
|
||||
// stack: cur_block, retdest
|
||||
|
||||
@ -149,27 +149,29 @@ run_g_function_round:
|
||||
// stack: retdest, round, start
|
||||
JUMP
|
||||
|
||||
global run_12_rounds_g_function:
|
||||
// stack: start, retdest
|
||||
global run_rounds_g_function:
|
||||
// stack: start, rounds, retdest
|
||||
PUSH 0
|
||||
// stack: round=0, start, retdest
|
||||
// stack: round=0, start, rounds, retdest
|
||||
run_next_round_g_function:
|
||||
// stack: round, start, retdest
|
||||
// stack: round, start, rounds, retdest
|
||||
PUSH run_next_round_g_function_return
|
||||
// stack: run_next_round_g_function_return, round, start, retdest
|
||||
// stack: run_next_round_g_function_return, round, start, rounds, retdest
|
||||
SWAP2
|
||||
// stack: start, round, run_next_round_g_function_return, retdest
|
||||
SWAP1
|
||||
// stack: round, start, run_next_round_g_function_return, retdest
|
||||
%jump(run_g_function_round)
|
||||
run_next_round_g_function_return:
|
||||
// stack: round, start, retdest
|
||||
// stack: round, start, rounds, retdest
|
||||
%increment
|
||||
// stack: round+1, start, retdest
|
||||
// stack: round+1, start, rounds, retdest
|
||||
DUP1
|
||||
// stack: round+1, round+1, start, retdest
|
||||
%lt_const(12)
|
||||
// stack: round+1 < 12, round+1, start, retdest
|
||||
// stack: round+1, round+1, start, rounds, retdest
|
||||
DUP4
|
||||
// stack: rounds, round+1, round+1, start, rounds, retdest
|
||||
GT
|
||||
// stack: round+1 < rounds, round+1, start, rounds, retdest
|
||||
%jumpi(run_next_round_g_function)
|
||||
// stack: round+1, start, retdest
|
||||
%pop2
|
||||
|
||||
@ -1,3 +1,4 @@
|
||||
// Generate a new hash value from the previous hash value and two elements of the internal state.
|
||||
blake2b_generate_new_hash_value:
|
||||
// stack: i, retdest
|
||||
%blake2b_hash_value_addr
|
||||
|
||||
@ -225,5 +225,5 @@ const PRECOMPILES_GAS: [(&str, u16); 13] = [
|
||||
("BN_MUL_GAS", 6_000),
|
||||
("SNARKV_STATIC_GAS", 45_000),
|
||||
("SNARKV_DYNAMIC_GAS", 34_000),
|
||||
("BLAKE2_F_DYNAMIC_GAS", 1),
|
||||
("BLAKE2_F__GAS", 1),
|
||||
];
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user