github.com/theQRL/go-zond@v0.1.1/p2p/discover/v5wire/encoding.go (about) 1 // Copyright 2020 The go-ethereum Authors 2 // This file is part of the go-ethereum library. 3 // 4 // The go-ethereum library is free software: you can redistribute it and/or modify 5 // it under the terms of the GNU Lesser General Public License as published by 6 // the Free Software Foundation, either version 3 of the License, or 7 // (at your option) any later version. 8 // 9 // The go-ethereum library is distributed in the hope that it will be useful, 10 // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 // GNU Lesser General Public License for more details. 13 // 14 // You should have received a copy of the GNU Lesser General Public License 15 // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>. 16 17 package v5wire 18 19 import ( 20 "bytes" 21 "crypto/aes" 22 "crypto/cipher" 23 "crypto/ecdsa" 24 crand "crypto/rand" 25 "crypto/sha256" 26 "encoding/binary" 27 "errors" 28 "fmt" 29 "hash" 30 31 "github.com/theQRL/go-zond/common/mclock" 32 "github.com/theQRL/go-zond/p2p/enode" 33 "github.com/theQRL/go-zond/p2p/enr" 34 "github.com/theQRL/go-zond/rlp" 35 ) 36 37 // TODO concurrent WHOAREYOU tie-breaker 38 // TODO rehandshake after X packets 39 40 // Header represents a packet header. 41 type Header struct { 42 IV [sizeofMaskingIV]byte 43 StaticHeader 44 AuthData []byte 45 46 src enode.ID // used by decoder 47 } 48 49 // StaticHeader contains the static fields of a packet header. 50 type StaticHeader struct { 51 ProtocolID [6]byte 52 Version uint16 53 Flag byte 54 Nonce Nonce 55 AuthSize uint16 56 } 57 58 // Authdata layouts. 59 type ( 60 whoareyouAuthData struct { 61 IDNonce [16]byte // ID proof data 62 RecordSeq uint64 // highest known ENR sequence of requester 63 } 64 65 handshakeAuthData struct { 66 h struct { 67 SrcID enode.ID 68 SigSize byte // signature data 69 PubkeySize byte // offset of 70 } 71 // Trailing variable-size data. 72 signature, pubkey, record []byte 73 } 74 75 messageAuthData struct { 76 SrcID enode.ID 77 } 78 ) 79 80 // Packet header flag values. 81 const ( 82 flagMessage = iota 83 flagWhoareyou 84 flagHandshake 85 ) 86 87 // Protocol constants. 88 const ( 89 version = 1 90 minVersion = 1 91 sizeofMaskingIV = 16 92 93 // The minimum size of any Discovery v5 packet is 63 bytes. 94 // Should reject packets smaller than minPacketSize. 95 minPacketSize = 63 96 97 maxPacketSize = 1280 98 99 minMessageSize = 48 // this refers to data after static headers 100 randomPacketMsgSize = 20 101 ) 102 103 var DefaultProtocolID = [6]byte{'d', 'i', 's', 'c', 'v', '5'} 104 105 // Errors. 106 var ( 107 errTooShort = errors.New("packet too short") 108 errInvalidHeader = errors.New("invalid packet header") 109 errInvalidFlag = errors.New("invalid flag value in header") 110 errMinVersion = errors.New("version of packet header below minimum") 111 errMsgTooShort = errors.New("message/handshake packet below minimum size") 112 errAuthSize = errors.New("declared auth size is beyond packet length") 113 errUnexpectedHandshake = errors.New("unexpected auth response, not in handshake") 114 errInvalidAuthKey = errors.New("invalid ephemeral pubkey") 115 errNoRecord = errors.New("expected ENR in handshake but none sent") 116 errInvalidNonceSig = errors.New("invalid ID nonce signature") 117 errMessageTooShort = errors.New("message contains no data") 118 errMessageDecrypt = errors.New("cannot decrypt message") 119 ) 120 121 // Public errors. 122 var ( 123 // ErrInvalidReqID represents error when the ID is invalid. 124 ErrInvalidReqID = errors.New("request ID larger than 8 bytes") 125 ) 126 127 // IsInvalidHeader reports whether 'err' is related to an invalid packet header. When it 128 // returns false, it is pretty certain that the packet causing the error does not belong 129 // to discv5. 130 func IsInvalidHeader(err error) bool { 131 return err == errTooShort || err == errInvalidHeader || err == errMsgTooShort 132 } 133 134 // Packet sizes. 135 var ( 136 sizeofStaticHeader = binary.Size(StaticHeader{}) 137 sizeofWhoareyouAuthData = binary.Size(whoareyouAuthData{}) 138 sizeofHandshakeAuthData = binary.Size(handshakeAuthData{}.h) 139 sizeofMessageAuthData = binary.Size(messageAuthData{}) 140 sizeofStaticPacketData = sizeofMaskingIV + sizeofStaticHeader 141 ) 142 143 // Codec encodes and decodes Discovery v5 packets. 144 // This type is not safe for concurrent use. 145 type Codec struct { 146 sha256 hash.Hash 147 localnode *enode.LocalNode 148 privkey *ecdsa.PrivateKey 149 sc *SessionCache 150 protocolID [6]byte 151 152 // encoder buffers 153 buf bytes.Buffer // whole packet 154 headbuf bytes.Buffer // packet header 155 msgbuf bytes.Buffer // message RLP plaintext 156 msgctbuf []byte // message data ciphertext 157 158 // decoder buffer 159 decbuf []byte 160 reader bytes.Reader 161 } 162 163 // NewCodec creates a wire codec. 164 func NewCodec(ln *enode.LocalNode, key *ecdsa.PrivateKey, clock mclock.Clock, protocolID *[6]byte) *Codec { 165 c := &Codec{ 166 sha256: sha256.New(), 167 localnode: ln, 168 privkey: key, 169 sc: NewSessionCache(1024, clock), 170 protocolID: DefaultProtocolID, 171 decbuf: make([]byte, maxPacketSize), 172 } 173 if protocolID != nil { 174 c.protocolID = *protocolID 175 } 176 return c 177 } 178 179 // Encode encodes a packet to a node. 'id' and 'addr' specify the destination node. The 180 // 'challenge' parameter should be the most recently received WHOAREYOU packet from that 181 // node. 182 func (c *Codec) Encode(id enode.ID, addr string, packet Packet, challenge *Whoareyou) ([]byte, Nonce, error) { 183 // Create the packet header. 184 var ( 185 head Header 186 session *session 187 msgData []byte 188 err error 189 ) 190 switch { 191 case packet.Kind() == WhoareyouPacket: 192 head, err = c.encodeWhoareyou(id, packet.(*Whoareyou)) 193 case challenge != nil: 194 // We have an unanswered challenge, send handshake. 195 head, session, err = c.encodeHandshakeHeader(id, addr, challenge) 196 default: 197 session = c.sc.session(id, addr) 198 if session != nil { 199 // There is a session, use it. 200 head, err = c.encodeMessageHeader(id, session) 201 } else { 202 // No keys, send random data to kick off the handshake. 203 head, msgData, err = c.encodeRandom(id) 204 } 205 } 206 if err != nil { 207 return nil, Nonce{}, err 208 } 209 210 // Generate masking IV. 211 if err := c.sc.maskingIVGen(head.IV[:]); err != nil { 212 return nil, Nonce{}, fmt.Errorf("can't generate masking IV: %v", err) 213 } 214 215 // Encode header data. 216 c.writeHeaders(&head) 217 218 // Store sent WHOAREYOU challenges. 219 if challenge, ok := packet.(*Whoareyou); ok { 220 challenge.ChallengeData = bytesCopy(&c.buf) 221 c.sc.storeSentHandshake(id, addr, challenge) 222 } else if msgData == nil { 223 headerData := c.buf.Bytes() 224 msgData, err = c.encryptMessage(session, packet, &head, headerData) 225 if err != nil { 226 return nil, Nonce{}, err 227 } 228 } 229 230 enc, err := c.EncodeRaw(id, head, msgData) 231 return enc, head.Nonce, err 232 } 233 234 // EncodeRaw encodes a packet with the given header. 235 func (c *Codec) EncodeRaw(id enode.ID, head Header, msgdata []byte) ([]byte, error) { 236 c.writeHeaders(&head) 237 238 // Apply masking. 239 masked := c.buf.Bytes()[sizeofMaskingIV:] 240 mask := head.mask(id) 241 mask.XORKeyStream(masked[:], masked[:]) 242 243 // Write message data. 244 c.buf.Write(msgdata) 245 return c.buf.Bytes(), nil 246 } 247 248 func (c *Codec) writeHeaders(head *Header) { 249 c.buf.Reset() 250 c.buf.Write(head.IV[:]) 251 binary.Write(&c.buf, binary.BigEndian, &head.StaticHeader) 252 c.buf.Write(head.AuthData) 253 } 254 255 // makeHeader creates a packet header. 256 func (c *Codec) makeHeader(toID enode.ID, flag byte, authsizeExtra int) Header { 257 var authsize int 258 switch flag { 259 case flagMessage: 260 authsize = sizeofMessageAuthData 261 case flagWhoareyou: 262 authsize = sizeofWhoareyouAuthData 263 case flagHandshake: 264 authsize = sizeofHandshakeAuthData 265 default: 266 panic(fmt.Errorf("BUG: invalid packet header flag %x", flag)) 267 } 268 authsize += authsizeExtra 269 if authsize > int(^uint16(0)) { 270 panic(fmt.Errorf("BUG: auth size %d overflows uint16", authsize)) 271 } 272 return Header{ 273 StaticHeader: StaticHeader{ 274 ProtocolID: c.protocolID, 275 Version: version, 276 Flag: flag, 277 AuthSize: uint16(authsize), 278 }, 279 } 280 } 281 282 // encodeRandom encodes a packet with random content. 283 func (c *Codec) encodeRandom(toID enode.ID) (Header, []byte, error) { 284 head := c.makeHeader(toID, flagMessage, 0) 285 286 // Encode auth data. 287 auth := messageAuthData{SrcID: c.localnode.ID()} 288 if _, err := crand.Read(head.Nonce[:]); err != nil { 289 return head, nil, fmt.Errorf("can't get random data: %v", err) 290 } 291 c.headbuf.Reset() 292 binary.Write(&c.headbuf, binary.BigEndian, auth) 293 head.AuthData = c.headbuf.Bytes() 294 295 // Fill message ciphertext buffer with random bytes. 296 c.msgctbuf = append(c.msgctbuf[:0], make([]byte, randomPacketMsgSize)...) 297 crand.Read(c.msgctbuf) 298 return head, c.msgctbuf, nil 299 } 300 301 // encodeWhoareyou encodes a WHOAREYOU packet. 302 func (c *Codec) encodeWhoareyou(toID enode.ID, packet *Whoareyou) (Header, error) { 303 // Sanity check node field to catch misbehaving callers. 304 if packet.RecordSeq > 0 && packet.Node == nil { 305 panic("BUG: missing node in whoareyou with non-zero seq") 306 } 307 308 // Create header. 309 head := c.makeHeader(toID, flagWhoareyou, 0) 310 head.AuthData = bytesCopy(&c.buf) 311 head.Nonce = packet.Nonce 312 313 // Encode auth data. 314 auth := &whoareyouAuthData{ 315 IDNonce: packet.IDNonce, 316 RecordSeq: packet.RecordSeq, 317 } 318 c.headbuf.Reset() 319 binary.Write(&c.headbuf, binary.BigEndian, auth) 320 head.AuthData = c.headbuf.Bytes() 321 return head, nil 322 } 323 324 // encodeHandshakeHeader encodes the handshake message packet header. 325 func (c *Codec) encodeHandshakeHeader(toID enode.ID, addr string, challenge *Whoareyou) (Header, *session, error) { 326 // Ensure calling code sets challenge.node. 327 if challenge.Node == nil { 328 panic("BUG: missing challenge.Node in encode") 329 } 330 331 // Generate new secrets. 332 auth, session, err := c.makeHandshakeAuth(toID, addr, challenge) 333 if err != nil { 334 return Header{}, nil, err 335 } 336 337 // Generate nonce for message. 338 nonce, err := c.sc.nextNonce(session) 339 if err != nil { 340 return Header{}, nil, fmt.Errorf("can't generate nonce: %v", err) 341 } 342 343 // TODO: this should happen when the first authenticated message is received 344 c.sc.storeNewSession(toID, addr, session) 345 346 // Encode the auth header. 347 var ( 348 authsizeExtra = len(auth.pubkey) + len(auth.signature) + len(auth.record) 349 head = c.makeHeader(toID, flagHandshake, authsizeExtra) 350 ) 351 c.headbuf.Reset() 352 binary.Write(&c.headbuf, binary.BigEndian, &auth.h) 353 c.headbuf.Write(auth.signature) 354 c.headbuf.Write(auth.pubkey) 355 c.headbuf.Write(auth.record) 356 head.AuthData = c.headbuf.Bytes() 357 head.Nonce = nonce 358 return head, session, err 359 } 360 361 // makeHandshakeAuth creates the auth header on a request packet following WHOAREYOU. 362 func (c *Codec) makeHandshakeAuth(toID enode.ID, addr string, challenge *Whoareyou) (*handshakeAuthData, *session, error) { 363 auth := new(handshakeAuthData) 364 auth.h.SrcID = c.localnode.ID() 365 366 // Create the ephemeral key. This needs to be first because the 367 // key is part of the ID nonce signature. 368 var remotePubkey = new(ecdsa.PublicKey) 369 if err := challenge.Node.Load((*enode.Secp256k1)(remotePubkey)); err != nil { 370 return nil, nil, fmt.Errorf("can't find secp256k1 key for recipient") 371 } 372 ephkey, err := c.sc.ephemeralKeyGen() 373 if err != nil { 374 return nil, nil, fmt.Errorf("can't generate ephemeral key") 375 } 376 ephpubkey := EncodePubkey(&ephkey.PublicKey) 377 auth.pubkey = ephpubkey[:] 378 auth.h.PubkeySize = byte(len(auth.pubkey)) 379 380 // Add ID nonce signature to response. 381 cdata := challenge.ChallengeData 382 idsig, err := makeIDSignature(c.sha256, c.privkey, cdata, ephpubkey[:], toID) 383 if err != nil { 384 return nil, nil, fmt.Errorf("can't sign: %v", err) 385 } 386 auth.signature = idsig 387 auth.h.SigSize = byte(len(auth.signature)) 388 389 // Add our record to response if it's newer than what remote side has. 390 ln := c.localnode.Node() 391 if challenge.RecordSeq < ln.Seq() { 392 auth.record, _ = rlp.EncodeToBytes(ln.Record()) 393 } 394 395 // Create session keys. 396 sec := deriveKeys(sha256.New, ephkey, remotePubkey, c.localnode.ID(), challenge.Node.ID(), cdata) 397 if sec == nil { 398 return nil, nil, fmt.Errorf("key derivation failed") 399 } 400 return auth, sec, err 401 } 402 403 // encodeMessageHeader encodes an encrypted message packet. 404 func (c *Codec) encodeMessageHeader(toID enode.ID, s *session) (Header, error) { 405 head := c.makeHeader(toID, flagMessage, 0) 406 407 // Create the header. 408 nonce, err := c.sc.nextNonce(s) 409 if err != nil { 410 return Header{}, fmt.Errorf("can't generate nonce: %v", err) 411 } 412 auth := messageAuthData{SrcID: c.localnode.ID()} 413 c.buf.Reset() 414 binary.Write(&c.buf, binary.BigEndian, &auth) 415 head.AuthData = bytesCopy(&c.buf) 416 head.Nonce = nonce 417 return head, err 418 } 419 420 func (c *Codec) encryptMessage(s *session, p Packet, head *Header, headerData []byte) ([]byte, error) { 421 // Encode message plaintext. 422 c.msgbuf.Reset() 423 c.msgbuf.WriteByte(p.Kind()) 424 if err := rlp.Encode(&c.msgbuf, p); err != nil { 425 return nil, err 426 } 427 messagePT := c.msgbuf.Bytes() 428 429 // Encrypt into message ciphertext buffer. 430 messageCT, err := encryptGCM(c.msgctbuf[:0], s.writeKey, head.Nonce[:], messagePT, headerData) 431 if err == nil { 432 c.msgctbuf = messageCT 433 } 434 return messageCT, err 435 } 436 437 // Decode decodes a discovery packet. 438 func (c *Codec) Decode(inputData []byte, addr string) (src enode.ID, n *enode.Node, p Packet, err error) { 439 if len(inputData) < minPacketSize { 440 return enode.ID{}, nil, nil, errTooShort 441 } 442 // Copy the packet to a tmp buffer to avoid modifying it. 443 c.decbuf = append(c.decbuf[:0], inputData...) 444 input := c.decbuf 445 // Unmask the static header. 446 var head Header 447 copy(head.IV[:], input[:sizeofMaskingIV]) 448 mask := head.mask(c.localnode.ID()) 449 staticHeader := input[sizeofMaskingIV:sizeofStaticPacketData] 450 mask.XORKeyStream(staticHeader, staticHeader) 451 452 // Decode and verify the static header. 453 c.reader.Reset(staticHeader) 454 binary.Read(&c.reader, binary.BigEndian, &head.StaticHeader) 455 remainingInput := len(input) - sizeofStaticPacketData 456 if err := head.checkValid(remainingInput, c.protocolID); err != nil { 457 return enode.ID{}, nil, nil, err 458 } 459 460 // Unmask auth data. 461 authDataEnd := sizeofStaticPacketData + int(head.AuthSize) 462 authData := input[sizeofStaticPacketData:authDataEnd] 463 mask.XORKeyStream(authData, authData) 464 head.AuthData = authData 465 466 // Delete timed-out handshakes. This must happen before decoding to avoid 467 // processing the same handshake twice. 468 c.sc.handshakeGC() 469 470 // Decode auth part and message. 471 headerData := input[:authDataEnd] 472 msgData := input[authDataEnd:] 473 switch head.Flag { 474 case flagWhoareyou: 475 p, err = c.decodeWhoareyou(&head, headerData) 476 case flagHandshake: 477 n, p, err = c.decodeHandshakeMessage(addr, &head, headerData, msgData) 478 case flagMessage: 479 p, err = c.decodeMessage(addr, &head, headerData, msgData) 480 default: 481 err = errInvalidFlag 482 } 483 return head.src, n, p, err 484 } 485 486 // decodeWhoareyou reads packet data after the header as a WHOAREYOU packet. 487 func (c *Codec) decodeWhoareyou(head *Header, headerData []byte) (Packet, error) { 488 if len(head.AuthData) != sizeofWhoareyouAuthData { 489 return nil, fmt.Errorf("invalid auth size %d for WHOAREYOU", len(head.AuthData)) 490 } 491 var auth whoareyouAuthData 492 c.reader.Reset(head.AuthData) 493 binary.Read(&c.reader, binary.BigEndian, &auth) 494 p := &Whoareyou{ 495 Nonce: head.Nonce, 496 IDNonce: auth.IDNonce, 497 RecordSeq: auth.RecordSeq, 498 ChallengeData: make([]byte, len(headerData)), 499 } 500 copy(p.ChallengeData, headerData) 501 return p, nil 502 } 503 504 func (c *Codec) decodeHandshakeMessage(fromAddr string, head *Header, headerData, msgData []byte) (n *enode.Node, p Packet, err error) { 505 node, auth, session, err := c.decodeHandshake(fromAddr, head) 506 if err != nil { 507 c.sc.deleteHandshake(auth.h.SrcID, fromAddr) 508 return nil, nil, err 509 } 510 511 // Decrypt the message using the new session keys. 512 msg, err := c.decryptMessage(msgData, head.Nonce[:], headerData, session.readKey) 513 if err != nil { 514 c.sc.deleteHandshake(auth.h.SrcID, fromAddr) 515 return node, msg, err 516 } 517 518 // Handshake OK, drop the challenge and store the new session keys. 519 c.sc.storeNewSession(auth.h.SrcID, fromAddr, session) 520 c.sc.deleteHandshake(auth.h.SrcID, fromAddr) 521 return node, msg, nil 522 } 523 524 func (c *Codec) decodeHandshake(fromAddr string, head *Header) (n *enode.Node, auth handshakeAuthData, s *session, err error) { 525 if auth, err = c.decodeHandshakeAuthData(head); err != nil { 526 return nil, auth, nil, err 527 } 528 529 // Verify against our last WHOAREYOU. 530 challenge := c.sc.getHandshake(auth.h.SrcID, fromAddr) 531 if challenge == nil { 532 return nil, auth, nil, errUnexpectedHandshake 533 } 534 // Get node record. 535 n, err = c.decodeHandshakeRecord(challenge.Node, auth.h.SrcID, auth.record) 536 if err != nil { 537 return nil, auth, nil, err 538 } 539 // Verify ID nonce signature. 540 sig := auth.signature 541 cdata := challenge.ChallengeData 542 err = verifyIDSignature(c.sha256, sig, n, cdata, auth.pubkey, c.localnode.ID()) 543 if err != nil { 544 return nil, auth, nil, err 545 } 546 // Verify ephemeral key is on curve. 547 ephkey, err := DecodePubkey(c.privkey.Curve, auth.pubkey) 548 if err != nil { 549 return nil, auth, nil, errInvalidAuthKey 550 } 551 // Derive session keys. 552 session := deriveKeys(sha256.New, c.privkey, ephkey, auth.h.SrcID, c.localnode.ID(), cdata) 553 session = session.keysFlipped() 554 return n, auth, session, nil 555 } 556 557 // decodeHandshakeAuthData reads the authdata section of a handshake packet. 558 func (c *Codec) decodeHandshakeAuthData(head *Header) (auth handshakeAuthData, err error) { 559 // Decode fixed size part. 560 if len(head.AuthData) < sizeofHandshakeAuthData { 561 return auth, fmt.Errorf("header authsize %d too low for handshake", head.AuthSize) 562 } 563 c.reader.Reset(head.AuthData) 564 binary.Read(&c.reader, binary.BigEndian, &auth.h) 565 head.src = auth.h.SrcID 566 567 // Decode variable-size part. 568 var ( 569 vardata = head.AuthData[sizeofHandshakeAuthData:] 570 sigAndKeySize = int(auth.h.SigSize) + int(auth.h.PubkeySize) 571 keyOffset = int(auth.h.SigSize) 572 recOffset = keyOffset + int(auth.h.PubkeySize) 573 ) 574 if len(vardata) < sigAndKeySize { 575 return auth, errTooShort 576 } 577 auth.signature = vardata[:keyOffset] 578 auth.pubkey = vardata[keyOffset:recOffset] 579 auth.record = vardata[recOffset:] 580 return auth, nil 581 } 582 583 // decodeHandshakeRecord verifies the node record contained in a handshake packet. The 584 // remote node should include the record if we don't have one or if ours is older than the 585 // latest sequence number. 586 func (c *Codec) decodeHandshakeRecord(local *enode.Node, wantID enode.ID, remote []byte) (*enode.Node, error) { 587 node := local 588 if len(remote) > 0 { 589 var record enr.Record 590 if err := rlp.DecodeBytes(remote, &record); err != nil { 591 return nil, err 592 } 593 if local == nil || local.Seq() < record.Seq() { 594 n, err := enode.New(enode.ValidSchemes, &record) 595 if err != nil { 596 return nil, fmt.Errorf("invalid node record: %v", err) 597 } 598 if n.ID() != wantID { 599 return nil, fmt.Errorf("record in handshake has wrong ID: %v", n.ID()) 600 } 601 node = n 602 } 603 } 604 if node == nil { 605 return nil, errNoRecord 606 } 607 return node, nil 608 } 609 610 // decodeMessage reads packet data following the header as an ordinary message packet. 611 func (c *Codec) decodeMessage(fromAddr string, head *Header, headerData, msgData []byte) (Packet, error) { 612 if len(head.AuthData) != sizeofMessageAuthData { 613 return nil, fmt.Errorf("invalid auth size %d for message packet", len(head.AuthData)) 614 } 615 var auth messageAuthData 616 c.reader.Reset(head.AuthData) 617 binary.Read(&c.reader, binary.BigEndian, &auth) 618 head.src = auth.SrcID 619 620 // Try decrypting the message. 621 key := c.sc.readKey(auth.SrcID, fromAddr) 622 msg, err := c.decryptMessage(msgData, head.Nonce[:], headerData, key) 623 if errors.Is(err, errMessageDecrypt) { 624 // It didn't work. Start the handshake since this is an ordinary message packet. 625 return &Unknown{Nonce: head.Nonce}, nil 626 } 627 return msg, err 628 } 629 630 func (c *Codec) decryptMessage(input, nonce, headerData, readKey []byte) (Packet, error) { 631 msgdata, err := decryptGCM(readKey, nonce, input, headerData) 632 if err != nil { 633 return nil, errMessageDecrypt 634 } 635 if len(msgdata) == 0 { 636 return nil, errMessageTooShort 637 } 638 return DecodeMessage(msgdata[0], msgdata[1:]) 639 } 640 641 // checkValid performs some basic validity checks on the header. 642 // The packetLen here is the length remaining after the static header. 643 func (h *StaticHeader) checkValid(packetLen int, protocolID [6]byte) error { 644 if h.ProtocolID != protocolID { 645 return errInvalidHeader 646 } 647 if h.Version < minVersion { 648 return errMinVersion 649 } 650 if h.Flag != flagWhoareyou && packetLen < minMessageSize { 651 return errMsgTooShort 652 } 653 if int(h.AuthSize) > packetLen { 654 return errAuthSize 655 } 656 return nil 657 } 658 659 // mask returns a cipher for 'masking' / 'unmasking' packet headers. 660 func (h *Header) mask(destID enode.ID) cipher.Stream { 661 block, err := aes.NewCipher(destID[:16]) 662 if err != nil { 663 panic("can't create cipher") 664 } 665 return cipher.NewCTR(block, h.IV[:]) 666 } 667 668 func bytesCopy(r *bytes.Buffer) []byte { 669 b := make([]byte, r.Len()) 670 copy(b, r.Bytes()) 671 return b 672 }