github.com/linapex/ethereum-go-chinese@v0.0.0-20190316121929-f8b7a73c3fa1/whisper/whisperv5/message_test.go (about) 1 2 //<developer> 3 // <name>linapex 曹一峰</name> 4 // <email>linapex@163.com</email> 5 // <wx>superexc</wx> 6 // <qqgroup>128148617</qqgroup> 7 // <url>https://jsq.ink</url> 8 // <role>pku engineer</role> 9 // <date>2019-03-16 19:16:46</date> 10 //</624450124700979200> 11 12 13 package whisperv5 14 15 import ( 16 "bytes" 17 mrand "math/rand" 18 "testing" 19 20 "github.com/ethereum/go-ethereum/crypto" 21 "github.com/ethereum/go-ethereum/rlp" 22 ) 23 24 func generateMessageParams() (*MessageParams, error) { 25 //设置除P.DST和P.PADDING以外的所有参数 26 27 buf := make([]byte, 4) 28 mrand.Read(buf) 29 sz := mrand.Intn(400) 30 31 var p MessageParams 32 p.PoW = 0.01 33 p.WorkTime = 1 34 p.TTL = uint32(mrand.Intn(1024)) 35 p.Payload = make([]byte, sz) 36 p.KeySym = make([]byte, aesKeyLength) 37 mrand.Read(p.Payload) 38 mrand.Read(p.KeySym) 39 p.Topic = BytesToTopic(buf) 40 41 var err error 42 p.Src, err = crypto.GenerateKey() 43 if err != nil { 44 return nil, err 45 } 46 47 return &p, nil 48 } 49 50 func singleMessageTest(t *testing.T, symmetric bool) { 51 params, err := generateMessageParams() 52 if err != nil { 53 t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err) 54 } 55 56 key, err := crypto.GenerateKey() 57 if err != nil { 58 t.Fatalf("failed GenerateKey with seed %d: %s.", seed, err) 59 } 60 61 if !symmetric { 62 params.KeySym = nil 63 params.Dst = &key.PublicKey 64 } 65 66 text := make([]byte, 0, 512) 67 text = append(text, params.Payload...) 68 69 msg, err := NewSentMessage(params) 70 if err != nil { 71 t.Fatalf("failed to create new message with seed %d: %s.", seed, err) 72 } 73 env, err := msg.Wrap(params) 74 if err != nil { 75 t.Fatalf("failed Wrap with seed %d: %s.", seed, err) 76 } 77 78 var decrypted *ReceivedMessage 79 if symmetric { 80 decrypted, err = env.OpenSymmetric(params.KeySym) 81 } else { 82 decrypted, err = env.OpenAsymmetric(key) 83 } 84 85 if err != nil { 86 t.Fatalf("failed to encrypt with seed %d: %s.", seed, err) 87 } 88 89 if !decrypted.Validate() { 90 t.Fatalf("failed to validate with seed %d.", seed) 91 } 92 93 if !bytes.Equal(text, decrypted.Payload) { 94 t.Fatalf("failed with seed %d: compare payload.", seed) 95 } 96 if !isMessageSigned(decrypted.Raw[0]) { 97 t.Fatalf("failed with seed %d: unsigned.", seed) 98 } 99 if len(decrypted.Signature) != signatureLength { 100 t.Fatalf("failed with seed %d: signature len %d.", seed, len(decrypted.Signature)) 101 } 102 if !IsPubKeyEqual(decrypted.Src, ¶ms.Src.PublicKey) { 103 t.Fatalf("failed with seed %d: signature mismatch.", seed) 104 } 105 } 106 107 func TestMessageEncryption(t *testing.T) { 108 InitSingleTest() 109 110 var symmetric bool 111 for i := 0; i < 256; i++ { 112 singleMessageTest(t, symmetric) 113 symmetric = !symmetric 114 } 115 } 116 117 func TestMessageWrap(t *testing.T) { 118 seed = int64(1777444222) 119 mrand.Seed(seed) 120 target := 128.0 121 122 params, err := generateMessageParams() 123 if err != nil { 124 t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err) 125 } 126 127 msg, err := NewSentMessage(params) 128 if err != nil { 129 t.Fatalf("failed to create new message with seed %d: %s.", seed, err) 130 } 131 params.TTL = 1 132 params.WorkTime = 12 133 params.PoW = target 134 env, err := msg.Wrap(params) 135 if err != nil { 136 t.Fatalf("failed Wrap with seed %d: %s.", seed, err) 137 } 138 139 pow := env.PoW() 140 if pow < target { 141 t.Fatalf("failed Wrap with seed %d: pow < target (%f vs. %f).", seed, pow, target) 142 } 143 144 //设置POW目标太高,预期错误 145 msg2, err := NewSentMessage(params) 146 if err != nil { 147 t.Fatalf("failed to create new message with seed %d: %s.", seed, err) 148 } 149 params.TTL = 1000000 150 params.WorkTime = 1 151 params.PoW = 10000000.0 152 _, err = msg2.Wrap(params) 153 if err == nil { 154 t.Fatalf("unexpectedly reached the PoW target with seed %d.", seed) 155 } 156 } 157 158 func TestMessageSeal(t *testing.T) { 159 //此测试取决于种子的确定性选择(1976726903) 160 seed = int64(1976726903) 161 mrand.Seed(seed) 162 163 params, err := generateMessageParams() 164 if err != nil { 165 t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err) 166 } 167 168 msg, err := NewSentMessage(params) 169 if err != nil { 170 t.Fatalf("failed to create new message with seed %d: %s.", seed, err) 171 } 172 params.TTL = 1 173 aesnonce := make([]byte, 12) 174 mrand.Read(aesnonce) 175 176 env := NewEnvelope(params.TTL, params.Topic, aesnonce, msg) 177 if err != nil { 178 t.Fatalf("failed Wrap with seed %d: %s.", seed, err) 179 } 180 181 env.Expiry = uint32(seed) //使其具有确定性 182 target := 32.0 183 params.WorkTime = 4 184 params.PoW = target 185 env.Seal(params) 186 187 env.calculatePoW(0) 188 pow := env.PoW() 189 if pow < target { 190 t.Fatalf("failed Wrap with seed %d: pow < target (%f vs. %f).", seed, pow, target) 191 } 192 193 params.WorkTime = 1 194 params.PoW = 1000000000.0 195 env.Seal(params) 196 env.calculatePoW(0) 197 pow = env.PoW() 198 if pow < 2*target { 199 t.Fatalf("failed Wrap with seed %d: pow too small %f.", seed, pow) 200 } 201 } 202 203 func TestEnvelopeOpen(t *testing.T) { 204 InitSingleTest() 205 206 var symmetric bool 207 for i := 0; i < 256; i++ { 208 singleEnvelopeOpenTest(t, symmetric) 209 symmetric = !symmetric 210 } 211 } 212 213 func singleEnvelopeOpenTest(t *testing.T, symmetric bool) { 214 params, err := generateMessageParams() 215 if err != nil { 216 t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err) 217 } 218 219 key, err := crypto.GenerateKey() 220 if err != nil { 221 t.Fatalf("failed GenerateKey with seed %d: %s.", seed, err) 222 } 223 224 if !symmetric { 225 params.KeySym = nil 226 params.Dst = &key.PublicKey 227 } 228 229 text := make([]byte, 0, 512) 230 text = append(text, params.Payload...) 231 232 msg, err := NewSentMessage(params) 233 if err != nil { 234 t.Fatalf("failed to create new message with seed %d: %s.", seed, err) 235 } 236 env, err := msg.Wrap(params) 237 if err != nil { 238 t.Fatalf("failed Wrap with seed %d: %s.", seed, err) 239 } 240 241 f := Filter{KeyAsym: key, KeySym: params.KeySym} 242 decrypted := env.Open(&f) 243 if decrypted == nil { 244 t.Fatalf("failed to open with seed %d.", seed) 245 } 246 247 if !bytes.Equal(text, decrypted.Payload) { 248 t.Fatalf("failed with seed %d: compare payload.", seed) 249 } 250 if !isMessageSigned(decrypted.Raw[0]) { 251 t.Fatalf("failed with seed %d: unsigned.", seed) 252 } 253 if len(decrypted.Signature) != signatureLength { 254 t.Fatalf("failed with seed %d: signature len %d.", seed, len(decrypted.Signature)) 255 } 256 if !IsPubKeyEqual(decrypted.Src, ¶ms.Src.PublicKey) { 257 t.Fatalf("failed with seed %d: signature mismatch.", seed) 258 } 259 if decrypted.isAsymmetricEncryption() == symmetric { 260 t.Fatalf("failed with seed %d: asymmetric %v vs. %v.", seed, decrypted.isAsymmetricEncryption(), symmetric) 261 } 262 if decrypted.isSymmetricEncryption() != symmetric { 263 t.Fatalf("failed with seed %d: symmetric %v vs. %v.", seed, decrypted.isSymmetricEncryption(), symmetric) 264 } 265 if !symmetric { 266 if decrypted.Dst == nil { 267 t.Fatalf("failed with seed %d: dst is nil.", seed) 268 } 269 if !IsPubKeyEqual(decrypted.Dst, &key.PublicKey) { 270 t.Fatalf("failed with seed %d: Dst.", seed) 271 } 272 } 273 } 274 275 func TestEncryptWithZeroKey(t *testing.T) { 276 InitSingleTest() 277 278 params, err := generateMessageParams() 279 if err != nil { 280 t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err) 281 } 282 msg, err := NewSentMessage(params) 283 if err != nil { 284 t.Fatalf("failed to create new message with seed %d: %s.", seed, err) 285 } 286 params.KeySym = make([]byte, aesKeyLength) 287 _, err = msg.Wrap(params) 288 if err == nil { 289 t.Fatalf("wrapped with zero key, seed: %d.", seed) 290 } 291 292 params, err = generateMessageParams() 293 if err != nil { 294 t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err) 295 } 296 msg, err = NewSentMessage(params) 297 if err != nil { 298 t.Fatalf("failed to create new message with seed %d: %s.", seed, err) 299 } 300 params.KeySym = make([]byte, 0) 301 _, err = msg.Wrap(params) 302 if err == nil { 303 t.Fatalf("wrapped with empty key, seed: %d.", seed) 304 } 305 306 params, err = generateMessageParams() 307 if err != nil { 308 t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err) 309 } 310 msg, err = NewSentMessage(params) 311 if err != nil { 312 t.Fatalf("failed to create new message with seed %d: %s.", seed, err) 313 } 314 params.KeySym = nil 315 _, err = msg.Wrap(params) 316 if err == nil { 317 t.Fatalf("wrapped with nil key, seed: %d.", seed) 318 } 319 } 320 321 func TestRlpEncode(t *testing.T) { 322 InitSingleTest() 323 324 params, err := generateMessageParams() 325 if err != nil { 326 t.Fatalf("failed generateMessageParams with seed %d: %s.", seed, err) 327 } 328 msg, err := NewSentMessage(params) 329 if err != nil { 330 t.Fatalf("failed to create new message with seed %d: %s.", seed, err) 331 } 332 env, err := msg.Wrap(params) 333 if err != nil { 334 t.Fatalf("wrapped with zero key, seed: %d.", seed) 335 } 336 337 raw, err := rlp.EncodeToBytes(env) 338 if err != nil { 339 t.Fatalf("RLP encode failed: %s.", err) 340 } 341 342 var decoded Envelope 343 rlp.DecodeBytes(raw, &decoded) 344 if err != nil { 345 t.Fatalf("RLP decode failed: %s.", err) 346 } 347 348 he := env.Hash() 349 hd := decoded.Hash() 350 351 if he != hd { 352 t.Fatalf("Hashes are not equal: %x vs. %x", he, hd) 353 } 354 } 355 356 func singlePaddingTest(t *testing.T, padSize int) { 357 params, err := generateMessageParams() 358 if err != nil { 359 t.Fatalf("failed generateMessageParams with seed %d and sz=%d: %s.", seed, padSize, err) 360 } 361 params.Padding = make([]byte, padSize) 362 params.PoW = 0.0000000001 363 pad := make([]byte, padSize) 364 _, err = mrand.Read(pad) 365 if err != nil { 366 t.Fatalf("padding is not generated (seed %d): %s", seed, err) 367 } 368 n := copy(params.Padding, pad) 369 if n != padSize { 370 t.Fatalf("padding is not copied (seed %d): %s", seed, err) 371 } 372 msg, err := NewSentMessage(params) 373 if err != nil { 374 t.Fatalf("failed to create new message with seed %d: %s.", seed, err) 375 } 376 env, err := msg.Wrap(params) 377 if err != nil { 378 t.Fatalf("failed to wrap, seed: %d and sz=%d.", seed, padSize) 379 } 380 f := Filter{KeySym: params.KeySym} 381 decrypted := env.Open(&f) 382 if decrypted == nil { 383 t.Fatalf("failed to open, seed and sz=%d: %d.", seed, padSize) 384 } 385 if !bytes.Equal(pad, decrypted.Padding) { 386 t.Fatalf("padding is not retireved as expected with seed %d and sz=%d:\n[%x]\n[%x].", seed, padSize, pad, decrypted.Padding) 387 } 388 } 389 390 func TestPadding(t *testing.T) { 391 InitSingleTest() 392 393 for i := 1; i < 260; i++ { 394 singlePaddingTest(t, i) 395 } 396 397 lim := 256 * 256 398 for i := lim - 5; i < lim+2; i++ { 399 singlePaddingTest(t, i) 400 } 401 402 for i := 0; i < 256; i++ { 403 n := mrand.Intn(256*254) + 256 404 singlePaddingTest(t, n) 405 } 406 407 for i := 0; i < 256; i++ { 408 n := mrand.Intn(256*1024) + 256*256 409 singlePaddingTest(t, n) 410 } 411 } 412