github.com/lbryio/lbcd@v0.22.119/wire/msgnotfound_test.go (about) 1 // Copyright (c) 2013-2016 The btcsuite developers 2 // Use of this source code is governed by an ISC 3 // license that can be found in the LICENSE file. 4 5 package wire 6 7 import ( 8 "bytes" 9 "io" 10 "reflect" 11 "testing" 12 13 "github.com/davecgh/go-spew/spew" 14 "github.com/lbryio/lbcd/chaincfg/chainhash" 15 ) 16 17 // TestNotFound tests the MsgNotFound API. 18 func TestNotFound(t *testing.T) { 19 pver := ProtocolVersion 20 21 // Ensure the command is expected value. 22 wantCmd := "notfound" 23 msg := NewMsgNotFound() 24 if cmd := msg.Command(); cmd != wantCmd { 25 t.Errorf("NewMsgNotFound: wrong command - got %v want %v", 26 cmd, wantCmd) 27 } 28 29 // Ensure max payload is expected value for latest protocol version. 30 // Num inventory vectors (varInt) + max allowed inventory vectors. 31 wantPayload := uint32(1800009) 32 maxPayload := msg.MaxPayloadLength(pver) 33 if maxPayload != wantPayload { 34 t.Errorf("MaxPayloadLength: wrong max payload length for "+ 35 "protocol version %d - got %v, want %v", pver, 36 maxPayload, wantPayload) 37 } 38 39 // Ensure inventory vectors are added properly. 40 hash := chainhash.Hash{} 41 iv := NewInvVect(InvTypeBlock, &hash) 42 err := msg.AddInvVect(iv) 43 if err != nil { 44 t.Errorf("AddInvVect: %v", err) 45 } 46 if msg.InvList[0] != iv { 47 t.Errorf("AddInvVect: wrong invvect added - got %v, want %v", 48 spew.Sprint(msg.InvList[0]), spew.Sprint(iv)) 49 } 50 51 // Ensure adding more than the max allowed inventory vectors per 52 // message returns an error. 53 for i := 0; i < MaxInvPerMsg; i++ { 54 err = msg.AddInvVect(iv) 55 } 56 if err == nil { 57 t.Errorf("AddInvVect: expected error on too many inventory " + 58 "vectors not received") 59 } 60 } 61 62 // TestNotFoundWire tests the MsgNotFound wire encode and decode for various 63 // numbers of inventory vectors and protocol versions. 64 func TestNotFoundWire(t *testing.T) { 65 // Block 203707 hash. 66 hashStr := "3264bc2ac36a60840790ba1d475d01367e7c723da941069e9dc" 67 blockHash, err := chainhash.NewHashFromStr(hashStr) 68 if err != nil { 69 t.Errorf("NewHashFromStr: %v", err) 70 } 71 72 // Transaction 1 of Block 203707 hash. 73 hashStr = "d28a3dc7392bf00a9855ee93dd9a81eff82a2c4fe57fbd42cfe71b487accfaf0" 74 txHash, err := chainhash.NewHashFromStr(hashStr) 75 if err != nil { 76 t.Errorf("NewHashFromStr: %v", err) 77 } 78 79 iv := NewInvVect(InvTypeBlock, blockHash) 80 iv2 := NewInvVect(InvTypeTx, txHash) 81 82 // Empty notfound message. 83 NoInv := NewMsgNotFound() 84 NoInvEncoded := []byte{ 85 0x00, // Varint for number of inventory vectors 86 } 87 88 // NotFound message with multiple inventory vectors. 89 MultiInv := NewMsgNotFound() 90 MultiInv.AddInvVect(iv) 91 MultiInv.AddInvVect(iv2) 92 MultiInvEncoded := []byte{ 93 0x02, // Varint for number of inv vectors 94 0x02, 0x00, 0x00, 0x00, // InvTypeBlock 95 0xdc, 0xe9, 0x69, 0x10, 0x94, 0xda, 0x23, 0xc7, 96 0xe7, 0x67, 0x13, 0xd0, 0x75, 0xd4, 0xa1, 0x0b, 97 0x79, 0x40, 0x08, 0xa6, 0x36, 0xac, 0xc2, 0x4b, 98 0x26, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Block 203707 hash 99 0x01, 0x00, 0x00, 0x00, // InvTypeTx 100 0xf0, 0xfa, 0xcc, 0x7a, 0x48, 0x1b, 0xe7, 0xcf, 101 0x42, 0xbd, 0x7f, 0xe5, 0x4f, 0x2c, 0x2a, 0xf8, 102 0xef, 0x81, 0x9a, 0xdd, 0x93, 0xee, 0x55, 0x98, 103 0x0a, 0xf0, 0x2b, 0x39, 0xc7, 0x3d, 0x8a, 0xd2, // Tx 1 of block 203707 hash 104 } 105 106 tests := []struct { 107 in *MsgNotFound // Message to encode 108 out *MsgNotFound // Expected decoded message 109 buf []byte // Wire encoding 110 pver uint32 // Protocol version for wire encoding 111 enc MessageEncoding // Message encoding format 112 }{ 113 // Latest protocol version with no inv vectors. 114 { 115 NoInv, 116 NoInv, 117 NoInvEncoded, 118 ProtocolVersion, 119 BaseEncoding, 120 }, 121 122 // Latest protocol version with multiple inv vectors. 123 { 124 MultiInv, 125 MultiInv, 126 MultiInvEncoded, 127 ProtocolVersion, 128 BaseEncoding, 129 }, 130 131 // Protocol version BIP0035Version no inv vectors. 132 { 133 NoInv, 134 NoInv, 135 NoInvEncoded, 136 BIP0035Version, 137 BaseEncoding, 138 }, 139 140 // Protocol version BIP0035Version with multiple inv vectors. 141 { 142 MultiInv, 143 MultiInv, 144 MultiInvEncoded, 145 BIP0035Version, 146 BaseEncoding, 147 }, 148 149 // Protocol version BIP0031Version no inv vectors. 150 { 151 NoInv, 152 NoInv, 153 NoInvEncoded, 154 BIP0031Version, 155 BaseEncoding, 156 }, 157 158 // Protocol version BIP0031Version with multiple inv vectors. 159 { 160 MultiInv, 161 MultiInv, 162 MultiInvEncoded, 163 BIP0031Version, 164 BaseEncoding, 165 }, 166 167 // Protocol version NetAddressTimeVersion no inv vectors. 168 { 169 NoInv, 170 NoInv, 171 NoInvEncoded, 172 NetAddressTimeVersion, 173 BaseEncoding, 174 }, 175 176 // Protocol version NetAddressTimeVersion with multiple inv vectors. 177 { 178 MultiInv, 179 MultiInv, 180 MultiInvEncoded, 181 NetAddressTimeVersion, 182 BaseEncoding, 183 }, 184 185 // Protocol version MultipleAddressVersion no inv vectors. 186 { 187 NoInv, 188 NoInv, 189 NoInvEncoded, 190 MultipleAddressVersion, 191 BaseEncoding, 192 }, 193 194 // Protocol version MultipleAddressVersion with multiple inv vectors. 195 { 196 MultiInv, 197 MultiInv, 198 MultiInvEncoded, 199 MultipleAddressVersion, 200 BaseEncoding, 201 }, 202 } 203 204 t.Logf("Running %d tests", len(tests)) 205 for i, test := range tests { 206 // Encode the message to wire format. 207 var buf bytes.Buffer 208 err := test.in.BtcEncode(&buf, test.pver, test.enc) 209 if err != nil { 210 t.Errorf("BtcEncode #%d error %v", i, err) 211 continue 212 } 213 if !bytes.Equal(buf.Bytes(), test.buf) { 214 t.Errorf("BtcEncode #%d\n got: %s want: %s", i, 215 spew.Sdump(buf.Bytes()), spew.Sdump(test.buf)) 216 continue 217 } 218 219 // Decode the message from wire format. 220 var msg MsgNotFound 221 rbuf := bytes.NewReader(test.buf) 222 err = msg.BtcDecode(rbuf, test.pver, test.enc) 223 if err != nil { 224 t.Errorf("BtcDecode #%d error %v", i, err) 225 continue 226 } 227 if !reflect.DeepEqual(&msg, test.out) { 228 t.Errorf("BtcDecode #%d\n got: %s want: %s", i, 229 spew.Sdump(msg), spew.Sdump(test.out)) 230 continue 231 } 232 } 233 } 234 235 // TestNotFoundWireErrors performs negative tests against wire encode and decode 236 // of MsgNotFound to confirm error paths work correctly. 237 func TestNotFoundWireErrors(t *testing.T) { 238 pver := ProtocolVersion 239 wireErr := &MessageError{} 240 241 // Block 203707 hash. 242 hashStr := "3264bc2ac36a60840790ba1d475d01367e7c723da941069e9dc" 243 blockHash, err := chainhash.NewHashFromStr(hashStr) 244 if err != nil { 245 t.Errorf("NewHashFromStr: %v", err) 246 } 247 248 iv := NewInvVect(InvTypeBlock, blockHash) 249 250 // Base message used to induce errors. 251 baseNotFound := NewMsgNotFound() 252 baseNotFound.AddInvVect(iv) 253 baseNotFoundEncoded := []byte{ 254 0x02, // Varint for number of inv vectors 255 0x02, 0x00, 0x00, 0x00, // InvTypeBlock 256 0xdc, 0xe9, 0x69, 0x10, 0x94, 0xda, 0x23, 0xc7, 257 0xe7, 0x67, 0x13, 0xd0, 0x75, 0xd4, 0xa1, 0x0b, 258 0x79, 0x40, 0x08, 0xa6, 0x36, 0xac, 0xc2, 0x4b, 259 0x26, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Block 203707 hash 260 } 261 262 // Message that forces an error by having more than the max allowed inv 263 // vectors. 264 maxNotFound := NewMsgNotFound() 265 for i := 0; i < MaxInvPerMsg; i++ { 266 maxNotFound.AddInvVect(iv) 267 } 268 maxNotFound.InvList = append(maxNotFound.InvList, iv) 269 maxNotFoundEncoded := []byte{ 270 0xfd, 0x51, 0xc3, // Varint for number of inv vectors (50001) 271 } 272 273 tests := []struct { 274 in *MsgNotFound // Value to encode 275 buf []byte // Wire encoding 276 pver uint32 // Protocol version for wire encoding 277 enc MessageEncoding // Message encoding format 278 max int // Max size of fixed buffer to induce errors 279 writeErr error // Expected write error 280 readErr error // Expected read error 281 }{ 282 // Force error in inventory vector count 283 {baseNotFound, baseNotFoundEncoded, pver, BaseEncoding, 0, io.ErrShortWrite, io.EOF}, 284 // Force error in inventory list. 285 {baseNotFound, baseNotFoundEncoded, pver, BaseEncoding, 1, io.ErrShortWrite, io.EOF}, 286 // Force error with greater than max inventory vectors. 287 {maxNotFound, maxNotFoundEncoded, pver, BaseEncoding, 3, wireErr, wireErr}, 288 } 289 290 t.Logf("Running %d tests", len(tests)) 291 for i, test := range tests { 292 // Encode to wire format. 293 w := newFixedWriter(test.max) 294 err := test.in.BtcEncode(w, test.pver, test.enc) 295 if reflect.TypeOf(err) != reflect.TypeOf(test.writeErr) { 296 t.Errorf("BtcEncode #%d wrong error got: %v, want: %v", 297 i, err, test.writeErr) 298 continue 299 } 300 301 // For errors which are not of type MessageError, check them for 302 // equality. 303 if _, ok := err.(*MessageError); !ok { 304 if err != test.writeErr { 305 t.Errorf("BtcEncode #%d wrong error got: %v, "+ 306 "want: %v", i, err, test.writeErr) 307 continue 308 } 309 } 310 311 // Decode from wire format. 312 var msg MsgNotFound 313 r := newFixedReader(test.max, test.buf) 314 err = msg.BtcDecode(r, test.pver, test.enc) 315 if reflect.TypeOf(err) != reflect.TypeOf(test.readErr) { 316 t.Errorf("BtcDecode #%d wrong error got: %v, want: %v", 317 i, err, test.readErr) 318 continue 319 } 320 321 // For errors which are not of type MessageError, check them for 322 // equality. 323 if _, ok := err.(*MessageError); !ok { 324 if err != test.readErr { 325 t.Errorf("BtcDecode #%d wrong error got: %v, "+ 326 "want: %v", i, err, test.readErr) 327 continue 328 } 329 } 330 } 331 }