Puncte:1

Cum se găsește punctul întreg al unei curbe ec într-un interval dat?

drapel it

Mă uitam la elementele de bază ale ecc și am găsit exemplele de pe Internet fie folosesc curba de domeniu continuă, fie folosesc un număr prim foarte mic p ca 17 într-un domeniu discret pentru a arăta punctele.

Sunt chiar curios că dacă pot găsi un punct cu un foarte mare p in practica. De exemplu, secp256k1 folosește un foarte mare p=2^256â2^32â977 în domeniu (p,a,b,G,n,h).

Mai jos este codul python pe care îl folosesc pentru a deduce posibilul întreg al lui y din rezolvarea ecuației cu intervalul întregului X. Spre surprinderea mea că nu există nicio descoperire chiar și în intervalul de 1 milion!

Deci întrebarea mea este, este mai jos codul, nu? Și în al doilea rând, dacă este corect sau corectat de un expert real, ce interval de valori ar trebui să încerc?

P.S. Ma intreb cum punct generatorul G este selectat, de asemenea. Dar asta ar putea avea nevoie de o înțelegere mai profundă a subiectului.

import matematică

# secp256k1
# y**2 = x**3 + 7 (mod p)
P = 2**256 - 2**32 - 977
A = 0
B = 7

#nist P256
P = 115792089210356248762697446949407573530086143415290314195533631308867097853951
A = -3
B = 41058363725152142129326129780047268409114441015993725554835256314039467401291

def in_curve(x):
    curba = x**3 + A*x + B
    y_float = math.sqrt(curbă)
    dacă abs(math.modf(y_float)[0]) < 0,0001 sau \
          (1 - abs(math.modf(y_float)[0]) < 0,0001):
        # print(y_float)
        # bug: y_int = int(math.modf(y_float)[1])
        y_int = int(round(y_float))
        dacă y_int * y_int == (curbă):
            print(y_int)
            returnează y_int
    return Niciunul
 
pentru x în interval (1, 1000000):
    y = curba_în(x)
    dacă y nu este Niciunul:
        print(x, y)

Actualizare 1

Codul anterior este greșit, deoarece virgulă mobilă sqrt() va cauza o eroare inacceptabilă la convertirea lui înapoi în număr întreg.

Dar, după înlocuire math.sqrt() la math.isqrt(), tot nu face lucrurile rezonabile.

Actualizare 2

Mulțumesc sfaturilor tuturor răspunsurilor în thread. Folosind punctul generator pentru a-mi verifica algoritmul, acum știu clar de ce nu reușeam.

Ideea este, pe lângă utilizarea % pentru toate înmulțirile și adunările, I ar trebui să utilizați și rădăcina pătrată modulară pentru a găsi soluția, în loc de rădăcină pătrată întreagă împreună cu %. Este o utilizare totală greșită a % desigur.

Codul modificat trece testul cu niște vectori de testare.

import modular_sqrt
#  de exemplu. Folosisem codul de la https://eli.thegreenplace.net/2009/03/07/computing-modular-square-roots-in-python
# vă rugăm să cereți permisiunea dacă utilizarea depășește domeniul educațional pentru pasionați și enumerați întotdeauna creditul fiind un om decent ;-)

# nist P256, preluat de pe https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-186-draft.pdf
P = 115792089210356248762697446949407573530086143415290314195533631308867097853951
A = -3
B = 41058363725152142129326129780047268409114441015993725554835256314039467401291
Gx = 48439561293906451759052585252797914202762949526041747995844080717082404635286
Gy = 36134250956749795798585127919587881956611106672985015071877198253568414405109

def get_y_in_curve(x):
    y2 = x**3 + A*x + B
    y_int = modular_sqrt(y2, P)
    dacă y_int și ((y_int * y_int) % P) == (y2 % P):
        returnează y_int
    return Niciunul

