From 4bb6e3b4d999e5f642595e2dc75c04f70862cc4b Mon Sep 17 00:00:00 2001 From: Harikrishnan Shaji Date: Tue, 2 Jul 2024 16:14:48 +0530 Subject: [PATCH 1/6] Implement RandomEcPoint --- .../cairo_zero_hint_tests/random_ec.cairo | 32 +++ pkg/hintrunner/utils/ec_utils.go | 55 ++++++ pkg/hintrunner/zero/hintcode.go | 1 + pkg/hintrunner/zero/zerohint.go | 2 + pkg/hintrunner/zero/zerohint_ec.go | 185 +++++++++++++++--- pkg/vm/memory/memory_value.go | 18 ++ 6 files changed, 264 insertions(+), 29 deletions(-) create mode 100644 integration_tests/cairo_zero_hint_tests/random_ec.cairo create mode 100644 pkg/hintrunner/utils/ec_utils.go diff --git a/integration_tests/cairo_zero_hint_tests/random_ec.cairo b/integration_tests/cairo_zero_hint_tests/random_ec.cairo new file mode 100644 index 000000000..a01966d7b --- /dev/null +++ b/integration_tests/cairo_zero_hint_tests/random_ec.cairo @@ -0,0 +1,32 @@ +from starkware.cairo.common.ec_point import EcPoint + +func test_random_ec_point(p: EcPoint, m: felt, q: EcPoint) -> (r: EcPoint) { + alloc_locals; + local s: EcPoint; + %{ + from starkware.crypto.signature.signature import ALPHA, BETA, FIELD_PRIME + from starkware.python.math_utils import random_ec_point + from starkware.python.utils import to_bytes + + # Define a seed for random_ec_point that's dependent on all the input, so that: + # (1) The added point s is deterministic. + # (2) It's hard to choose inputs for which the builtin will fail. + seed = b"".join(map(to_bytes, [ids.p.x, ids.p.y, ids.m, ids.q.x, ids.q.y])) + ids.s.x, ids.s.y = random_ec_point(FIELD_PRIME, ALPHA, BETA, seed) + %} + return (r=s); +} + +func main() { + let p = EcPoint( + x=0x6a4beaef5a93425b973179cdba0c9d42f30e01a5f1e2db73da0884b8d6756fc, + y=0x72565ec81bc09ff53fbfad99324a92aa5b39fb58267e395e8abe36290ebf24f, + ); + let m = 34; + let q = EcPoint( + x=0x654fd7e67a123dd13868093b3b7777f1ffef596c2e324f25ceaf9146698482c, + y=0x4fad269cbf860980e38768fe9cb6b0b9ab03ee3fe84cfde2eccce597c874fd8, + ); + test_random_ec_point(p, m, q); + return (); +} diff --git a/pkg/hintrunner/utils/ec_utils.go b/pkg/hintrunner/utils/ec_utils.go new file mode 100644 index 000000000..3b939c4aa --- /dev/null +++ b/pkg/hintrunner/utils/ec_utils.go @@ -0,0 +1,55 @@ +package utils + +import ( + "errors" + "math/big" +) + +func GetCairoPrime() (big.Int, bool) { + // 2**251 + 17 * 2**192 + 1 + cairoPrime, ok := new(big.Int).SetString("3618502788666131213697322783095070105623107215331596699973092056135872020481", 10) + return *cairoPrime, ok +} + +func getFeltMaxHalved() (big.Int, bool) { + feltMaxHalved, ok := new(big.Int).SetString("1809251394333065606848661391547535052811553607665798349986546028067936010240", 10) + return *feltMaxHalved, ok +} + +func isQuadResidue(n, fieldPrime *big.Int) bool { + if n.Cmp(big.NewInt(0)) == 0 || n.Cmp(big.NewInt(1)) == 0 { + return true + } + feltMaxHalved, _ := getFeltMaxHalved() + modPowResult := new(big.Int).Exp(n, &feltMaxHalved, fieldPrime) + return modPowResult.Cmp(big.NewInt(1)) == 0 +} + +func ySquaredFromX(x, alpha, beta, fieldPrime *big.Int) *big.Int { + // y^2 = (x^3 + alpha * x + beta) % fieldPrime + ySquared := new(big.Int).Exp(x, big.NewInt(3), fieldPrime) + ySquared.Add(ySquared, new(big.Int).Mul(alpha, x)) + ySquared.Add(ySquared, beta) + ySquared.Mod(ySquared, fieldPrime) + return ySquared +} + +func RecoverY(x, alpha, beta, fieldPrime *big.Int) (*big.Int, error) { + ySquared := ySquaredFromX(x, alpha, beta, fieldPrime) + if isQuadResidue(ySquared, fieldPrime) { + return sqrtMod(ySquared, fieldPrime), nil + } + return nil, errors.New("not on curve") +} + +func sqrtMod(n, p *big.Int) *big.Int { + root1 := new(big.Int).ModSqrt(n, p) + if root1 == nil { + return nil + } + root2 := new(big.Int).Sub(p, root1) + if root1.Cmp(root2) < 0 { + return root1 + } + return root2 +} diff --git a/pkg/hintrunner/zero/hintcode.go b/pkg/hintrunner/zero/hintcode.go index 3df68b47d..fb95b5948 100644 --- a/pkg/hintrunner/zero/hintcode.go +++ b/pkg/hintrunner/zero/hintcode.go @@ -97,6 +97,7 @@ ids.multiplicities = segments.gen_arg([len(positions_dict[k]) for k in output])` isZeroNondetCode string = "x == 0" isZeroPackCode string = "from starkware.cairo.common.cairo_secp.secp_utils import SECP_P, pack\n\nx = pack(ids.x, PRIME) % SECP_P" isZeroDivModCode string = "from starkware.cairo.common.cairo_secp.secp_utils import SECP_P\nfrom starkware.python.math_utils import div_mod\n\nvalue = x_inv = div_mod(1, x, SECP_P)" + 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)" // ------ Signature hints related code ------ verifyECDSASignatureCode string = "ecdsa_builtin.add_signature(ids.ecdsa_ptr.address_, (ids.signature_r, ids.signature_s))" diff --git a/pkg/hintrunner/zero/zerohint.go b/pkg/hintrunner/zero/zerohint.go index 34b84e8bb..d01ed007c 100644 --- a/pkg/hintrunner/zero/zerohint.go +++ b/pkg/hintrunner/zero/zerohint.go @@ -149,6 +149,8 @@ func GetHintFromCode(program *zero.ZeroProgram, rawHint zero.Hint, hintPC uint64 return createIsZeroPackHinter(resolver) case isZeroDivModCode: return createIsZeroDivModHinter() + case randomEcPointCode: + return createRandomEcPointHinter(resolver) // Blake hints case blake2sAddUint256BigendCode: return createBlake2sAddUint256Hinter(resolver, true) diff --git a/pkg/hintrunner/zero/zerohint_ec.go b/pkg/hintrunner/zero/zerohint_ec.go index 6d67362f9..287892803 100644 --- a/pkg/hintrunner/zero/zerohint_ec.go +++ b/pkg/hintrunner/zero/zerohint_ec.go @@ -1,11 +1,14 @@ package zero import ( + "crypto/sha256" + "encoding/binary" + "encoding/hex" "fmt" "math/big" "github.com/NethermindEth/cairo-vm-go/pkg/hintrunner/hinter" - secp_utils "github.com/NethermindEth/cairo-vm-go/pkg/hintrunner/utils" + hintrunner_utils "github.com/NethermindEth/cairo-vm-go/pkg/hintrunner/utils" "github.com/NethermindEth/cairo-vm-go/pkg/utils" VM "github.com/NethermindEth/cairo-vm-go/pkg/vm" mem "github.com/NethermindEth/cairo-vm-go/pkg/vm/memory" @@ -28,7 +31,7 @@ func newEcNegateHint(point hinter.ResOperander) hinter.Hinter { //> # The modulo operation in python always returns a nonnegative number. //> value = (-y) % SECP_P - secPBig, ok := secp_utils.GetSecPBig() + secPBig, ok := hintrunner_utils.GetSecPBig() if !ok { return fmt.Errorf("GetSecPBig failed") } @@ -49,7 +52,7 @@ func newEcNegateHint(point hinter.ResOperander) hinter.Hinter { } //> y = pack(ids.point.y, PRIME) % SECP_P - yBig, err := secp_utils.SecPPacked(pointYValues) + yBig, err := hintrunner_utils.SecPPacked(pointYValues) if err != nil { return err } @@ -97,7 +100,7 @@ func newNondetBigint3V1Hint(res hinter.ResOperander) hinter.Hinter { } //> split(value) - values, err := secp_utils.SecPSplit(valueBig) + values, err := hintrunner_utils.SecPSplit(valueBig) if err != nil { return err } @@ -194,32 +197,32 @@ func newFastEcAddAssignNewXHint(slope, point0, point1 hinter.ResOperander) hinte } //> slope = pack(ids.slope, PRIME) - slopeBig, err := secp_utils.SecPPacked(slopeValues) + slopeBig, err := hintrunner_utils.SecPPacked(slopeValues) if err != nil { return err } //> x0 = pack(ids.point0.x, PRIME) - x0Big, err := secp_utils.SecPPacked(point0XValues) + x0Big, err := hintrunner_utils.SecPPacked(point0XValues) if err != nil { return err } //> x1 = pack(ids.point1.x, PRIME) - x1Big, err := secp_utils.SecPPacked(point1XValues) + x1Big, err := hintrunner_utils.SecPPacked(point1XValues) if err != nil { return err } //> y0 = pack(ids.point0.y, PRIME) - y0Big, err := secp_utils.SecPPacked(point0YValues) + y0Big, err := hintrunner_utils.SecPPacked(point0YValues) if err != nil { return err } //> value = new_x = (pow(slope, 2, SECP_P) - x0 - x1) % SECP_P - secPBig, ok := secp_utils.GetSecPBig() + secPBig, ok := hintrunner_utils.GetSecPBig() if !ok { return fmt.Errorf("GetSecPBig failed") } @@ -342,24 +345,24 @@ func newEcDoubleSlopeV1Hint(point hinter.ResOperander) hinter.Hinter { } //> x = pack(ids.point.x, PRIME) - xBig, err := secp_utils.SecPPacked(pointXValues) + xBig, err := hintrunner_utils.SecPPacked(pointXValues) if err != nil { return err } //> y = pack(ids.point.y, PRIME) - yBig, err := secp_utils.SecPPacked(pointYValues) + yBig, err := hintrunner_utils.SecPPacked(pointYValues) if err != nil { return err } - secPBig, ok := secp_utils.GetSecPBig() + secPBig, ok := hintrunner_utils.GetSecPBig() if !ok { return fmt.Errorf("GetSecPBig failed") } //> value = slope = ec_double_slope(point=(x, y), alpha=0, p=SECP_P) - valueBig, err := secp_utils.EcDoubleSlope(&xBig, &yBig, big.NewInt(0), &secPBig) + valueBig, err := hintrunner_utils.EcDoubleSlope(&xBig, &yBig, big.NewInt(0), &secPBig) if err != nil { return err } @@ -391,7 +394,7 @@ func newReduceV1Hint(x hinter.ResOperander) hinter.Hinter { //> from starkware.cairo.common.cairo_secp.secp_utils import SECP_P, pack //> value = pack(ids.x, PRIME) % SECP_P - secPBig, ok := secp_utils.GetSecPBig() + secPBig, ok := hintrunner_utils.GetSecPBig() if !ok { return fmt.Errorf("GetSecPBig failed") } @@ -406,7 +409,7 @@ func newReduceV1Hint(x hinter.ResOperander) hinter.Hinter { return err } - xBig, err := secp_utils.SecPPacked(xValues) + xBig, err := hintrunner_utils.SecPPacked(xValues) if err != nil { return err } @@ -480,25 +483,25 @@ func newEcDoubleAssignNewXV1Hint(slope, point hinter.ResOperander) hinter.Hinter } //> slope = pack(ids.slope, PRIME) - slopeBig, err := secp_utils.SecPPacked(slopeValues) + slopeBig, err := hintrunner_utils.SecPPacked(slopeValues) if err != nil { return err } //> x = pack(ids.point.x, PRIME) - xBig, err := secp_utils.SecPPacked(pointXValues) + xBig, err := hintrunner_utils.SecPPacked(pointXValues) if err != nil { return err } //> y = pack(ids.point.y, PRIME) - yBig, err := secp_utils.SecPPacked(pointYValues) + yBig, err := hintrunner_utils.SecPPacked(pointYValues) if err != nil { return err } //> value = new_x = (pow(slope, 2, SECP_P) - 2 * x) % SECP_P - secPBig, ok := secp_utils.GetSecPBig() + secPBig, ok := hintrunner_utils.GetSecPBig() if !ok { return fmt.Errorf("GetSecPBig failed") } @@ -642,36 +645,36 @@ func newComputeSlopeV1Hint(point0, point1 hinter.ResOperander) hinter.Hinter { } //> x0 = pack(ids.point0.x, PRIME) - x0Big, err := secp_utils.SecPPacked(point0XValues) + x0Big, err := hintrunner_utils.SecPPacked(point0XValues) if err != nil { return err } //> x1 = pack(ids.point1.x, PRIME) - x1Big, err := secp_utils.SecPPacked(point1XValues) + x1Big, err := hintrunner_utils.SecPPacked(point1XValues) if err != nil { return err } //> y0 = pack(ids.point0.y, PRIME) - y0Big, err := secp_utils.SecPPacked(point0YValues) + y0Big, err := hintrunner_utils.SecPPacked(point0YValues) if err != nil { return err } //> y1 = pack(ids.point0.y, PRIME) - y1Big, err := secp_utils.SecPPacked(point1YValues) + y1Big, err := hintrunner_utils.SecPPacked(point1YValues) if err != nil { return err } - secPBig, ok := secp_utils.GetSecPBig() + secPBig, ok := hintrunner_utils.GetSecPBig() if !ok { return fmt.Errorf("GetSecPBig failed") } // value = slope = line_slope(point1=(x0, y0), point2=(x1, y1), p=SECP_P) - slopeBig, err := secp_utils.LineSlope(&x0Big, &y0Big, &x1Big, &y1Big, &secPBig) + slopeBig, err := hintrunner_utils.LineSlope(&x0Big, &y0Big, &x1Big, &y1Big, &secPBig) if err != nil { return err } @@ -787,12 +790,12 @@ func newIsZeroPackHint(x hinter.ResOperander) hinter.Hinter { return err } - secPBig, ok := secp_utils.GetSecPBig() + secPBig, ok := hintrunner_utils.GetSecPBig() if !ok { return fmt.Errorf("GetSecPBig failed") } - xPackedBig, err := secp_utils.SecPPacked(xValues) + xPackedBig, err := hintrunner_utils.SecPPacked(xValues) if err != nil { return err } @@ -831,7 +834,7 @@ func newIsZeroDivModHint() hinter.Hinter { //> from starkware.python.math_utils import div_mod //> value = x_inv = div_mod(1, x, SECP_P) - secPBig, ok := secp_utils.GetSecPBig() + secPBig, ok := hintrunner_utils.GetSecPBig() if !ok { return fmt.Errorf("GetSecPBig failed") } @@ -841,7 +844,7 @@ func newIsZeroDivModHint() hinter.Hinter { return err } - resBig, err := secp_utils.Divmod(big.NewInt(1), x, &secPBig) + resBig, err := hintrunner_utils.Divmod(big.NewInt(1), x, &secPBig) if err != nil { return err } @@ -854,3 +857,127 @@ func newIsZeroDivModHint() hinter.Hinter { func createIsZeroDivModHinter() (hinter.Hinter, error) { return newIsZeroDivModHint(), nil } + +func newRandomEcPointHint(p, m, q, s hinter.ResOperander) hinter.Hinter { + return &GenericZeroHinter{ + Name: "RandomEcPoint", + Op: func(vm *VM.VirtualMachine, ctx *hinter.HintRunnerContext) error { + //> from starkware.crypto.signature.signature import ALPHA, BETA, FIELD_PRIME + //> from starkware.python.math_utils import random_ec_point + //> from starkware.python.utils import to_bytes + //> + //> # Define a seed for random_ec_point that's dependent on all the input, so that: + //> # (1) The added point s is deterministic. + //> # (2) It's hard to choose inputs for which the builtin will fail. + //> seed = b"".join(map(to_bytes, [ids.p.x, ids.p.y, ids.m, ids.q.x, ids.q.y])) + //> ids.s.x, ids.s.y = random_ec_point(FIELD_PRIME, ALPHA, BETA, seed) + + pAddr, err := p.GetAddress(vm) + if err != nil { + return err + } + pValues, err := vm.Memory.ResolveAsEcPoint(pAddr) + if err != nil { + return err + } + mFelt, err := hinter.ResolveAsFelt(vm, m) + if err != nil { + return err + } + qAddr, err := q.GetAddress(vm) + if err != nil { + return err + } + qValues, err := vm.Memory.ResolveAsEcPoint(qAddr) + if err != nil { + return err + } + + var bytesArray []byte + writeFeltToBytesArray := func(n *fp.Element) { + for _, byteValue := range n.Bytes() { + bytesArray = append(bytesArray, byteValue) + } + } + for _, felt := range pValues { + writeFeltToBytesArray(felt) + } + writeFeltToBytesArray(mFelt) + for _, felt := range qValues { + writeFeltToBytesArray(felt) + } + seed := sha256.Sum256(bytesArray) + + alphaBig := new(big.Int) + utils.Alpha.BigInt(alphaBig) + betaBig := new(big.Int) + utils.Beta.BigInt(betaBig) + fieldPrime, ok := hintrunner_utils.GetCairoPrime() + + for i := uint64(0); i < 100; i++ { + iBytes := make([]byte, 10) + binary.LittleEndian.PutUint64(iBytes, i) + concatenated := append(seed[1:], iBytes...) + hash := sha256.Sum256(concatenated) + hashHex := hex.EncodeToString(hash[:]) + x := new(big.Int) + x.SetString(hashHex, 16) + + yCoef := big.NewInt(1) + if seed[0]&1 == 1 { + yCoef.Neg(yCoef) + } + + // Try to recover y + if !ok { + return fmt.Errorf("failed to get field prime value") + } + if y, err := hintrunner_utils.RecoverY(x, alphaBig, betaBig, &fieldPrime); err == nil { + y.Mul(yCoef, y) + y.Mod(y, &fieldPrime) + + sAddr, err := s.GetAddress(vm) + if err != nil { + return err + } + + sXFelt := new(fp.Element).SetBigInt(x) + sYFelt := new(fp.Element).SetBigInt(y) + fmt.Println(sXFelt.String()) + fmt.Println(sYFelt.String()) + sXMv := mem.MemoryValueFromFieldElement(sXFelt) + sYMv := mem.MemoryValueFromFieldElement(sYFelt) + + err = vm.Memory.WriteToNthStructField(sAddr, sXMv, 0) + if err != nil { + return err + } + return vm.Memory.WriteToNthStructField(sAddr, sYMv, 1) + } + } + + return fmt.Errorf("could not find a point on the curve") + }, + } +} + +func createRandomEcPointHinter(resolver hintReferenceResolver) (hinter.Hinter, error) { + p, err := resolver.GetResOperander("p") + if err != nil { + return nil, err + } + m, err := resolver.GetResOperander("m") + if err != nil { + return nil, err + } + q, err := resolver.GetResOperander("q") + if err != nil { + return nil, err + } + s, err := resolver.GetResOperander("s") + if err != nil { + return nil, err + } + + return newRandomEcPointHint(p, m, q, s), nil +} diff --git a/pkg/vm/memory/memory_value.go b/pkg/vm/memory/memory_value.go index 2dbd4a6cb..1ab3f66a8 100644 --- a/pkg/vm/memory/memory_value.go +++ b/pkg/vm/memory/memory_value.go @@ -375,3 +375,21 @@ func (memory *Memory) ResolveAsBigInt3(valAddr MemoryAddress) ([3]*f.Element, er return valValues, nil } + +func (memory *Memory) ResolveAsEcPoint(valAddr MemoryAddress) ([2]*f.Element, error) { + valMemoryValues, err := memory.GetConsecutiveMemoryValues(valAddr, int16(2)) + if err != nil { + return [2]*f.Element{}, err + } + + var valValues [2]*f.Element + for i := 0; i < 2; i++ { + valValue, err := valMemoryValues[i].FieldElement() + if err != nil { + return [2]*f.Element{}, err + } + valValues[i] = valValue + } + + return valValues, nil +} From 4f2133fbc873e137821c3190a0303073eae71dc9 Mon Sep 17 00:00:00 2001 From: Harikrishnan Shaji Date: Tue, 2 Jul 2024 16:44:39 +0530 Subject: [PATCH 2/6] Add unit test --- pkg/hintrunner/zero/zerohint_ec_test.go | 46 +++++++++++++++++++++++++ 1 file changed, 46 insertions(+) diff --git a/pkg/hintrunner/zero/zerohint_ec_test.go b/pkg/hintrunner/zero/zerohint_ec_test.go index 5e5abb76a..671ef2491 100644 --- a/pkg/hintrunner/zero/zerohint_ec_test.go +++ b/pkg/hintrunner/zero/zerohint_ec_test.go @@ -974,6 +974,52 @@ func TestZeroHintEc(t *testing.T) { check: varValueInScopeEquals("value", bigIntString("4", 10)), }, }, + "RandomEcPoint": { + { + operanders: []*hintOperander{ + {Name: "p.x", Kind: apRelative, Value: feltString("3004956058830981475544150447242655232275382685012344776588097793621230049020")}, + {Name: "p.y", Kind: apRelative, Value: feltString("3232266734070744637901977159303149980795588196503166389060831401046564401743")}, + {Name: "m", Kind: apRelative, Value: feltUint64(34)}, + {Name: "q.x", Kind: apRelative, Value: feltString("2864041794633455918387139831609347757720597354645583729611044800117714995244")}, + {Name: "q.y", Kind: apRelative, Value: feltString("2252415379535459416893084165764951913426528160630388985542241241048300343256")}, + {Name: "s.x", Kind: uninitialized}, + }, + makeHinter: func(ctx *hintTestContext) hinter.Hinter { + return newRandomEcPointHint( + ctx.operanders["p.x"], + ctx.operanders["m"], + ctx.operanders["q.x"], + ctx.operanders["s.x"], + ) + }, + check: consecutiveVarValueEquals("s.x", []*fp.Element{ + feltString("96578541406087262240552119423829615463800550101008760434566010168435227837635"), + feltString("3412645436898503501401619513420382337734846074629040678138428701431530606439"), + }), + }, + { + operanders: []*hintOperander{ + {Name: "p.x", Kind: apRelative, Value: feltUint64(12345)}, + {Name: "p.y", Kind: apRelative, Value: feltUint64(6789)}, + {Name: "m", Kind: apRelative, Value: feltUint64(101)}, + {Name: "q.x", Kind: apRelative, Value: feltUint64(98765)}, + {Name: "q.y", Kind: apRelative, Value: feltUint64(4321)}, + {Name: "s.x", Kind: uninitialized}, + }, + makeHinter: func(ctx *hintTestContext) hinter.Hinter { + return newRandomEcPointHint( + ctx.operanders["p.x"], + ctx.operanders["m"], + ctx.operanders["q.x"], + ctx.operanders["s.x"], + ) + }, + check: consecutiveVarValueEquals("s.x", []*fp.Element{ + feltString("39190969885360777615413526676655883809466222002423777590585892821354159079496"), + feltString("533983185449702770508526175744869430974740140562200547506631069957329272485"), + }), + }, + }, }, ) } From 3c3091da04265694a677ee7b8abbb15a5dc61b70 Mon Sep 17 00:00:00 2001 From: Harikrishnan Shaji Date: Fri, 5 Jul 2024 11:35:22 +0530 Subject: [PATCH 3/6] Update test assert --- integration_tests/cairozero_test.go | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/integration_tests/cairozero_test.go b/integration_tests/cairozero_test.go index 04653c83d..5d8a43236 100644 --- a/integration_tests/cairozero_test.go +++ b/integration_tests/cairozero_test.go @@ -444,8 +444,7 @@ func TestEcOp(t *testing.T) { require.NoError(t, err) _, _, _, _, err = runVm(compiledOutput) - // todo(rodro): This test is failing due to the lack of hint processing. It should be address soon - require.Error(t, err) + require.NoError(t, err) clean("./builtin_tests/") } From e9a3feced692fa5cb50f8a161ead9ff0c556021e Mon Sep 17 00:00:00 2001 From: Harikrishnan Shaji Date: Mon, 8 Jul 2024 13:17:20 +0530 Subject: [PATCH 4/6] Add comment --- pkg/hintrunner/zero/zerohint_ec.go | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/pkg/hintrunner/zero/zerohint_ec.go b/pkg/hintrunner/zero/zerohint_ec.go index 711b47f06..583fa1b7a 100644 --- a/pkg/hintrunner/zero/zerohint_ec.go +++ b/pkg/hintrunner/zero/zerohint_ec.go @@ -941,6 +941,15 @@ func createRecoverYHinter(resolver hintReferenceResolver) (hinter.Hinter, error) return newRecoverYHint(x, p), nil } +// RandomEcPoint hint Returns a random non-zero point on the elliptic curve +// y^2 = x^3 + alpha * x + beta (mod field_prime). +// The point is created deterministically from the seed. +// +// `newRandomEcPointHint` takes 4 operanders as arguments +// - `p` is an EC point used for seed generation +// - `m` the multiplication coefficient of Q used for seed generation +// - `q` an EC point used for seed generation +// - `s` is where the generated random EC point is written to func newRandomEcPointHint(p, m, q, s hinter.ResOperander) hinter.Hinter { return &GenericZeroHinter{ Name: "RandomEcPoint", From e53fdd2c85cb6208d9b3aef005a146c0d3b929eb Mon Sep 17 00:00:00 2001 From: Harikrishnan Shaji Date: Thu, 11 Jul 2024 21:33:39 +0530 Subject: [PATCH 5/6] Some test changes --- .../cairo_zero_hint_tests/random_ec.cairo | 32 ------------------- integration_tests/cairozero_test.go | 3 -- 2 files changed, 35 deletions(-) delete mode 100644 integration_tests/cairo_zero_hint_tests/random_ec.cairo diff --git a/integration_tests/cairo_zero_hint_tests/random_ec.cairo b/integration_tests/cairo_zero_hint_tests/random_ec.cairo deleted file mode 100644 index a01966d7b..000000000 --- a/integration_tests/cairo_zero_hint_tests/random_ec.cairo +++ /dev/null @@ -1,32 +0,0 @@ -from starkware.cairo.common.ec_point import EcPoint - -func test_random_ec_point(p: EcPoint, m: felt, q: EcPoint) -> (r: EcPoint) { - alloc_locals; - local s: EcPoint; - %{ - from starkware.crypto.signature.signature import ALPHA, BETA, FIELD_PRIME - from starkware.python.math_utils import random_ec_point - from starkware.python.utils import to_bytes - - # Define a seed for random_ec_point that's dependent on all the input, so that: - # (1) The added point s is deterministic. - # (2) It's hard to choose inputs for which the builtin will fail. - seed = b"".join(map(to_bytes, [ids.p.x, ids.p.y, ids.m, ids.q.x, ids.q.y])) - ids.s.x, ids.s.y = random_ec_point(FIELD_PRIME, ALPHA, BETA, seed) - %} - return (r=s); -} - -func main() { - let p = EcPoint( - x=0x6a4beaef5a93425b973179cdba0c9d42f30e01a5f1e2db73da0884b8d6756fc, - y=0x72565ec81bc09ff53fbfad99324a92aa5b39fb58267e395e8abe36290ebf24f, - ); - let m = 34; - let q = EcPoint( - x=0x654fd7e67a123dd13868093b3b7777f1ffef596c2e324f25ceaf9146698482c, - y=0x4fad269cbf860980e38768fe9cb6b0b9ab03ee3fe84cfde2eccce597c874fd8, - ); - test_random_ec_point(p, m, q); - return (); -} diff --git a/integration_tests/cairozero_test.go b/integration_tests/cairozero_test.go index bcfdc4686..c2cea37d7 100644 --- a/integration_tests/cairozero_test.go +++ b/integration_tests/cairozero_test.go @@ -78,9 +78,6 @@ func TestCairoFiles(t *testing.T) { errorExpected := false if name == "range_check.small.cairo" { errorExpected = true - } else if name == "ecop.starknet_with_keccak.cairo" { - // temporary, being fixed in another PR soon - continue } path := filepath.Join(root, name) From 12b4bb90264fb41a389ad06e755631aa69342fdc Mon Sep 17 00:00:00 2001 From: Harikrishnan Shaji Date: Thu, 11 Jul 2024 22:15:37 +0530 Subject: [PATCH 6/6] Update pkg/hintrunner/zero/zerohint_ec.go Co-authored-by: Tristan <122918260+TAdev0@users.noreply.github.com> --- pkg/hintrunner/zero/zerohint_ec.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pkg/hintrunner/zero/zerohint_ec.go b/pkg/hintrunner/zero/zerohint_ec.go index 583fa1b7a..ab1f7b92c 100644 --- a/pkg/hintrunner/zero/zerohint_ec.go +++ b/pkg/hintrunner/zero/zerohint_ec.go @@ -941,7 +941,7 @@ func createRecoverYHinter(resolver hintReferenceResolver) (hinter.Hinter, error) return newRecoverYHint(x, p), nil } -// RandomEcPoint hint Returns a random non-zero point on the elliptic curve +// RandomEcPoint hint returns a random non-zero point on the elliptic curve // y^2 = x^3 + alpha * x + beta (mod field_prime). // The point is created deterministically from the seed. //