github.com/consensys/gnark-crypto@v0.14.0/ecc/stark-curve/marshal_test.go (about) 1 // Copyright 2020 ConsenSys Software Inc. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 // FOO 16 17 package starkcurve 18 19 import ( 20 "bytes" 21 "io" 22 "math/big" 23 "math/rand" 24 "testing" 25 26 "github.com/leanovate/gopter" 27 "github.com/leanovate/gopter/prop" 28 29 "github.com/consensys/gnark-crypto/ecc/stark-curve/fp" 30 "github.com/consensys/gnark-crypto/ecc/stark-curve/fr" 31 ) 32 33 func TestEncoder(t *testing.T) { 34 t.Parallel() 35 // TODO need proper fuzz testing here 36 37 var inA uint64 38 var inB fr.Element 39 var inC fp.Element 40 var inD G1Affine 41 var inE G1Affine 42 var inG []G1Affine 43 var inI []fp.Element 44 var inJ []fr.Element 45 46 // set values of inputs 47 inA = rand.Uint64() //#nosec G404 weak rng is fine here 48 inB.SetRandom() 49 inC.SetRandom() 50 inD.ScalarMultiplication(&g1GenAff, new(big.Int).SetUint64(rand.Uint64())) //#nosec G404 weak rng is fine here 51 // inE --> infinity 52 inG = make([]G1Affine, 2) 53 inG[1] = inD 54 inI = make([]fp.Element, 3) 55 inI[2] = inD.X 56 inJ = make([]fr.Element, 0) 57 58 // encode them, compressed and raw 59 var buf, bufRaw bytes.Buffer 60 enc := NewEncoder(&buf) 61 encRaw := NewEncoder(&bufRaw, RawEncoding()) 62 toEncode := []interface{}{inA, &inB, &inC, &inD, &inE, inG, inI, inJ} 63 for _, v := range toEncode { 64 if err := enc.Encode(v); err != nil { 65 t.Fatal(err) 66 } 67 if err := encRaw.Encode(v); err != nil { 68 t.Fatal(err) 69 } 70 } 71 72 testDecode := func(t *testing.T, r io.Reader, n int64) { 73 dec := NewDecoder(r) 74 var outA uint64 75 var outB fr.Element 76 var outC fp.Element 77 var outD G1Affine 78 var outE G1Affine 79 outE.X.SetOne() 80 outE.Y.SetUint64(42) 81 var outG []G1Affine 82 var outI []fp.Element 83 var outJ []fr.Element 84 85 toDecode := []interface{}{&outA, &outB, &outC, &outD, &outE, &outG, &outI, &outJ} 86 for _, v := range toDecode { 87 if err := dec.Decode(v); err != nil { 88 t.Fatal(err) 89 } 90 } 91 92 // compare values 93 if inA != outA { 94 t.Fatal("didn't encode/decode uint64 value properly") 95 } 96 97 if !inB.Equal(&outB) || !inC.Equal(&outC) { 98 t.Fatal("decode(encode(Element) failed") 99 } 100 if !inD.Equal(&outD) || !inE.Equal(&outE) { 101 t.Fatal("decode(encode(G1Affine) failed") 102 } 103 for i := 0; i < len(inG); i++ { 104 if !inG[i].Equal(&outG[i]) { 105 t.Fatal("decode(encode(slice(points))) failed") 106 } 107 } 108 if (len(inI) != len(outI)) || (len(inJ) != len(outJ)) { 109 t.Fatal("decode(encode(slice(elements))) failed") 110 } 111 for i := 0; i < len(inI); i++ { 112 if !inI[i].Equal(&outI[i]) { 113 t.Fatal("decode(encode(slice(elements))) failed") 114 } 115 } 116 if n != dec.BytesRead() { 117 t.Fatal("bytes read don't match bytes written") 118 } 119 } 120 121 // decode them 122 testDecode(t, &buf, enc.BytesWritten()) 123 testDecode(t, &bufRaw, encRaw.BytesWritten()) 124 125 } 126 127 func TestIsCompressed(t *testing.T) { 128 t.Parallel() 129 var g1Inf, g1 G1Affine 130 131 g1 = g1GenAff 132 133 { 134 b := g1Inf.Bytes() 135 if !isCompressed(b[0]) { 136 t.Fatal("g1Inf.Bytes() should be compressed") 137 } 138 } 139 140 { 141 b := g1Inf.RawBytes() 142 if isCompressed(b[0]) { 143 t.Fatal("g1Inf.RawBytes() should be uncompressed") 144 } 145 } 146 147 { 148 b := g1.Bytes() 149 if !isCompressed(b[0]) { 150 t.Fatal("g1.Bytes() should be compressed") 151 } 152 } 153 154 { 155 b := g1.RawBytes() 156 if isCompressed(b[0]) { 157 t.Fatal("g1.RawBytes() should be uncompressed") 158 } 159 } 160 161 } 162 163 func TestG1AffineSerialization(t *testing.T) { 164 t.Parallel() 165 // test round trip serialization of infinity 166 { 167 // compressed 168 { 169 var p1, p2 G1Affine 170 p2.X.SetRandom() 171 p2.Y.SetRandom() 172 buf := p1.Bytes() 173 n, err := p2.SetBytes(buf[:]) 174 if err != nil { 175 t.Fatal(err) 176 } 177 if n != SizeOfG1AffineCompressed { 178 t.Fatal("invalid number of bytes consumed in buffer") 179 } 180 if !(p2.X.IsZero() && p2.Y.IsZero()) { 181 t.Fatal("deserialization of uncompressed infinity point is not infinity") 182 } 183 } 184 185 // uncompressed 186 { 187 var p1, p2 G1Affine 188 p2.X.SetRandom() 189 p2.Y.SetRandom() 190 buf := p1.RawBytes() 191 n, err := p2.SetBytes(buf[:]) 192 if err != nil { 193 t.Fatal(err) 194 } 195 if n != SizeOfG1AffineUncompressed { 196 t.Fatal("invalid number of bytes consumed in buffer") 197 } 198 if !(p2.X.IsZero() && p2.Y.IsZero()) { 199 t.Fatal("deserialization of uncompressed infinity point is not infinity") 200 } 201 } 202 } 203 204 parameters := gopter.DefaultTestParameters() 205 if testing.Short() { 206 parameters.MinSuccessfulTests = nbFuzzShort 207 } else { 208 parameters.MinSuccessfulTests = nbFuzz 209 } 210 211 properties := gopter.NewProperties(parameters) 212 213 properties.Property("[G1] Affine SetBytes(RawBytes) should stay the same", prop.ForAll( 214 func(a fp.Element) bool { 215 var start, end G1Affine 216 var ab big.Int 217 a.BigInt(&ab) 218 start.ScalarMultiplication(&g1GenAff, &ab) 219 220 buf := start.RawBytes() 221 n, err := end.SetBytes(buf[:]) 222 if err != nil { 223 return false 224 } 225 if n != SizeOfG1AffineUncompressed { 226 return false 227 } 228 return start.X.Equal(&end.X) && start.Y.Equal(&end.Y) 229 }, 230 GenFp(), 231 )) 232 233 properties.Property("[G1] Affine SetBytes(Bytes()) should stay the same", prop.ForAll( 234 func(a fp.Element) bool { 235 var start, end G1Affine 236 var ab big.Int 237 a.BigInt(&ab) 238 start.ScalarMultiplication(&g1GenAff, &ab) 239 240 buf := start.Bytes() 241 n, err := end.SetBytes(buf[:]) 242 if err != nil { 243 return false 244 } 245 if n != SizeOfG1AffineCompressed { 246 return false 247 } 248 return start.X.Equal(&end.X) && start.Y.Equal(&end.Y) 249 }, 250 GenFp(), 251 )) 252 253 properties.TestingRun(t, gopter.ConsoleReporter(false)) 254 }