src/protocol.cpp
//TODO: Nodes that fail to respond should be removed from consideration unless they respond
Nodes that fail to respond should be removed from consideration unless they respond
Nodes that fail to respond should be removed from consideration unless they respond
void Protocol::node_lookup_callback(mp::uint256_t sender, RequestState& request_state, Nodes k_nodes,
                                        mp::uint256_t key, bool found) {
        request_state.responses_waiting--;
        request_state.responded_nodes.insert(sender);
        if (found) {
            assert(request_state.findValue);
            find_value_callback(k_nodes, found, request_state.callback);
            lookups.erase(lookups.find(key), lookups.end());
            return;
        }
        for(NodeInfo node : k_nodes) {
            NodeInfoWrapper node_wrapper(key, node);
            request_state.k_closest_nodes.insert(node_wrapper);
        }
        int responded = 0;
        bool k_responded = true;
        for (auto it=request_state.k_closest_nodes.begin(); it!=request_state.k_closest_nodes.end(); ++it) {
            if (request_state.responses_waiting >= ALPHA) break;
            if (k_responded && responded >= kdml::K) break;
            NodeInfoWrapper node_wrapper = *it;
            auto responded_it = request_state.responded_nodes.find(node_wrapper.node.id);
            if (responded_it != request_state.responded_nodes.end()) {
                responded++;
            } else {
                k_responded = false;
            }
            auto queried_it = request_state.queried_nodes.find(node_wrapper.node.id);
            if (queried_it != request_state.queried_nodes.end()) {
                continue;
            }
            request_state.responses_waiting++;
            request_state.queried_nodes.insert(node_wrapper.node.id);
            if (request_state.findValue) {
                network->send_find_value(key, node_wrapper.node);
            } else {
                network->send_find_node(key, node_wrapper.node);
            }
        }
        if (request_state.responses_waiting == 0) {
            Nodes k_closest_nodes_list;
            for (auto it=request_state.k_closest_nodes.begin(); it!=request_state.k_closest_nodes.end()
                    && k_closest_nodes_list.size() < kdml::K; ++it) {
                NodeInfoWrapper node_wrapper = *it;
                k_closest_nodes_list.push_back(node_wrapper.node);
            }
            if (request_state.findValue) {
                find_value_callback(k_closest_nodes_list, found, request_state.callback);
            } else if (request_state.store){
                store_callback(key, k_closest_nodes_list);
            } else {
                std::cout << "Completed lookup for bootstrapping" << std::endl;
            }
            lookups.erase (lookups.find(key), lookups.end());
        }
    }
void Protocol :: node_lookup_callback ( mp :: uint256_t sender , RequestState & request_state , Nodes k_nodes , mp :: uint256_t key , bool found ) { request_state . responses_waiting -- ; request_state . responded_nodes . insert ( sender ) ; if ( found ) { assert ( request_state . findValue ) ; find_value_callback ( k_nodes , found , request_state . callback ) ; lookups . erase ( lookups . find ( key ) , lookups . end ( ) ) ; return ; } for ( NodeInfo node : k_nodes ) { NodeInfoWrapper node_wrapper ( key , node ) ; request_state . k_closest_nodes . insert ( node_wrapper ) ; } int responded = 0 ; bool k_responded = true ; for ( auto it = request_state . k_closest_nodes . begin ( ) ; it != request_state . k_closest_nodes . end ( ) ; ++ it ) { if ( request_state . responses_waiting >= ALPHA ) break ; if ( k_responded && responded >= kdml :: K ) break ; NodeInfoWrapper node_wrapper = * it ; auto responded_it = request_state . responded_nodes . find ( node_wrapper . node . id ) ; if ( responded_it != request_state . responded_nodes . end ( ) ) { responded ++ ; } else { k_responded = false ; } auto queried_it = request_state . queried_nodes . find ( node_wrapper . node . id ) ; if ( queried_it != request_state . queried_nodes . end ( ) ) { continue ; } request_state . responses_waiting ++ ; request_state . queried_nodes . insert ( node_wrapper . node . id ) ; if ( request_state . findValue ) { network -> send_find_value ( key , node_wrapper . node ) ; } else { network -> send_find_node ( key , node_wrapper . node ) ; } } if ( request_state . responses_waiting == 0 ) { Nodes k_closest_nodes_list ; for ( auto it = request_state . k_closest_nodes . begin ( ) ; it != request_state . k_closest_nodes . end ( ) && k_closest_nodes_list . size ( ) < kdml :: K ; ++ it ) { NodeInfoWrapper node_wrapper = * it ; k_closest_nodes_list . push_back ( node_wrapper . node ) ; } if ( request_state . findValue ) { find_value_callback ( k_closest_nodes_list , found , request_state . callback ) ; } else if ( request_state . store ) { store_callback ( key , k_closest_nodes_list ) ; } else { std :: cout << " " << std :: endl ; } lookups . erase ( lookups . find ( key ) , lookups . end ( ) ) ; } }
TODO: Nodes that fail to respond should be removed from consideration unless they respond
TODO : Nodes that fail to respond should be removed from consideration unless they respond
// If found, k_nodes will be the list of values associated with key // Query alpha more nodes // Terminates when has queried and heard responses from k closest nodes // Keep track if k closest nodes have responded // Do not query if node has already been queried