| 1876 | } |
| 1877 | |
| 1878 | void node_impl::on_hello_message( peer_connection* originating_peer, const hello_message& hello_message_received ) |
| 1879 | { |
| 1880 | VERIFY_CORRECT_THREAD(); |
| 1881 | // this already_connected check must come before we fill in peer data below |
| 1882 | node_id_t peer_node_id = hello_message_received.node_public_key; |
| 1883 | try |
| 1884 | { |
| 1885 | peer_node_id = hello_message_received.user_data["node_id"].as<node_id_t>(); |
| 1886 | } |
| 1887 | catch (const fc::exception&) |
| 1888 | { |
| 1889 | // either it's not there or it's not a valid session id. either way, ignore. |
| 1890 | } |
| 1891 | bool already_connected_to_this_peer = is_already_connected_to_id(peer_node_id); |
| 1892 | |
| 1893 | // validate the node id |
| 1894 | fc::sha256::encoder shared_secret_encoder; |
| 1895 | fc::sha512 shared_secret = originating_peer->get_shared_secret(); |
| 1896 | shared_secret_encoder.write(shared_secret.data(), sizeof(shared_secret)); |
| 1897 | fc::ecc::public_key expected_node_public_key(hello_message_received.signed_shared_secret, shared_secret_encoder.result(), false); |
| 1898 | |
| 1899 | // store off the data provided in the hello message |
| 1900 | originating_peer->user_agent = hello_message_received.user_agent; |
| 1901 | originating_peer->node_public_key = hello_message_received.node_public_key; |
| 1902 | originating_peer->node_id = hello_message_received.node_public_key; // will probably be overwritten in parse_hello_user_data_for_peer() |
| 1903 | originating_peer->core_protocol_version = hello_message_received.core_protocol_version; |
| 1904 | originating_peer->inbound_address = hello_message_received.inbound_address; |
| 1905 | originating_peer->inbound_port = hello_message_received.inbound_port; |
| 1906 | originating_peer->outbound_port = hello_message_received.outbound_port; |
| 1907 | |
| 1908 | parse_hello_user_data_for_peer(originating_peer, hello_message_received.user_data); |
| 1909 | |
| 1910 | // if they didn't provide a last known fork, try to guess it |
| 1911 | if (originating_peer->last_known_fork_block_number == 0 && |
| 1912 | originating_peer->graphene_git_revision_unix_timestamp) |
| 1913 | { |
| 1914 | uint32_t unix_timestamp = originating_peer->graphene_git_revision_unix_timestamp->sec_since_epoch(); |
| 1915 | originating_peer->last_known_fork_block_number = _delegate->estimate_last_known_fork_from_git_revision_timestamp(unix_timestamp); |
| 1916 | } |
| 1917 | |
| 1918 | // now decide what to do with it |
| 1919 | if (originating_peer->their_state == peer_connection::their_connection_state::just_connected) |
| 1920 | { |
| 1921 | if (hello_message_received.node_public_key != expected_node_public_key.serialize()) |
| 1922 | { |
| 1923 | wlog("Invalid signature in hello message from peer ${peer}", ("peer", originating_peer->get_remote_endpoint())); |
| 1924 | std::string rejection_message("Invalid signature in hello message"); |
| 1925 | connection_rejected_message connection_rejected(_user_agent_string, core_protocol_version, |
| 1926 | originating_peer->get_socket().remote_endpoint(), |
| 1927 | rejection_reason_code::invalid_hello_message, |
| 1928 | rejection_message); |
| 1929 | |
| 1930 | originating_peer->their_state = peer_connection::their_connection_state::connection_rejected; |
| 1931 | originating_peer->send_message( message(connection_rejected ) ); |
| 1932 | // for this type of message, we're immediately disconnecting this peer |
| 1933 | disconnect_from_peer( originating_peer, "Invalid signature in hello message" ); |
| 1934 | return; |
| 1935 | } |
nothing calls this directly
no test coverage detected