Пример #1
0
func makeBlockMeta(h *wire.BlockHeader) *BlockMeta {
	return &BlockMeta{
		Block: Block{
			Hash:   h.BlockSha(),
			Height: int32(h.Height),
		},
		Time: time.Time{},
	}
}
Пример #2
0
func makeHeaderData(h *wire.BlockHeader) BlockHeaderData {
	var b bytes.Buffer
	err := h.Serialize(&b)
	if err != nil {
		panic(err)
	}
	d := BlockHeaderData{BlockHash: h.BlockSha()}
	copy(d.SerializedHeader[:], b.Bytes())
	return d
}
Пример #3
0
func TestBlockHeaderHashing(t *testing.T) {
	dummyHeader := "0000000049e0b48ade043f729d60095ed92642d96096fe6aba42f2eda" +
		"632d461591a152267dc840ff27602ce1968a81eb30a43423517207617a0150b56c4f72" +
		"b803e497f00000000000000000000000000000000000000000000000000000000000000" +
		"00010000000000000000000000b7000000ffff7f20204e0000000000005800000060010" +
		"0008b990956000000000000000000000000000000000000000000000000000000000000" +
		"0000000000000000ABCD"
	// This hash has reversed endianness compared to what chainhash spits out.
	hashStr := "0d40d58703482d81d711be0ffc1b313788d3c3937e1617e4876661d33a8c4c41"
	hashB, _ := hex.DecodeString(hashStr)
	hash, _ := chainhash.NewHash(hashB)

	vecH, _ := hex.DecodeString(dummyHeader)
	r := bytes.NewReader(vecH)
	var bh wire.BlockHeader
	bh.Deserialize(r)
	hash2 := bh.BlockSha()

	if !hash2.IsEqual(hash) {
		t.Errorf("wrong block sha returned (want %v, got %v)",
			hash,
			hash2)
	}
}
Пример #4
0
// onBlockConnected is the entry point for processing chain server
// blockconnected notifications.
func (w *Wallet) onBlockConnected(dbtx walletdb.ReadWriteTx, serializedBlockHeader []byte, transactions [][]byte) error {
	var blockHeader wire.BlockHeader
	err := blockHeader.Deserialize(bytes.NewReader(serializedBlockHeader))
	if err != nil {
		return err
	}
	block := wtxmgr.BlockHeaderData{BlockHash: blockHeader.BlockSha()}
	err = copyHeaderSliceToArray(&block.SerializedHeader, serializedBlockHeader)
	if err != nil {
		return err
	}

	w.reorganizingLock.Lock()
	reorg, reorgToHash := w.reorganizing, w.reorganizeToHash
	w.reorganizingLock.Unlock()
	if reorg {
		// add to side chain
		scBlock := sideChainBlock{
			transactions: transactions,
			headerData:   block,
		}
		w.sideChain = append(w.sideChain, scBlock)
		log.Infof("Adding block %v (height %v) to sidechain",
			block.BlockHash, block.SerializedHeader.Height())

		if block.BlockHash != reorgToHash {
			// Nothing left to do until the later blocks are
			// received.
			return nil
		}

		err = w.switchToSideChain(dbtx)
		if err != nil {
			return err
		}

		w.sideChain = nil
		w.reorganizingLock.Lock()
		w.reorganizing = false
		w.reorganizingLock.Unlock()
		log.Infof("Wallet reorganization to block %v complete", reorgToHash)
	} else {
		err = w.extendMainChain(dbtx, &block, transactions)
		if err != nil {
			return err
		}
	}

	height := int32(blockHeader.Height)

	// Handle automatic ticket purchasing if enabled.  This function should
	// not error due to an error purchasing tickets (several tickets may be
	// have been purhcased and successfully published, as well as addresses
	// created and used), so just log it instead.
	err = w.handleTicketPurchases(dbtx, height)
	switch err.(type) {
	case nil:
	case txauthor.InsufficientFundsError:
		log.Debugf("Insufficient funds to auto-purchase maximum number " +
			"of tickets")
	default:
		log.Errorf("Failed to perform automatic picket purchasing: %v", err)
	}

	// Prune all expired transactions and all stake tickets that no longer
	// meet the minimum stake difficulty.
	txmgrNs := dbtx.ReadWriteBucket(wtxmgrNamespaceKey)
	err = w.TxStore.PruneUnconfirmed(txmgrNs, height, blockHeader.SBits)
	if err != nil {
		log.Errorf("Failed to prune unconfirmed transactions when "+
			"connecting block height %v: %s", height, err.Error())
	}

	return nil
}