aboutsummaryrefslogblamecommitdiff
path: root/src/hotstuff.cpp
blob: 95825310c5a6365df45cf1b9adf73a1b4a47a352 (plain) (tree)
1
2
3
4
5
6
7
8

                              
                                      



                                    
 






                                                         

 

                                                           

 











































                                                                                        
         

                                         
         

     
 

























































                                                                  
         




                                                                           
 


                            
         

                                                             
         
                                       
     













                                                                  
      







                                                          

 















                                                                             

 




























































                                                                                  
                               













                                                                            
 









































                                                                              
     



                                                                           
     


                                            
     


































                                                                                 
           





                                                                         
     
                      

 
































                                                                                                     

 





                                                                
 






                                                                       

 



















                                                                           
 
 
#include "hotstuff/hotstuff.h"

using salticidae::static_pointer_cast;

#define LOG_INFO HOTSTUFF_LOG_INFO
#define LOG_DEBUG HOTSTUFF_LOG_DEBUG
#define LOG_WARN HOTSTUFF_LOG_WARN

namespace hotstuff {

void MsgHotStuff::gen_propose(const Proposal &proposal) {
    DataStream s;
    set_opcode(PROPOSE);
    s << proposal;
    set_payload(std::move(s));
}

void MsgHotStuff::parse_propose(Proposal &proposal) const {
    DataStream(get_payload()) >> proposal;
}

void MsgHotStuff::gen_vote(const Vote &vote) {
    DataStream s;
    set_opcode(VOTE);
    s << vote;
    set_payload(std::move(s));
}

void MsgHotStuff::parse_vote(Vote &vote) const {
    DataStream(get_payload()) >> vote;
}

void MsgHotStuff::gen_qfetchblk(const std::vector<uint256_t> &blk_hashes) {
    DataStream s;
    set_opcode(QUERY_FETCH_BLK);
    gen_hash_list(s, blk_hashes);
    set_payload(std::move(s));
}

void MsgHotStuff::parse_qfetchblk(std::vector<uint256_t> &blk_hashes) const {
    DataStream s(get_payload());
    parse_hash_list(s, blk_hashes);
}

void MsgHotStuff::gen_rfetchblk(const std::vector<block_t> &blks) {
    DataStream s;
    set_opcode(RESP_FETCH_BLK);
    s << htole((uint32_t)blks.size());
    for (auto blk: blks) s << *blk;
    set_payload(std::move(s));
}

void MsgHotStuff::parse_rfetchblk(std::vector<block_t> &blks, HotStuffCore *hsc) const {
    DataStream s;
    uint32_t size;
    s >> size;
    size = letoh(size);
    blks.resize(size);
    for (auto &blk: blks)
    {
        Block _blk;
        _blk.unserialize(s, hsc);
        if (!_blk.verify(hsc->get_config()))
            blk = hsc->storage->add_blk(std::move(_blk));
        else
        {
            blk = nullptr;
            LOG_WARN("block is invalid");
        }
    }
}

void HotStuffBase::add_replica(ReplicaID idx, const NetAddr &addr,
                                pubkey_bt &&pub_key) {
    HotStuffCore::add_replica(idx, addr, std::move(pub_key));
    if (addr != listen_addr)
        pn.add_peer(addr);
}

void HotStuffBase::on_fetch_blk(const block_t &blk) {
#ifdef HOTSTUFF_ENABLE_TX_PROFILE
    blk_profiler.get_tx(blk->get_hash());
#endif
    LOG_DEBUG("fetched %.10s", get_hex(blk->get_hash()).c_str());
    part_fetched++;
    fetched++;
    for (auto cmd: blk->get_cmds()) on_fetch_cmd(cmd);
    const uint256_t &blk_hash = blk->get_hash();
    auto it = blk_fetch_waiting.find(blk_hash);
    if (it != blk_fetch_waiting.end())
    {
        it->second.resolve(blk);
        blk_fetch_waiting.erase(it);
    }
}

void HotStuffBase::on_fetch_cmd(const command_t &cmd) {
    const uint256_t &cmd_hash = cmd->get_hash();
    auto it = cmd_fetch_waiting.find(cmd_hash);
    if (it != cmd_fetch_waiting.end())
    {
        it->second.resolve(cmd);
        cmd_fetch_waiting.erase(it);
    }
}

void HotStuffBase::on_deliver_blk(const block_t &blk) {
    const uint256_t &blk_hash = blk->get_hash();
    bool valid;
    /* sanity check: all parents must be delivered */
    for (const auto &p: blk->get_parent_hashes())
        assert(storage->is_blk_delivered(p));
    if ((valid = HotStuffCore::on_deliver_blk(blk)))