Barretenberg
The ZK-SNARK library at the core of Aztec
Loading...
Searching...
No Matches
get_env_var.test.cpp
Go to the documentation of this file.
1#include <gmock/gmock.h>
2#include <gtest/gtest.h>
3
4#include <cstdint>
5
18
19namespace bb::avm2::constraining {
20namespace {
21
22using testing::PublicInputsBuilder;
23using tracegen::ExecutionTraceBuilder;
24using tracegen::PrecomputedTraceBuilder;
25using tracegen::PublicInputsTraceBuilder;
26using tracegen::TestTraceContainer;
28using C = Column;
29using get_env_var = bb::avm2::get_env_var<FF>;
30
31TEST(GetEnvVarConstrainingTest, EmptyRow)
32{
33 check_relation<get_env_var>(testing::empty_trace());
34}
35
36TEST(GetEnvVarConstrainingTest, AddressContextVariable)
37{
38 // Test reading ADDRESS from context
39 TestTraceContainer trace({
40 { { C::precomputed_first_row, 1 } },
41 // Getting ADDRESS env var
42 { { C::execution_sel, 1 },
43 { C::execution_sel_execute_get_env_var, 1 },
44 { C::execution_is_address, 1 },
45 { C::execution_register_0_, FF(1234567890) },
46 { C::execution_contract_address, FF(1234567890) },
47 { C::execution_rop_1_, 0 } }, // ADDRESS enum = 0
48 // Not getting ADDRESS
49 { { C::execution_sel, 1 },
50 { C::execution_sel_execute_get_env_var, 1 },
51 { C::execution_is_address, 0 },
52 { C::execution_register_0_, 999 },
53 { C::execution_contract_address, FF(1234567890) },
54 { C::execution_rop_1_, 1 } }, // SENDER enum = 1
55 });
56
57 check_relation<get_env_var>(trace, get_env_var::SR_ADDRESS_FROM_CONTEXT);
58
59 // Negative test: getting ADDRESS but register != contract_address
60 trace.set(C::execution_register_0_, 1, FF(0xDEADBEEF));
62 "ADDRESS_FROM_CONTEXT");
63}
64
65TEST(GetEnvVarConstrainingTest, SenderContextVariable)
66{
67 // Test reading SENDER from context
68 TestTraceContainer trace({
69 { { C::precomputed_first_row, 1 } },
70 // Getting SENDER env var
71 { { C::execution_sel, 1 },
72 { C::execution_sel_execute_get_env_var, 1 },
73 { C::execution_is_sender, 1 },
74 { C::execution_register_0_, FF(1234567890) },
75 { C::execution_msg_sender, FF(1234567890) },
76 { C::execution_rop_1_, 1 } }, // SENDER enum = 1
77 // Not getting SENDER
78 { { C::execution_sel, 1 },
79 { C::execution_sel_execute_get_env_var, 1 },
80 { C::execution_is_sender, 0 },
81 { C::execution_register_0_, 999 },
82 { C::execution_msg_sender, FF(1234567890) },
83 { C::execution_rop_1_, 0 } }, // ADDRESS enum = 0
84 });
85
86 check_relation<get_env_var>(trace, get_env_var::SR_SENDER_FROM_CONTEXT);
87
88 // Negative test: getting SENDER but register != msg_sender
89 trace.set(C::execution_register_0_, 1, FF(0xDEADBEEF));
91 "SENDER_FROM_CONTEXT");
92}
93
94TEST(GetEnvVarConstrainingTest, TransactionFeeContextVariable)
95{
96 // Test reading TRANSACTIONFEE from context
97 TestTraceContainer trace({
98 { { C::precomputed_first_row, 1 } },
99 // Getting TRANSACTIONFEE env var
100 { { C::execution_sel, 1 },
101 { C::execution_sel_execute_get_env_var, 1 },
102 { C::execution_is_transactionfee, 1 },
103 { C::execution_register_0_, 1000 },
104 { C::execution_transaction_fee, 1000 },
105 { C::execution_rop_1_, 2 } }, // TRANSACTIONFEE enum = 2
106 // Not getting TRANSACTIONFEE
107 { { C::execution_sel, 1 },
108 { C::execution_sel_execute_get_env_var, 1 },
109 { C::execution_is_transactionfee, 0 },
110 { C::execution_register_0_, 999 },
111 { C::execution_transaction_fee, 1000 },
112 { C::execution_rop_1_, 0 } }, // ADDRESS enum = 0
113 });
114
115 check_relation<get_env_var>(trace, get_env_var::SR_TRANSACTION_FEE_FROM_CONTEXT);
116
117 // Negative test: getting TRANSACTIONFEE but register != transaction_fee
118 trace.set(C::execution_register_0_, 1, 2000);
120 "TRANSACTION_FEE_FROM_CONTEXT");
121}
122
123TEST(GetEnvVarConstrainingTest, IsStaticCallContextVariable)
124{
125 // Test reading ISSTATICCALL from context
126 TestTraceContainer trace({
127 { { C::precomputed_first_row, 1 } },
128 // Getting ISSTATICCALL env var (true)
129 { { C::execution_sel, 1 },
130 { C::execution_sel_execute_get_env_var, 1 },
131 { C::execution_is_isstaticcall, 1 },
132 { C::execution_register_0_, 1 },
133 { C::execution_is_static, 1 },
134 { C::execution_rop_1_, 9 } }, // ISSTATICCALL enum = 9
135 // Getting ISSTATICCALL env var (false)
136 { { C::execution_sel, 1 },
137 { C::execution_sel_execute_get_env_var, 1 },
138 { C::execution_is_isstaticcall, 1 },
139 { C::execution_register_0_, 0 },
140 { C::execution_is_static, 0 },
141 { C::execution_rop_1_, 9 } }, // ISSTATICCALL enum = 9
142 // Not getting ISSTATICCALL
143 { { C::execution_sel, 1 },
144 { C::execution_sel_execute_get_env_var, 1 },
145 { C::execution_is_isstaticcall, 0 },
146 { C::execution_register_0_, 999 },
147 { C::execution_is_static, 1 },
148 { C::execution_rop_1_, 0 } }, // ADDRESS enum = 0
149 });
150
151 check_relation<get_env_var>(trace, get_env_var::SR_ISSTATICCALL_FROM_CONTEXT);
152
153 // Negative test: getting ISSTATICCALL but register != is_static
154 trace.set(C::execution_register_0_, 1, 0);
156 "ISSTATICCALL_FROM_CONTEXT");
157}
158
159TEST(GetEnvVarConstrainingTest, L2GasLeftGasVariable)
160{
161 // Test reading L2GASLEFT from gas columns
162 TestTraceContainer trace({
163 { { C::precomputed_first_row, 1 } },
164 // Getting L2GASLEFT env var
165 { { C::execution_sel, 1 },
166 { C::execution_sel_execute_get_env_var, 1 },
167 { C::execution_is_l2gasleft, 1 },
168 { C::execution_register_0_, 7500 }, // limit - used = 10000 - 2500
169 { C::execution_l2_gas_limit, 10000 },
170 { C::execution_l2_gas_used, 2500 },
171 { C::execution_rop_1_, 10 } }, // L2GASLEFT enum = 10
172 // Not getting L2GASLEFT
173 { { C::execution_sel, 1 },
174 { C::execution_sel_execute_get_env_var, 1 },
175 { C::execution_is_l2gasleft, 0 },
176 { C::execution_register_0_, 999 },
177 { C::execution_l2_gas_limit, 10000 },
178 { C::execution_l2_gas_used, 2500 },
179 { C::execution_rop_1_, 0 } }, // ADDRESS enum = 0
180 });
181
182 check_relation<get_env_var>(trace, get_env_var::SR_L2GASLEFT_FROM_GAS);
183
184 // Negative test: getting L2GASLEFT but register != (limit - used)
185 trace.set(C::execution_register_0_, 1, 5000);
187 "L2GASLEFT_FROM_GAS");
188}
189
190TEST(GetEnvVarConstrainingTest, DaGasLeftGasVariable)
191{
192 // Test reading DAGASLEFT from gas columns
193 TestTraceContainer trace({
194 { { C::precomputed_first_row, 1 } },
195 // Getting DAGASLEFT env var
196 { { C::execution_sel, 1 },
197 { C::execution_sel_execute_get_env_var, 1 },
198 { C::execution_is_dagasleft, 1 },
199 { C::execution_register_0_, 3000 }, // limit - used = 5000 - 2000
200 { C::execution_da_gas_limit, 5000 },
201 { C::execution_da_gas_used, 2000 },
202 { C::execution_rop_1_, 11 } }, // DAGASLEFT enum = 11
203 // Not getting DAGASLEFT
204 { { C::execution_sel, 1 },
205 { C::execution_sel_execute_get_env_var, 1 },
206 { C::execution_is_dagasleft, 0 },
207 { C::execution_register_0_, 999 },
208 { C::execution_da_gas_limit, 5000 },
209 { C::execution_da_gas_used, 2000 },
210 { C::execution_rop_1_, 0 } }, // ADDRESS enum = 0
211 });
212
213 check_relation<get_env_var>(trace, get_env_var::SR_DAGASLEFT_FROM_GAS);
214
215 // Negative test: getting DAGASLEFT but register != (limit - used)
216 trace.set(C::execution_register_0_, 1, 1000);
218 "DAGASLEFT_FROM_GAS");
219}
220
221TEST(GetEnvVarConstrainingTest, NoSideEffectsWhenNotGettingEnvVar)
222{
223 // Test that when sel_should_get_env_var = 0, the constraints don't interfere
224 TestTraceContainer trace({
225 { { C::precomputed_first_row, 1 } },
226 // Not getting env var - all context/gas values can be arbitrary
227 { { C::execution_sel, 1 },
228 { C::execution_sel_execute_get_env_var, 0 },
229 { C::execution_is_address, 1 }, // This is set but shouldn't matter
230 { C::execution_register_0_, 0 }, // Must be 0 when not getting env var
231 { C::execution_contract_address, FF(1234567890) }, // Arbitrary
232 { C::execution_msg_sender, FF(1234567890) }, // Arbitrary
233 { C::execution_l2_gas_limit, 10000 }, // Arbitrary
234 { C::execution_l2_gas_used, 5000 }, // Arbitrary
235 { C::execution_rop_1_, 0 } }, // ADDRESS enum = 0
236 });
237
238 // Should pass because sel_should_get_env_var = 0 disables the context/gas constraints
239 check_relation<get_env_var>(trace);
240}
241
242TEST(GetEnvVarConstrainingTest, ComplexTraceWithAllEnumsAndInteractions)
243{
244 auto test_public_inputs = PublicInputsBuilder().rand_global_variables().build();
245
246 AztecAddress sender = 0x424242;
248 uint256_t transaction_fee = 66666;
249 bool is_static_call = true;
250 uint256_t l2_gas_limit = 10000;
251 uint256_t l2_gas_used = 2500;
252 uint256_t da_gas_limit = 5000;
253 uint256_t da_gas_used = 2000;
254
255 // Test that an invalid enum value results in an error
256 TestTraceContainer trace({
257 { { C::precomputed_first_row, 1 } },
258 // address
259 { { C::execution_sel, 1 },
260 { C::execution_contract_address, contract_address },
261 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::ADDRESS) },
262 { C::execution_sel_should_execute_opcode, 1 },
263 // Do it! No prior error
264 { C::execution_sel_execute_get_env_var, 1 },
265 // from precomputed table
266 { C::execution_sel_opcode_error, 0 }, // valid enum
267 { C::execution_sel_envvar_pi_lookup_col0, 0 },
268 { C::execution_sel_envvar_pi_lookup_col1, 0 },
269 { C::execution_envvar_pi_row_idx, 0 }, // none
270 { C::execution_is_address, 1 },
271 { C::execution_is_sender, 0 },
272 { C::execution_is_transactionfee, 0 },
273 { C::execution_is_isstaticcall, 0 },
274 { C::execution_is_l2gasleft, 0 },
275 { C::execution_is_dagasleft, 0 },
276 // output
277 { C::execution_register_0_, contract_address },
278 // nothing from pis
279 { C::execution_value_from_pi, 0 },
280 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::FF) } },
281 // sender
282 { { C::execution_sel, 1 },
283 { C::execution_msg_sender, sender },
284 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::SENDER) },
285 { C::execution_sel_should_execute_opcode, 1 },
286 // Do it! No prior error
287 { C::execution_sel_execute_get_env_var, 1 },
288 // from precomputed table
289 { C::execution_sel_opcode_error, 0 }, // valid enum
290 { C::execution_sel_envvar_pi_lookup_col0, 0 },
291 { C::execution_sel_envvar_pi_lookup_col1, 0 },
292 { C::execution_envvar_pi_row_idx, 0 }, // none
293 { C::execution_is_address, 0 },
294 { C::execution_is_sender, 1 },
295 { C::execution_is_transactionfee, 0 },
296 { C::execution_is_isstaticcall, 0 },
297 { C::execution_is_l2gasleft, 0 },
298 { C::execution_is_dagasleft, 0 },
299 // output
300 { C::execution_register_0_, sender },
301 // nothing from pis
302 { C::execution_value_from_pi, 0 },
303 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::FF) } },
304 // transaction fee
305 { { C::execution_sel, 1 },
306 { C::execution_transaction_fee, transaction_fee },
307 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::TRANSACTIONFEE) },
308 { C::execution_sel_should_execute_opcode, 1 },
309 // Do it! No prior error
310 { C::execution_sel_execute_get_env_var, 1 },
311 // from precomputed table
312 { C::execution_sel_opcode_error, 0 }, // valid enum
313 { C::execution_sel_envvar_pi_lookup_col0, 0 },
314 { C::execution_sel_envvar_pi_lookup_col1, 0 },
315 { C::execution_envvar_pi_row_idx, 0 }, // none
316 { C::execution_is_address, 0 },
317 { C::execution_is_sender, 0 },
318 { C::execution_is_transactionfee, 1 },
319 { C::execution_is_isstaticcall, 0 },
320 { C::execution_is_l2gasleft, 0 },
321 { C::execution_is_dagasleft, 0 },
322 // output
323 { C::execution_register_0_, transaction_fee },
324 // nothing from pis
325 { C::execution_value_from_pi, 0 },
326 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::FF) } },
327 // chain id
328 { { C::execution_sel, 1 },
329 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::CHAINID) },
330 { C::execution_sel_should_execute_opcode, 1 },
331 // Do it! No prior error
332 { C::execution_sel_execute_get_env_var, 1 },
333 // from precomputed table
334 { C::execution_sel_opcode_error, 0 }, // valid enum
335 { C::execution_sel_envvar_pi_lookup_col0, 1 },
336 { C::execution_sel_envvar_pi_lookup_col1, 0 },
337 { C::execution_envvar_pi_row_idx, AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_CHAIN_ID_ROW_IDX },
338 { C::execution_is_address, 0 },
339 { C::execution_is_sender, 0 },
340 { C::execution_is_transactionfee, 0 },
341 { C::execution_is_isstaticcall, 0 },
342 { C::execution_is_l2gasleft, 0 },
343 { C::execution_is_dagasleft, 0 },
344 // output, looked up from PIs
345 { C::execution_register_0_, test_public_inputs.globalVariables.chainId },
346 // value from pi should match
347 { C::execution_value_from_pi, test_public_inputs.globalVariables.chainId },
348 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::FF) } },
349 // version
350 { { C::execution_sel, 1 },
351 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::VERSION) },
352 { C::execution_sel_should_execute_opcode, 1 },
353 // Do it! No prior error
354 { C::execution_sel_execute_get_env_var, 1 },
355 // from precomputed table
356 { C::execution_sel_opcode_error, 0 }, // valid enum
357 { C::execution_sel_envvar_pi_lookup_col0, 1 },
358 { C::execution_sel_envvar_pi_lookup_col1, 0 },
359 { C::execution_envvar_pi_row_idx, AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_VERSION_ROW_IDX },
360 { C::execution_is_address, 0 },
361 { C::execution_is_sender, 0 },
362 { C::execution_is_transactionfee, 0 },
363 { C::execution_is_isstaticcall, 0 },
364 { C::execution_is_l2gasleft, 0 },
365 { C::execution_is_dagasleft, 0 },
366 // output, looked up from PIs
367 { C::execution_register_0_, test_public_inputs.globalVariables.version },
368 // value from pi should match
369 { C::execution_value_from_pi, test_public_inputs.globalVariables.version },
370 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::FF) } },
371 // block number
372 { { C::execution_sel, 1 },
373 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::BLOCKNUMBER) },
374 { C::execution_sel_should_execute_opcode, 1 },
375 // Do it! No prior error
376 { C::execution_sel_execute_get_env_var, 1 },
377 // from precomputed table
378 { C::execution_sel_opcode_error, 0 }, // valid enum
379 { C::execution_sel_envvar_pi_lookup_col0, 1 },
380 { C::execution_sel_envvar_pi_lookup_col1, 0 },
381 { C::execution_envvar_pi_row_idx, AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_BLOCK_NUMBER_ROW_IDX },
382 { C::execution_is_address, 0 },
383 { C::execution_is_sender, 0 },
384 { C::execution_is_transactionfee, 0 },
385 { C::execution_is_isstaticcall, 0 },
386 { C::execution_is_l2gasleft, 0 },
387 { C::execution_is_dagasleft, 0 },
388 // output, looked up from PIs
389 { C::execution_register_0_, test_public_inputs.globalVariables.blockNumber },
390 // value from pi should match
391 { C::execution_value_from_pi, test_public_inputs.globalVariables.blockNumber },
392 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::U32) } },
393 // timestamp
394 { { C::execution_sel, 1 },
395 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::TIMESTAMP) },
396 { C::execution_sel_should_execute_opcode, 1 },
397 // Do it! No prior error
398 { C::execution_sel_execute_get_env_var, 1 },
399 // from precomputed table
400 { C::execution_sel_opcode_error, 0 }, // valid enum
401 { C::execution_sel_envvar_pi_lookup_col0, 1 },
402 { C::execution_sel_envvar_pi_lookup_col1, 0 },
403 { C::execution_envvar_pi_row_idx, AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_TIMESTAMP_ROW_IDX },
404 { C::execution_is_address, 0 },
405 { C::execution_is_sender, 0 },
406 { C::execution_is_transactionfee, 0 },
407 { C::execution_is_isstaticcall, 0 },
408 { C::execution_is_l2gasleft, 0 },
409 { C::execution_is_dagasleft, 0 },
410 // output, looked up from PIs
411 { C::execution_register_0_, test_public_inputs.globalVariables.timestamp },
412 // value from pi should match
413 { C::execution_value_from_pi, test_public_inputs.globalVariables.timestamp },
414 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::U64) } },
415 // feePerL2Gas
416 { { C::execution_sel, 1 },
417 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::BASEFEEPERL2GAS) },
418 { C::execution_sel_should_execute_opcode, 1 },
419 // Do it! No prior error
420 { C::execution_sel_execute_get_env_var, 1 },
421 // from precomputed table
422 { C::execution_sel_opcode_error, 0 }, // valid enum
423 { C::execution_sel_envvar_pi_lookup_col0, 0 },
424 { C::execution_sel_envvar_pi_lookup_col1, 1 }, // USES PI COL1
425 { C::execution_envvar_pi_row_idx, AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_GAS_FEES_ROW_IDX },
426 { C::execution_is_address, 0 },
427 { C::execution_is_sender, 0 },
428 { C::execution_is_transactionfee, 0 },
429 { C::execution_is_isstaticcall, 0 },
430 { C::execution_is_l2gasleft, 0 },
431 { C::execution_is_dagasleft, 0 },
432 // output, looked up from PIs
433 { C::execution_register_0_, test_public_inputs.globalVariables.gasFees.feePerL2Gas },
434 // value from pi should match
435 { C::execution_value_from_pi, test_public_inputs.globalVariables.gasFees.feePerL2Gas },
436 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::U128) } },
437 // feePerDaGas
438 { { C::execution_sel, 1 },
439 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::BASEFEEPERDAGAS) },
440 { C::execution_sel_should_execute_opcode, 1 },
441 // Do it! No prior error
442 { C::execution_sel_execute_get_env_var, 1 },
443 // from precomputed table
444 { C::execution_sel_opcode_error, 0 }, // valid enum
445 { C::execution_sel_envvar_pi_lookup_col0, 1 },
446 { C::execution_sel_envvar_pi_lookup_col1, 0 },
447 { C::execution_envvar_pi_row_idx, AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_GAS_FEES_ROW_IDX },
448 { C::execution_is_address, 0 },
449 { C::execution_is_sender, 0 },
450 { C::execution_is_transactionfee, 0 },
451 { C::execution_is_isstaticcall, 0 },
452 { C::execution_is_l2gasleft, 0 },
453 { C::execution_is_dagasleft, 0 },
454 // output, looked up from PIs
455 { C::execution_register_0_, test_public_inputs.globalVariables.gasFees.feePerDaGas },
456 // value from pi should match
457 { C::execution_value_from_pi, test_public_inputs.globalVariables.gasFees.feePerDaGas },
458 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::U128) } },
459 // isStaticCall
460 { { C::execution_sel, 1 },
461 { C::execution_is_static, is_static_call },
462 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::ISSTATICCALL) },
463 { C::execution_sel_should_execute_opcode, 1 },
464 // Do it! No prior error
465 { C::execution_sel_execute_get_env_var, 1 },
466 // from precomputed table
467 { C::execution_sel_opcode_error, 0 }, // valid enum
468 { C::execution_sel_envvar_pi_lookup_col0, 0 },
469 { C::execution_sel_envvar_pi_lookup_col1, 0 },
470 { C::execution_envvar_pi_row_idx, 0 }, // none
471 { C::execution_is_address, 0 },
472 { C::execution_is_sender, 0 },
473 { C::execution_is_transactionfee, 0 },
474 { C::execution_is_isstaticcall, 1 },
475 { C::execution_is_l2gasleft, 0 },
476 { C::execution_is_dagasleft, 0 },
477 // output
478 { C::execution_register_0_, is_static_call },
479 // nothing from pis
480 { C::execution_value_from_pi, 0 },
481 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::U1) } },
482 // l2GasLeft
483 { { C::execution_sel, 1 },
484 { C::execution_l2_gas_limit, l2_gas_limit },
485 { C::execution_l2_gas_used, l2_gas_used },
486 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::L2GASLEFT) },
487 { C::execution_sel_should_execute_opcode, 1 },
488 // Do it! No prior error
489 { C::execution_sel_execute_get_env_var, 1 },
490 // from precomputed table
491 { C::execution_sel_opcode_error, 0 }, // valid enum
492 { C::execution_sel_envvar_pi_lookup_col0, 0 },
493 { C::execution_sel_envvar_pi_lookup_col1, 0 },
494 { C::execution_envvar_pi_row_idx, 0 }, // none
495 { C::execution_is_address, 0 },
496 { C::execution_is_sender, 0 },
497 { C::execution_is_transactionfee, 0 },
498 { C::execution_is_isstaticcall, 0 },
499 { C::execution_is_l2gasleft, 1 },
500 { C::execution_is_dagasleft, 0 },
501 // output
502 { C::execution_register_0_, l2_gas_limit - l2_gas_used },
503 // nothing from pis
504 { C::execution_value_from_pi, 0 },
505 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::U32) } },
506 // daGasLeft
507 { { C::execution_sel, 1 },
508 { C::execution_da_gas_limit, da_gas_limit },
509 { C::execution_da_gas_used, da_gas_used },
510 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::DAGASLEFT) },
511 { C::execution_sel_should_execute_opcode, 1 },
512 // Do it! No prior error
513 { C::execution_sel_execute_get_env_var, 1 },
514 // from precomputed table
515 { C::execution_sel_opcode_error, 0 }, // valid enum
516 { C::execution_sel_envvar_pi_lookup_col0, 0 },
517 { C::execution_sel_envvar_pi_lookup_col1, 0 },
518 { C::execution_envvar_pi_row_idx, 0 }, // none
519 { C::execution_is_address, 0 },
520 { C::execution_is_sender, 0 },
521 { C::execution_is_transactionfee, 0 },
522 { C::execution_is_isstaticcall, 0 },
523 { C::execution_is_l2gasleft, 0 },
524 { C::execution_is_dagasleft, 1 },
525 // output
526 { C::execution_register_0_, da_gas_limit - da_gas_used },
527 // nothing from pis
528 { C::execution_value_from_pi, 0 },
529 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::U32) } },
530 // invalid enum
531 { { C::execution_sel, 1 },
532 { C::execution_rop_1_, 42 },
533 { C::execution_sel_should_execute_opcode, 1 },
534 // Do it! No prior error, although enum will later prove to be invalid.
535 { C::execution_sel_execute_get_env_var, 1 },
536 // from precomputed table
537 { C::execution_sel_opcode_error, 1 }, // invalid enum!
538 { C::execution_sel_envvar_pi_lookup_col0, 0 },
539 { C::execution_sel_envvar_pi_lookup_col1, 0 },
540 { C::execution_envvar_pi_row_idx, 0 }, // none
541 { C::execution_is_address, 0 },
542 { C::execution_is_sender, 0 },
543 { C::execution_is_transactionfee, 0 },
544 { C::execution_is_isstaticcall, 0 },
545 { C::execution_is_l2gasleft, 0 },
546 { C::execution_is_dagasleft, 0 },
547 // output
548 { C::execution_register_0_, 0 }, // no output on error
549 // nothing from pis
550 { C::execution_value_from_pi, 0 },
551 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::FF) } },
552 });
553
554 tracegen::PublicInputsTraceBuilder public_inputs_builder;
555 public_inputs_builder.process_public_inputs(trace, test_public_inputs);
556 public_inputs_builder.process_public_inputs_aux_precomputed(trace);
557
558 tracegen::PrecomputedTraceBuilder precomputed_builder;
560 precomputed_builder.process_get_env_var_table(trace);
561 precomputed_builder.process_sel_range_8(trace);
562
563 check_relation<get_env_var>(trace);
564 check_interaction<ExecutionTraceBuilder, lookup_get_env_var_precomputed_info_settings>(trace);
565 check_interaction<ExecutionTraceBuilder, lookup_get_env_var_read_from_public_inputs_col0_settings>(trace);
566 check_interaction<ExecutionTraceBuilder, lookup_get_env_var_read_from_public_inputs_col1_settings>(trace);
567
568 // corrupt and perform negative tests
569 trace.set(C::execution_rop_1_, 1, 42);
571 (check_interaction<ExecutionTraceBuilder, lookup_get_env_var_precomputed_info_settings>(trace)),
572 "Failed.*GET_ENV_VAR_PRECOMPUTED_INFO. Could not find tuple in destination.");
573 // reset/uncorrupt
574 trace.set(C::execution_rop_1_, 1, static_cast<uint8_t>(EnvironmentVariable::CHAINID));
575}
576
577TEST(GetEnvVarConstrainingTest, NegativeInteractionTests)
578{
579 auto test_public_inputs = PublicInputsBuilder().rand_global_variables().build();
580 TestTraceContainer trace({
581 { { C::execution_sel, 1 },
582 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::CHAINID) },
583 { C::execution_sel_should_execute_opcode, 1 },
584 // from precomputed table
585 { C::execution_sel_opcode_error, 0 }, // valid enum
586 { C::execution_sel_envvar_pi_lookup_col0, 1 },
587 { C::execution_sel_envvar_pi_lookup_col1, 0 },
588 { C::execution_envvar_pi_row_idx, AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_CHAIN_ID_ROW_IDX },
589 { C::execution_is_address, 0 },
590 { C::execution_is_sender, 0 },
591 { C::execution_is_transactionfee, 0 },
592 { C::execution_is_isstaticcall, 0 },
593 { C::execution_is_l2gasleft, 0 },
594 { C::execution_is_dagasleft, 0 },
595 // Do it! No prior error
596 { C::execution_sel_execute_get_env_var, 1 },
597 // output, looked up from PIs
598 { C::execution_register_0_, test_public_inputs.globalVariables.chainId },
599 // value from pi should match
600 { C::execution_value_from_pi, test_public_inputs.globalVariables.chainId },
601 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::FF) } },
602 });
603
604 PublicInputsTraceBuilder public_inputs_builder;
605 public_inputs_builder.process_public_inputs(trace, test_public_inputs);
606 public_inputs_builder.process_public_inputs_aux_precomputed(trace);
607
608 PrecomputedTraceBuilder precomputed_builder;
610 precomputed_builder.process_get_env_var_table(trace);
611 precomputed_builder.process_sel_range_8(trace);
612
613 check_relation<get_env_var>(trace);
614 check_interaction<ExecutionTraceBuilder, lookup_get_env_var_precomputed_info_settings>(trace);
615 check_interaction<ExecutionTraceBuilder, lookup_get_env_var_read_from_public_inputs_col0_settings>(trace);
616 check_interaction<ExecutionTraceBuilder, lookup_get_env_var_read_from_public_inputs_col1_settings>(trace);
617
618 // corrupt and perform negative tests
619 trace.set(C::execution_rop_1_, 0, 42);
621 (check_interaction<ExecutionTraceBuilder, lookup_get_env_var_precomputed_info_settings>(trace)),
622 "Failed.*GET_ENV_VAR_PRECOMPUTED_INFO. Could not find tuple in destination.");
623 // reset/uncorrupt
624 trace.set(C::execution_rop_1_, 0, static_cast<uint8_t>(EnvironmentVariable::CHAINID));
625
626 // corrupt the value so it doesn't match the public input
627 trace.set(C::execution_value_from_pi, 0, test_public_inputs.globalVariables.chainId + 1);
629 (check_interaction<ExecutionTraceBuilder, lookup_get_env_var_read_from_public_inputs_col0_settings>(trace)),
630 "Failed.*GET_ENV_VAR_READ_FROM_PUBLIC_INPUTS_COL0. Could not find tuple in destination.");
631 // reset/uncorrupt
632 trace.set(C::execution_value_from_pi, 0, test_public_inputs.globalVariables.chainId);
633}
634
635TEST(GetEnvVarConstrainingTest, NegativeInteractionTestsPICol1)
636{
637 auto test_public_inputs = PublicInputsBuilder().rand_global_variables().build();
638 TestTraceContainer trace({
639 { { C::execution_sel, 1 },
640 { C::execution_rop_1_, static_cast<uint8_t>(EnvironmentVariable::BASEFEEPERL2GAS) },
641 { C::execution_sel_should_execute_opcode, 1 },
642 // from precomputed table
643 { C::execution_sel_opcode_error, 0 }, // valid enum
644 { C::execution_sel_envvar_pi_lookup_col0, 0 },
645 { C::execution_sel_envvar_pi_lookup_col1, 1 }, // USES PI COL1
646 { C::execution_envvar_pi_row_idx, AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_GAS_FEES_ROW_IDX },
647 { C::execution_is_address, 0 },
648 { C::execution_is_sender, 0 },
649 { C::execution_is_transactionfee, 0 },
650 { C::execution_is_isstaticcall, 0 },
651 { C::execution_is_l2gasleft, 0 },
652 { C::execution_is_dagasleft, 0 },
653 // Do it! No prior error
654 { C::execution_sel_execute_get_env_var, 1 },
655 // output, looked up from PIs
656 { C::execution_register_0_, test_public_inputs.globalVariables.gasFees.feePerL2Gas },
657 // value from pi should match
658 { C::execution_value_from_pi, test_public_inputs.globalVariables.gasFees.feePerL2Gas },
659 { C::execution_mem_tag_reg_0_, static_cast<uint8_t>(ValueTag::U128) } },
660 });
661
662 PublicInputsTraceBuilder public_inputs_builder;
663 public_inputs_builder.process_public_inputs(trace, test_public_inputs);
664 public_inputs_builder.process_public_inputs_aux_precomputed(trace);
665
666 PrecomputedTraceBuilder precomputed_builder;
668 precomputed_builder.process_get_env_var_table(trace);
669 precomputed_builder.process_sel_range_8(trace);
670
671 check_relation<get_env_var>(trace);
672 check_interaction<ExecutionTraceBuilder, lookup_get_env_var_precomputed_info_settings>(trace);
673 check_interaction<ExecutionTraceBuilder, lookup_get_env_var_read_from_public_inputs_col0_settings>(trace);
674 check_interaction<ExecutionTraceBuilder, lookup_get_env_var_read_from_public_inputs_col1_settings>(trace);
675
676 // corrupt the value so it doesn't match the public input
677 trace.set(C::execution_value_from_pi, 0, test_public_inputs.globalVariables.gasFees.feePerL2Gas + 1);
679 (check_interaction<ExecutionTraceBuilder, lookup_get_env_var_read_from_public_inputs_col1_settings>(trace)),
680 "Failed.*GET_ENV_VAR_READ_FROM_PUBLIC_INPUTS_COL1. Could not find tuple in destination.");
681 // reset/uncorrupt
682 trace.set(C::execution_value_from_pi, 0, test_public_inputs.globalVariables.gasFees.feePerL2Gas);
683}
684
685} // namespace
686} // namespace bb::avm2::constraining
#define AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_GAS_FEES_ROW_IDX
#define AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_BLOCK_NUMBER_ROW_IDX
#define AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_VERSION_ROW_IDX
#define AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_TIMESTAMP_ROW_IDX
#define AVM_PUBLIC_INPUTS_GLOBAL_VARIABLES_CHAIN_ID_ROW_IDX
static constexpr size_t SR_TRANSACTION_FEE_FROM_CONTEXT
static constexpr size_t SR_DAGASLEFT_FROM_GAS
static constexpr size_t SR_ISSTATICCALL_FROM_CONTEXT
static constexpr size_t SR_SENDER_FROM_CONTEXT
static constexpr size_t SR_ADDRESS_FROM_CONTEXT
static constexpr size_t SR_L2GASLEFT_FROM_GAS
void set(Column col, uint32_t row, const FF &value)
PrecomputedTraceBuilder precomputed_builder
Definition alu.test.cpp:119
TestTraceContainer trace
#define EXPECT_THROW_WITH_MESSAGE(code, expectedMessage)
Definition macros.hpp:7
AvmFlavorSettings::FF FF
TEST(TxExecutionConstrainingTest, WriteTreeValue)
Definition tx.test.cpp:508
TestTraceContainer empty_trace()
Definition fixtures.cpp:153
typename Flavor::FF FF