Skip to content

Commit

Permalink
Implement more ec hints (#591)
Browse files Browse the repository at this point in the history
* Add new hintcode

* Add hint handler skeletons

* Implement EcRecoverDivModNPacked

* Implement EcRecoverSubAB

* Implement EcRecoverProductMod

* Implement EcRecoverProductDivM

* Fix missing variable

* Some clean up

* Add unit tests

* Add integration test

* Update benchmarks with new test

* Start adding comments

* Add comment
  • Loading branch information
har777 authored Jul 30, 2024
1 parent 30fa0e6 commit be34187
Show file tree
Hide file tree
Showing 6 changed files with 588 additions and 165 deletions.
243 changes: 78 additions & 165 deletions integration_tests/BenchMarks.txt

Large diffs are not rendered by default.

85 changes: 85 additions & 0 deletions integration_tests/cairo_zero_hint_tests/ec_recover.small.cairo
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
// from lambda cairo vm tests

%builtins range_check
from starkware.cairo.common.cairo_secp.bigint import BigInt3, nondet_bigint3

func test_div_mod_n_packed_hint{range_check_ptr: felt}() {

tempvar n = BigInt3(177, 0, 0);
tempvar x = BigInt3(25, 0, 0);
tempvar s = BigInt3(5, 0, 0);

%{
from starkware.cairo.common.cairo_secp.secp_utils import pack
from starkware.python.math_utils import div_mod, safe_div
N = pack(ids.n, PRIME)
x = pack(ids.x, PRIME) % N
s = pack(ids.s, PRIME) % N
value = res = div_mod(x, s, N)
%}

let (res) = nondet_bigint3();
assert res = BigInt3(5,0,0);

return();
}

func test_sub_a_b_hint{range_check_ptr: felt}() {

tempvar a = BigInt3(100, 0, 0);
tempvar b = BigInt3(25, 0, 0);

%{
from starkware.cairo.common.cairo_secp.secp_utils import pack
from starkware.python.math_utils import div_mod, safe_div
a = pack(ids.a, PRIME)
b = pack(ids.b, PRIME)
value = res = a - b
%}

let (res) = nondet_bigint3();
assert res = BigInt3(75,0,0);

return();
}

func test_product_hints{range_check_ptr: felt}() {

tempvar a = BigInt3(60, 0, 0);
tempvar b = BigInt3(2, 0, 0);
tempvar m = BigInt3(100, 0, 0);

%{
from starkware.cairo.common.cairo_secp.secp_utils import pack
from starkware.python.math_utils import div_mod, safe_div
a = pack(ids.a, PRIME)
b = pack(ids.b, PRIME)
product = a * b
m = pack(ids.m, PRIME)
value = res = product % m
%}

let (res) = nondet_bigint3();
assert res = BigInt3(20,0,0);

%{
value = k = product // m
%}

let (k) = nondet_bigint3();
assert k = BigInt3(1,0,0);

return();
}

func main{range_check_ptr: felt}() {
test_div_mod_n_packed_hint();
test_sub_a_b_hint();
test_product_hints();
return();
}
4 changes: 4 additions & 0 deletions pkg/hintrunner/zero/hintcode.go
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,10 @@ const (
recoverYCode string = "from starkware.crypto.signature.signature import ALPHA, BETA, FIELD_PRIME\nfrom starkware.python.math_utils import recover_y\nids.p.x = ids.x\n# This raises an exception if `x` is not on the curve.\nids.p.y = recover_y(ids.x, ALPHA, BETA, FIELD_PRIME)"
randomEcPointCode string = "from starkware.crypto.signature.signature import ALPHA, BETA, FIELD_PRIME\nfrom starkware.python.math_utils import random_ec_point\nfrom starkware.python.utils import to_bytes\n\n# Define a seed for random_ec_point that's dependent on all the input, so that:\n# (1) The added point s is deterministic.\n# (2) It's hard to choose inputs for which the builtin will fail.\nseed = b\"\".join(map(to_bytes, [ids.p.x, ids.p.y, ids.m, ids.q.x, ids.q.y]))\nids.s.x, ids.s.y = random_ec_point(FIELD_PRIME, ALPHA, BETA, seed)"
chainedEcOpCode string = "from starkware.crypto.signature.signature import ALPHA, BETA, FIELD_PRIME\nfrom starkware.python.math_utils import random_ec_point\nfrom starkware.python.utils import to_bytes\n\nn_elms = ids.len\nassert isinstance(n_elms, int) and n_elms >= 0, \\\n f'Invalid value for len. Got: {n_elms}.'\nif '__chained_ec_op_max_len' in globals():\n assert n_elms <= __chained_ec_op_max_len, \\\n f'chained_ec_op() can only be used with len<={__chained_ec_op_max_len}. ' \\\n f'Got: n_elms={n_elms}.'\n\n# Define a seed for random_ec_point that's dependent on all the input, so that:\n# (1) The added point s is deterministic.\n# (2) It's hard to choose inputs for which the builtin will fail.\nseed = b\"\".join(\n map(\n to_bytes,\n [\n ids.p.x,\n ids.p.y,\n *memory.get_range(ids.m, n_elms),\n *memory.get_range(ids.q.address_, 2 * n_elms),\n ],\n )\n)\nids.s.x, ids.s.y = random_ec_point(FIELD_PRIME, ALPHA, BETA, seed)"
ecRecoverDivModNPackedCode string = "from starkware.cairo.common.cairo_secp.secp_utils import pack\nfrom starkware.python.math_utils import div_mod, safe_div\n\nN = pack(ids.n, PRIME)\nx = pack(ids.x, PRIME) % N\ns = pack(ids.s, PRIME) % N\nvalue = res = div_mod(x, s, N)"
ecRecoverSubABCode string = "from starkware.cairo.common.cairo_secp.secp_utils import pack\nfrom starkware.python.math_utils import div_mod, safe_div\n\na = pack(ids.a, PRIME)\nb = pack(ids.b, PRIME)\n\nvalue = res = a - b"
ecRecoverProductModCode string = "from starkware.cairo.common.cairo_secp.secp_utils import pack\nfrom starkware.python.math_utils import div_mod, safe_div\n\na = pack(ids.a, PRIME)\nb = pack(ids.b, PRIME)\nproduct = a * b\nm = pack(ids.m, PRIME)\n\nvalue = res = product % m"
ecRecoverProductDivMCode string = "value = k = product // m"

// ------ Signature hints related code ------
verifyECDSASignatureCode string = "ecdsa_builtin.add_signature(ids.ecdsa_ptr.address_, (ids.signature_r, ids.signature_s))"
Expand Down
8 changes: 8 additions & 0 deletions pkg/hintrunner/zero/zerohint.go
Original file line number Diff line number Diff line change
Expand Up @@ -199,6 +199,14 @@ func GetHintFromCode(program *zero.ZeroProgram, rawHint zero.Hint) (hinter.Hinte
return createRandomEcPointHinter(resolver)
case chainedEcOpCode:
return createChainedEcOpHinter(resolver)
case ecRecoverDivModNPackedCode:
return createEcRecoverDivModNPackedHinter(resolver)
case ecRecoverSubABCode:
return createEcRecoverSubABHinter(resolver)
case ecRecoverProductModCode:
return createEcRecoverProductModHinter(resolver)
case ecRecoverProductDivMCode:
return createEcRecoverProductDivMHinter()
// Blake hints
case blake2sAddUint256BigendCode:
return createBlake2sAddUint256Hinter(resolver, true)
Expand Down
Loading

0 comments on commit be34187

Please sign in to comment.