afirmă get_y_in_curve(Gx) == Gy
fgrieu avatar
drapel ng
Codul este incorect. Problema principală este că cripto-ul Curbei Eliptice nu funcționează cu $x$ și $y$ într-un set infinit. Utilizează un [câmp finit](https://en.wikipedia.org/wiki/Finite_field). secp256k1 folosește câmpul $\mathbb F_p$, de asemenea [ring of integers modulo](https://en.wikipedia.org/w/index.php?title=Ring_of_integers_modulo_n) $p$. Astfel, codul ar trebui să calculeze `curba` redusă modulo `P` și să calculeze (când există) o rădăcină pătrată modulară a acesteia; consultați [this](https://en.wikipedia.org/wiki/Tonelli%E2%80%93Shanks_algorithm) pentru o metodă. Vă rugăm să îmbunătățiți sau să închideți întrebarea.
Match Man avatar
drapel it
@fgrieu Da, mi-am dat seama de greșeala mea imediat după ce Daniel a subliniat-o. Acum întrebarea este actualizată cu algoritmul corectat. Vrei să închid întrebarea deoarece *a* greșit? Sau păstrați-l ca exemplu despre cum ar trebui făcute lucrurile în spațiul finit al ECC. Sau chiar cum ar putea merge prost lucrurile când trecem de la „curba” spațiului infinit la spațiul finit? :)
fgrieu avatar
drapel ng
Întrebarea actualizată este OK. Deoarece răspunsul a ajutat, cred că cel mai bine este să-l accepți și totul va fi bine. Notă despre noul cod: ar fi mai elegant să redenumim `curve` în `y2`; calculați-o modulo `P` mai devreme (de exemplu, `y2 = (x**3 + A*x + B) % P` sau `y2 = (pow(x, 3, P) + A*x + B) % P )` ; și pentru a-l reutiliza în `y_int = modular_sqrt(y2)` și `if ((y_int * y_int) % P) == y2:`. Nu este imediat clar ce face `modular_sqrt` atunci când eșuează. În mod independent, folosirea `modular_sqrt` al altei persoane este OK în context? Asta e partea implicată!
Match Man avatar
drapel it
Codul este refactorizat. modular_sqrt va returna 0 pentru eșec, iar codul nou a adăugat și această verificare. Nu folosesc codul lui Eli direct, dar fac referire la codul lui ca exemplu.
Puncte:3
drapel ru

Nu sunt foarte sigur la ce vrei să spui $p$ și nu sunt sigur la ce ați vrut să vă imprimați codul.

Cu toate acestea, se pare că încercați să găsiți puncte cu valori întregi pe curba eliptică $y^2=x^3+7$ prin epuizare peste $x$ valori și nu pot identifica o eroare în afară de instrucțiunea print. DAR Siegel a arătat că, în general, curbele eliptice peste numerele raționale au doar un număr finit de puncte cu valori întregi și ne așteptăm ca acestea să fie într-adevăr foarte rare. De fapt pentru curba pe care ați ales-o nu există puncte întregi.

S-ar putea să încercați să găsiți numere întregi $x$ și $y$ astfel încât $y^2\equiv x^3+7\pmod p$ pentru un prim mare $p$. În acest caz, ar trebui să luați rădăcini pătrate mod $p$ mai degrabă decât peste numerele reale. Aceasta foloseste un calcul diferit. Alegerea unui prim mare $p$ și apoi luând oricare $x$ valoare are o șansă de aproximativ 50% să găsească un potrivit $y$ luând o rădăcină pătrată modulară a $x^3+17$.

Match Man avatar
drapel it
Am adăugat sensul lui `p` în cauză. Este atât de mare încât nu trebuie să fac modulare cu niciun număr mic, cum ar fi 1 miliard... > De fapt, pentru curba pe care ați ales-o nu există puncte întregi.
Daniel S avatar
drapel ru
Aha, înțeleg. În acest caz, dacă încercați să generați puncte fără a utiliza nicio aritmetică modulară, nu va funcționa, deoarece atunci ar fi puncte integrale și nu există niciunul pe această curbă. Rețineți că numerele „mici” care nu sunt pătrate perfecte pot avea totuși rădăcini pătrate mod $p$ dacă cineva este pregătit să folosească aritmetica modulară.
Match Man avatar
drapel it
Vrei să spui că ar trebui să schimb if y_int * y_int == (x^3 + 7) la if y_int * y_int == (x^3 + 7) % P, unde P =2^256â2^32â 977? Înțeleg că secp256k1 este definit peste â¤p, așa că calculul anterior cu virgulă mobilă este doar pentru a afla dacă y este suficient de aproape pentru a fi un număr întreg. Există într-adevăr o mulțime de candidați posibili într-un milion, dar niciunul dintre ei nu este cu adevărat unul...
Daniel S avatar
drapel ru
Nu. Adică (folosind faptul că $p\equiv 3\pmod 4$), ar trebui să înlocuiți y_float=math.sqrt(x^3+7) cu y_int=pow(x^3+7,(p+) 1)/4,p) și apoi verificați dacă y_int*y_int==(x^3+7)%p. Acest lucru nu vă va oferi o valoare mică de $y$, dar nu există o soluție cu o valoare mică atât de $x$ cât și de $y$. Consultați linkul despre modul de calcul al rădăcinilor pătrate $p$.
Match Man avatar
drapel it
Am înţeles. Întrebarea este actualizată cu funcționarea corectă acum. Mulțumiri.

Postează un răspuns

Majoritatea oamenilor nu înțeleg că a pune multe întrebări deblochează învățarea și îmbunătățește legătura interpersonală. În studiile lui Alison, de exemplu, deși oamenii își puteau aminti cu exactitate câte întrebări au fost puse în conversațiile lor, ei nu au intuit legătura dintre întrebări și apreciere. În patru studii, în care participanții au fost implicați în conversații ei înșiși sau au citit transcrieri ale conversațiilor altora, oamenii au avut tendința să nu realizeze că întrebarea ar influența – sau ar fi influențat – nivelul de prietenie dintre conversatori.