github.com/decred/dcrlnd@v0.7.6/channeldb/migration_01_to_11/codec.go (about) 1 package migration_01_to_11 2 3 import ( 4 "encoding/binary" 5 "fmt" 6 "io" 7 "net" 8 9 "github.com/decred/dcrd/chaincfg/chainhash" 10 "github.com/decred/dcrd/dcrec/secp256k1/v4" 11 "github.com/decred/dcrd/dcrutil/v4" 12 "github.com/decred/dcrd/wire" 13 lnwire "github.com/decred/dcrlnd/channeldb/migration/lnwire21" 14 "github.com/decred/dcrlnd/keychain" 15 "github.com/decred/dcrlnd/shachain" 16 ) 17 18 // writeOutpoint writes an outpoint to the passed writer using the minimal 19 // amount of bytes possible. 20 func writeOutpoint(w io.Writer, o *wire.OutPoint) error { 21 if _, err := w.Write(o.Hash[:]); err != nil { 22 return err 23 } 24 if err := binary.Write(w, byteOrder, o.Index); err != nil { 25 return err 26 } 27 28 // Note: this is decred-only. 29 if err := binary.Write(w, byteOrder, o.Tree); err != nil { 30 return err 31 } 32 33 return nil 34 } 35 36 // readOutpoint reads an outpoint from the passed reader that was previously 37 // written using the writeOutpoint struct. 38 func readOutpoint(r io.Reader, o *wire.OutPoint) error { 39 if _, err := io.ReadFull(r, o.Hash[:]); err != nil { 40 return err 41 } 42 if err := binary.Read(r, byteOrder, &o.Index); err != nil { 43 return err 44 } 45 46 // Note: this is decred-only. 47 if err := binary.Read(r, byteOrder, &o.Tree); err != nil { 48 return err 49 } 50 51 return nil 52 } 53 54 // UnknownElementType is an error returned when the codec is unable to encode or 55 // decode a particular type. 56 type UnknownElementType struct { 57 method string 58 element interface{} 59 } 60 61 // Error returns the name of the method that encountered the error, as well as 62 // the type that was unsupported. 63 func (e UnknownElementType) Error() string { 64 return fmt.Sprintf("Unknown type in %s: %T", e.method, e.element) 65 } 66 67 // WriteElement is a one-stop shop to write the big endian representation of 68 // any element which is to be serialized for storage on disk. The passed 69 // io.Writer should be backed by an appropriately sized byte slice, or be able 70 // to dynamically expand to accommodate additional data. 71 func WriteElement(w io.Writer, element interface{}) error { 72 switch e := element.(type) { 73 case keychain.KeyDescriptor: 74 if err := binary.Write(w, byteOrder, e.Family); err != nil { 75 return err 76 } 77 if err := binary.Write(w, byteOrder, e.Index); err != nil { 78 return err 79 } 80 81 if e.PubKey != nil { 82 if err := binary.Write(w, byteOrder, true); err != nil { 83 return fmt.Errorf("error writing serialized element: %s", err) 84 } 85 86 return WriteElement(w, e.PubKey) 87 } 88 89 return binary.Write(w, byteOrder, false) 90 case ChannelType: 91 if err := binary.Write(w, byteOrder, e); err != nil { 92 return err 93 } 94 95 case chainhash.Hash: 96 if _, err := w.Write(e[:]); err != nil { 97 return err 98 } 99 100 case wire.OutPoint: 101 return writeOutpoint(w, &e) 102 103 case lnwire.ShortChannelID: 104 if err := binary.Write(w, byteOrder, e.ToUint64()); err != nil { 105 return err 106 } 107 108 case lnwire.ChannelID: 109 if _, err := w.Write(e[:]); err != nil { 110 return err 111 } 112 113 case int64, uint64: 114 if err := binary.Write(w, byteOrder, e); err != nil { 115 return err 116 } 117 118 case uint32: 119 if err := binary.Write(w, byteOrder, e); err != nil { 120 return err 121 } 122 123 case int32: 124 if err := binary.Write(w, byteOrder, e); err != nil { 125 return err 126 } 127 128 case uint16: 129 if err := binary.Write(w, byteOrder, e); err != nil { 130 return err 131 } 132 133 case uint8: 134 if err := binary.Write(w, byteOrder, e); err != nil { 135 return err 136 } 137 138 case bool: 139 if err := binary.Write(w, byteOrder, e); err != nil { 140 return err 141 } 142 143 case dcrutil.Amount: 144 if err := binary.Write(w, byteOrder, uint64(e)); err != nil { 145 return err 146 } 147 148 case lnwire.MilliAtom: 149 if err := binary.Write(w, byteOrder, uint64(e)); err != nil { 150 return err 151 } 152 153 case *secp256k1.PrivateKey: 154 b := e.Serialize() 155 if _, err := w.Write(b); err != nil { 156 return err 157 } 158 159 case *secp256k1.PublicKey: 160 b := e.SerializeCompressed() 161 if _, err := w.Write(b); err != nil { 162 return err 163 } 164 165 case shachain.Producer: 166 return e.Encode(w) 167 168 case shachain.Store: 169 return e.Encode(w) 170 171 case *wire.MsgTx: 172 return e.Serialize(w) 173 174 case [32]byte: 175 if _, err := w.Write(e[:]); err != nil { 176 return err 177 } 178 179 case []byte: 180 if err := wire.WriteVarBytes(w, 0, e); err != nil { 181 return err 182 } 183 184 case lnwire.Message: 185 if _, err := lnwire.WriteMessage(w, e, 0); err != nil { 186 return err 187 } 188 189 case ChannelStatus: 190 if err := binary.Write(w, byteOrder, e); err != nil { 191 return err 192 } 193 194 case ClosureType: 195 if err := binary.Write(w, byteOrder, e); err != nil { 196 return err 197 } 198 199 case lnwire.FundingFlag: 200 if err := binary.Write(w, byteOrder, e); err != nil { 201 return err 202 } 203 204 case net.Addr: 205 if err := serializeAddr(w, e); err != nil { 206 return err 207 } 208 209 case []net.Addr: 210 if err := WriteElement(w, uint32(len(e))); err != nil { 211 return err 212 } 213 214 for _, addr := range e { 215 if err := serializeAddr(w, addr); err != nil { 216 return err 217 } 218 } 219 220 default: 221 return UnknownElementType{"WriteElement", e} 222 } 223 224 return nil 225 } 226 227 // WriteElements is writes each element in the elements slice to the passed 228 // io.Writer using WriteElement. 229 func WriteElements(w io.Writer, elements ...interface{}) error { 230 for _, element := range elements { 231 err := WriteElement(w, element) 232 if err != nil { 233 return err 234 } 235 } 236 return nil 237 } 238 239 // ReadElement is a one-stop utility function to deserialize any datastructure 240 // encoded using the serialization format of the database. 241 func ReadElement(r io.Reader, element interface{}) error { 242 switch e := element.(type) { 243 case *keychain.KeyDescriptor: 244 if err := binary.Read(r, byteOrder, &e.Family); err != nil { 245 return err 246 } 247 if err := binary.Read(r, byteOrder, &e.Index); err != nil { 248 return err 249 } 250 251 var hasPubKey bool 252 if err := binary.Read(r, byteOrder, &hasPubKey); err != nil { 253 return err 254 } 255 256 if hasPubKey { 257 return ReadElement(r, &e.PubKey) 258 } 259 260 case *ChannelType: 261 if err := binary.Read(r, byteOrder, e); err != nil { 262 return err 263 } 264 265 case *chainhash.Hash: 266 if _, err := io.ReadFull(r, e[:]); err != nil { 267 return err 268 } 269 270 case *wire.OutPoint: 271 return readOutpoint(r, e) 272 273 case *lnwire.ShortChannelID: 274 var a uint64 275 if err := binary.Read(r, byteOrder, &a); err != nil { 276 return err 277 } 278 *e = lnwire.NewShortChanIDFromInt(a) 279 280 case *lnwire.ChannelID: 281 if _, err := io.ReadFull(r, e[:]); err != nil { 282 return err 283 } 284 285 case *int64, *uint64: 286 if err := binary.Read(r, byteOrder, e); err != nil { 287 return err 288 } 289 290 case *uint32: 291 if err := binary.Read(r, byteOrder, e); err != nil { 292 return err 293 } 294 295 case *int32: 296 if err := binary.Read(r, byteOrder, e); err != nil { 297 return err 298 } 299 300 case *uint16: 301 if err := binary.Read(r, byteOrder, e); err != nil { 302 return err 303 } 304 305 case *uint8: 306 if err := binary.Read(r, byteOrder, e); err != nil { 307 return err 308 } 309 310 case *bool: 311 if err := binary.Read(r, byteOrder, e); err != nil { 312 return err 313 } 314 315 case *dcrutil.Amount: 316 var a uint64 317 if err := binary.Read(r, byteOrder, &a); err != nil { 318 return err 319 } 320 321 *e = dcrutil.Amount(a) 322 323 case *lnwire.MilliAtom: 324 var a uint64 325 if err := binary.Read(r, byteOrder, &a); err != nil { 326 return err 327 } 328 329 *e = lnwire.MilliAtom(a) 330 331 case **secp256k1.PrivateKey: 332 var b [secp256k1.PrivKeyBytesLen]byte 333 if _, err := io.ReadFull(r, b[:]); err != nil { 334 return err 335 } 336 337 priv := secp256k1.PrivKeyFromBytes(b[:]) 338 *e = priv 339 340 case **secp256k1.PublicKey: 341 var b [secp256k1.PubKeyBytesLenCompressed]byte 342 if _, err := io.ReadFull(r, b[:]); err != nil { 343 return err 344 } 345 346 pubKey, err := secp256k1.ParsePubKey(b[:]) 347 if err != nil { 348 return err 349 } 350 *e = pubKey 351 352 case *shachain.Producer: 353 var root [32]byte 354 if _, err := io.ReadFull(r, root[:]); err != nil { 355 return err 356 } 357 358 // TODO(roasbeef): remove 359 producer, err := shachain.NewRevocationProducerFromBytes(root[:]) 360 if err != nil { 361 return err 362 } 363 364 *e = producer 365 366 case *shachain.Store: 367 store, err := shachain.NewRevocationStoreFromBytes(r) 368 if err != nil { 369 return err 370 } 371 372 *e = store 373 374 case **wire.MsgTx: 375 tx := wire.NewMsgTx() 376 if err := tx.Deserialize(r); err != nil { 377 return err 378 } 379 380 *e = tx 381 382 case *[32]byte: 383 if _, err := io.ReadFull(r, e[:]); err != nil { 384 return err 385 } 386 387 case *[]byte: 388 bytes, err := wire.ReadVarBytes(r, 0, 66000, "[]byte") 389 if err != nil { 390 return err 391 } 392 393 *e = bytes 394 395 case *lnwire.Message: 396 msg, err := lnwire.ReadMessage(r, 0) 397 if err != nil { 398 return err 399 } 400 401 *e = msg 402 403 case *ChannelStatus: 404 if err := binary.Read(r, byteOrder, e); err != nil { 405 return err 406 } 407 408 case *ClosureType: 409 if err := binary.Read(r, byteOrder, e); err != nil { 410 return err 411 } 412 413 case *lnwire.FundingFlag: 414 if err := binary.Read(r, byteOrder, e); err != nil { 415 return err 416 } 417 418 case *net.Addr: 419 addr, err := deserializeAddr(r) 420 if err != nil { 421 return err 422 } 423 *e = addr 424 425 case *[]net.Addr: 426 var numAddrs uint32 427 if err := ReadElement(r, &numAddrs); err != nil { 428 return err 429 } 430 431 *e = make([]net.Addr, numAddrs) 432 for i := uint32(0); i < numAddrs; i++ { 433 addr, err := deserializeAddr(r) 434 if err != nil { 435 return err 436 } 437 (*e)[i] = addr 438 } 439 440 default: 441 return UnknownElementType{"ReadElement", e} 442 } 443 444 return nil 445 } 446 447 // ReadElements deserializes a variable number of elements into the passed 448 // io.Reader, with each element being deserialized according to the ReadElement 449 // function. 450 func ReadElements(r io.Reader, elements ...interface{}) error { 451 for _, element := range elements { 452 err := ReadElement(r, element) 453 if err != nil { 454 return err 455 } 456 } 457 return nil 458 }