Esempio n. 1
0
 private void extendMainChain(Block block) {
   if (Arrays.equals(block.getBlockPrev(), this.lastBlock.getBlockHash())) {
     block.setMain(true);
     this.addBlock(block);
     this.lastBlock = block;
   }
 }
Esempio n. 2
0
 public void addSPVBlock(Block block) {
   // only none block need add spv block
   if (this.getBlockCount() == 0) {
     block.setMain(true);
     this.addBlock(block);
     this.lastBlock = block;
   }
 }
Esempio n. 3
0
 private void forkMainChain(Block forkStartBlock, Block lastBlock) {
   Block b = this.lastBlock;
   Block next = lastBlock;
   while (!Arrays.equals(b.getBlockHash(), forkStartBlock.getBlockHash())) {
     next = AbstractDb.blockProvider.getOrphanBlockByPrevHash(b.getBlockPrev());
     AbstractDb.blockProvider.updateBlock(b.getBlockHash(), false);
     b = AbstractDb.blockProvider.getMainChainBlock(b.getBlockPrev());
     this.lastBlock = b;
   }
   b = next;
   AbstractDb.blockProvider.updateBlock(next.getBlockHash(), true);
   this.lastBlock = next;
   while (!Arrays.equals(b.getBlockHash(), lastBlock.getBlockPrev())) {
     AbstractDb.blockProvider.updateBlock(b.getBlockHash(), true);
     this.lastBlock = b;
     b = AbstractDb.blockProvider.getOrphanBlockByPrevHash(b.getBlockHash());
   }
   lastBlock.setMain(true);
   this.addBlock(lastBlock);
   this.lastBlock = lastBlock;
 }
Esempio n. 4
0
  public int relayedBlockHeadersForMainChain(List<Block> blocks) {
    if (blocks == null || blocks.size() == 0) {
      return 0;
    }
    ArrayList<Block> blocksToAdd = new ArrayList<Block>();
    Block prev = getLastBlock();
    if (prev == null) {
      log.warn("pre block is null");
      return 0;
    }
    for (int i = 0; i < blocks.size(); i++) {
      Block block = blocks.get(i);
      if (!Arrays.equals(prev.getBlockHash(), block.getBlockPrev())) {
        Block alreadyIn = getBlock(block.getBlockHash());
        if (alreadyIn != null) {
          log.debug("Block is already in, No." + alreadyIn.getBlockNo());
          continue;
        } else {
          this.singleBlocks.put(block.getBlockHash(), block);
          break;
        }
      }
      block.setBlockNo(prev.getBlockNo() + 1);
      try {
        block.verifyDifficultyFromPreviousBlock(prev);
      } catch (Exception e) {
        e.printStackTrace();
        break;
      }

      block.setMain(true);
      blocksToAdd.add(block);
      prev = block;
    }
    if (blocksToAdd.size() > 0) {
      addBlocks(blocksToAdd);
      lastBlock = blocksToAdd.get(blocksToAdd.size() - 1);
    }
    return blocksToAdd.size();
  }
Esempio n. 5
0
 private void addOrphan(Block block) {
   block.setMain(false);
   this.addBlock(block);
   this.lastOrphanBlock = block;
 }
Esempio n. 6
0
  public int relayedBlocks(List<Block> blocks) throws VerificationException {
    if (blocks == null || blocks.size() == 0) {
      return 0;
    }
    Block prev = null;
    Block first = blocks.get(0);
    int rollbackBlockNo = 0;
    if (Arrays.equals(first.getBlockPrev(), this.getLastBlock().getBlockHash())) {
      prev = this.getLastBlock();
    } else if (AbstractDb.blockProvider.getMainChainBlock(first.getBlockPrev()) != null) {
      prev = this.getSameParent(first, this.getLastBlock());
      rollbackBlockNo = prev.getBlockNo();
    }
    if (prev == null) {
      return 0;
    }
    for (Block block : blocks) {
      if (!Arrays.equals(block.getBlockPrev(), prev.getBlockHash())) {
        return 0;
      }
      block.setBlockNo(prev.getBlockNo() + 1);
      try {
        int transitionTime = 0;
        if (block.getBlockNo() % BitherjSettings.BLOCK_DIFFICULTY_INTERVAL == 0) {
          // We need to find a block far back in the chain. It's OK that this is expensive because
          // it only occurs every
          // two weeks after the initial block chain download.
          long now = System.currentTimeMillis();
          Block cursor = first;
          for (int i = 0;
              i
                  < BitherjSettings.BLOCK_DIFFICULTY_INTERVAL
                      - block.getBlockNo()
                      + first.getBlockNo();
              i++) {
            if (cursor == null) {
              // This should never happen. If it does, it means we are following an incorrect or
              // busted chain.
              throw new VerificationException(
                  "Difficulty transition point but we did not find a way back to the genesis block.");
            }
            cursor = getBlock(cursor.getBlockPrev());
          }
          long elapsed = System.currentTimeMillis() - now;
          if (elapsed > 50) log.info("Difficulty transition traversal took {}msec", elapsed);

          transitionTime = cursor.getBlockTime();
        }
        block.verifyDifficultyFromPreviousBlock(prev, transitionTime);
      } catch (Exception e) {
        e.printStackTrace();
        return 0;
      }

      block.setMain(true);
      prev = block;
    }
    if (rollbackBlockNo > 0) {
      this.rollbackBlock(rollbackBlockNo);
    }
    this.addBlocks(blocks);
    for (Block block : blocks) {
      AbstractDb.txProvider.confirmTx(block.getBlockNo(), block.getTxHashes());
    }
    this.lastBlock = blocks.get(blocks.size() - 1);
    return blocks.size();
  }