The NIST P256 curve uses a form of \(y^2=x^3+ax+b\) and specifically as \(y^2 = x^3-3x+41058363725152142129326129780047268409114441015993725554835256314039467401291\) and a finite field of \(p = 2^{256} - 2^{224} + 2^{192} + 2^{96} - 1\). The base point (\(G\) is at and the base point is at (48439561293906451759052585252797914202762949526041747995844080717082404635286, 36134250956749795798585127919587881956611106672985015071877198253568414405109):
Barebones P256: Adding and Scalar Multiply on the curveTheoryThe NIST P256 curve uses a form of \(y^2=x^3+ax+b\) and specifically as: \(y^2 = x^3-3x+41058363725152142129326129780047268409114441015993725554835256314039467401291\) and a finite field of: \(p = 2^{256} - 2^{224} + 2^{192} + 2^{96} - 1\) The simplest operations we have is to take a base point (\(G\)) and then perform point addition and where \(2G\) is equal to \(G+G\) and where we get a new point on the elliptic curve. For \(3G\) we can have \(G+2G\), and so on. We can also perform a scalar multiplication, such as taking a scalar of \(3\) and finding \(3G\). In the following code we have three scalar values of 1, 2 and 3, and then use point addition and scalar multiplication to find \(2G\) and \(3G\), and where we should get the same values as \(G+G\) and \(G+2G\), respectively. Note, in NIST P256, we the point on the curve is defined with a \((x,y)\) value. suite := suites.MustFind("P256") one := suite.Scalar().SetInt64(1) two := suite.Scalar().SetInt64(2) three := suite.Scalar().SetInt64(3) G:=suite.Point().Base() G_1 := suite.Point().Mul(one,G) G_2 := suite.Point().Mul(two,G) G_3 := suite.Point().Mul(three,G) G_T1 := suite.Point().Add(G_1,G_1) G_T2 := suite.Point().Add(G_1,G_2) G_T3 := suite.Point().Sub(G_T2,G_2) A sample run shows that \(2G\) is equal to \(G+G\), and \(3G\) is equal to \(G+2G\), and that \(2G-G=G\): Curve: P256 Point G (48439561293906451759052585252797914202762949526041747995844080717082404635286,36134250956749795798585127919587881956611106672985015071877198253568414405109) Point 1G (48439561293906451759052585252797914202762949526041747995844080717082404635286,36134250956749795798585127919587881956611106672985015071877198253568414405109) Point 2G (56515219790691171413109057904011688695424810155802929973526481321309856242040,3377031843712258259223711451491452598088675519751548567112458094635497583569) Point 3G (42877656971275811310262564894490210024759287182177196162425349131675946712428,61154801112014214504178281461992570017247172004704277041681093927569603776562) Point G+G (56515219790691171413109057904011688695424810155802929973526481321309856242040,3377031843712258259223711451491452598088675519751548567112458094635497583569) Point G+2G (42877656971275811310262564894490210024759287182177196162425349131675946712428,61154801112014214504178281461992570017247172004704277041681093927569603776562) Point 2G-G (48439561293906451759052585252797914202762949526041747995844080717082404635286,36134250956749795798585127919587881956611106672985015071877198253568414405109) CodeAn outline of the code is: package main import ( "fmt" "go.dedis.ch/kyber/v3/suites" "os" "strconv" ) func main() { val:=3 argCount := len(os.Args[1:]) if (argCount>0) { val,_= strconv.Atoi(os.Args[1]) } suite := suites.MustFind("p256") one := suite.Scalar().SetInt64(1) two := suite.Scalar().SetInt64(2) three := suite.Scalar().SetInt64(3) value := suite.Scalar().SetInt64(int64(val)) G:=suite.Point().Base() n := suite.Scalar().Pick(suite.RandomStream()) G_1 := suite.Point().Mul(one,G) G_2 := suite.Point().Mul(two,G) G_3 := suite.Point().Mul(three,G) G_val := suite.Point().Mul(value,G) G_n := suite.Point().Mul(n,G) G_T1 := suite.Point().Add(G_1,G_1) G_T2 := suite.Point().Add(G_1,G_2) G_T3 := suite.Point().Sub(G_T2,G_2) fmt.Printf("Curve: %s\n",suite.String()) fmt.Printf("Point G %s\n",G.String()) fmt.Printf("Point 1G %s\n",G_1.String()) fmt.Printf("Point 2G %s\n",G_2.String()) fmt.Printf("Point 3G %s\n",G_3.String()) fmt.Printf("\nPoint G+G %s\n",G_T1.String()) fmt.Printf("Point G+2G %s\n",G_T2.String()) fmt.Printf("Point 2G-G %s\n",G_T3.String()) fmt.Printf("\nValue %s\n",value.String()) fmt.Printf("Point vG %s\n",G_val.String()) fmt.Printf("\nRandom scale (n) %s\n",n.String()) fmt.Printf("Point nG %s\n",G_n.String()) } A sample run gives for a user entered value of 5 is: Curve: P256 Point G (48439561293906451759052585252797914202762949526041747995844080717082404635286,36134250956749795798585127919587881956611106672985015071877198253568414405109) Point 1G (48439561293906451759052585252797914202762949526041747995844080717082404635286,36134250956749795798585127919587881956611106672985015071877198253568414405109) Point 2G (56515219790691171413109057904011688695424810155802929973526481321309856242040,3377031843712258259223711451491452598088675519751548567112458094635497583569) Point 3G (42877656971275811310262564894490210024759287182177196162425349131675946712428,61154801112014214504178281461992570017247172004704277041681093927569603776562) Point G+G (56515219790691171413109057904011688695424810155802929973526481321309856242040,3377031843712258259223711451491452598088675519751548567112458094635497583569) Point G+2G (42877656971275811310262564894490210024759287182177196162425349131675946712428,61154801112014214504178281461992570017247172004704277041681093927569603776562) Value 05 Point vG (36794669340896883012101473439538929759152396476648692591795318194054580155373,101659946828913883886577915207667153874746613498030835602133042203824767462820) Random scale (n) 310f986f0f00a77455666c5eae9562a05302af5117ba52e491d5304f59e9014f Point nG (78494224767026010845293406669882772940749287347599241954953609326585048933324,91347054593758823544042866206920974212996319719285507232050206961209393062005) |