Main Page | Modules | Alphabetical List | Data Structures | File List | Data Fields | Globals | Related Pages

nodes.c File Reference


Detailed Description

Gnutella node management.

Author:
Raphael Manfredi
Date:
2001-2004

#include "common.h"
#include "sockets.h"
#include "search.h"
#include "share.h"
#include "routing.h"
#include "hosts.h"
#include "nodes.h"
#include "gmsg.h"
#include "mq.h"
#include "mq_tcp.h"
#include "mq_udp.h"
#include "sq.h"
#include "tx.h"
#include "tx_link.h"
#include "tx_deflate.h"
#include "tx_dgram.h"
#include "rxbuf.h"
#include "rx.h"
#include "rx_link.h"
#include "rx_inflate.h"
#include "pmsg.h"
#include "pcache.h"
#include "bsched.h"
#include "http.h"
#include "version.h"
#include "alive.h"
#include "uploads.h"
#include "whitelist.h"
#include "gnet_stats.h"
#include "ban.h"
#include "hcache.h"
#include "qrp.h"
#include "vmsg.h"
#include "token.h"
#include "hostiles.h"
#include "clock.h"
#include "hsep.h"
#include "dq.h"
#include "dh.h"
#include "ioheader.h"
#include "settings.h"
#include "features.h"
#include "udp.h"
#include "tsync.h"
#include "geo_ip.h"
#include "extensions.h"
#include "bh_upload.h"
#include "lib/aging.h"
#include "lib/atoms.h"
#include "lib/cq.h"
#include "lib/dbus_util.h"
#include "lib/getdate.h"
#include "lib/endian.h"
#include "lib/getline.h"
#include "lib/glib-missing.h"
#include "lib/header.h"
#include "lib/idtable.h"
#include "lib/listener.h"
#include "lib/misc.h"
#include "lib/tm.h"
#include "lib/utf8.h"
#include "lib/walloc.h"
#include "lib/zlib_util.h"
#include "if/gnet_property.h"
#include "if/gnet_property_priv.h"
#include "lib/override.h"

Data Structures

struct  node_bad_client

Defines

#define CONNECT_PONGS_COUNT   10 /**< Amoung of pongs to send */
 Amoung of pongs to send.

#define CONNECT_PONGS_LOW   5 /**< Amoung of pongs sent if saturated */
 Amoung of pongs sent if saturated.

#define BYE_MAX_SIZE   4096 /**< Maximum size for the Bye message */
 Maximum size for the Bye message.

#define NODE_SEND_BUFSIZE   4096 /**< TCP send buffer size - 4K */
 TCP send buffer size - 4K.

#define NODE_SEND_LEAF_BUFSIZE   1024 /**< TCP send buffer size for leaves */
 TCP send buffer size for leaves.

#define MAX_GGEP_PAYLOAD   1536 /**< In ping, pong, push */
 In ping, pong, push.

#define MAX_MSG_SIZE   65536 /**< Absolute maximum message length */
 Absolute maximum message length.

#define MAX_HOP_COUNT   255 /**< Architecturally defined maximum */
 Architecturally defined maximum.

#define NODE_LEGACY_DEGREE   8 /**< Older node without X-Degree */
 Older node without X-Degree.

#define NODE_LEGACY_TTL   7 /**< Older node without X-Max-TTL */
 Older node without X-Max-TTL.

#define NODE_USELESS_GRACE   20 /**< No kick if condition too recent */
 No kick if condition too recent.

#define SHUTDOWN_GRACE_DELAY   120 /**< Grace time for shutdowning nodes */
 Grace time for shutdowning nodes.

#define BYE_GRACE_DELAY   30 /**< Bye sent, give time to propagate */
 Bye sent, give time to propagate.

#define MAX_WEIRD_MSG   5 /**< End link after so much weirds */
 End link after so much weirds.

#define MAX_TX_RX_RATIO   70 /**< Max TX/RX ratio for shortage */
 Max TX/RX ratio for shortage.

#define MIN_TX_FOR_RATIO   500 /**< TX packets before enforcing ratio */
 TX packets before enforcing ratio.

#define ALIVE_PERIOD   20 /**< Seconds between each alive ping */
 Seconds between each alive ping.

#define ALIVE_PERIOD_LEAF   120 /**< Idem, for leaves <-> ultrapeers */
 Idem, for leaves <-> ultrapeers.

#define ALIVE_MAX_PENDING   6 /**< Max unanswered pings in a row */
 Max unanswered pings in a row.

#define ALIVE_MAX_PENDING_LEAF   4 /**< Max unanswered pings in a row (leaves) */
 Max unanswered pings in a row (leaves).

#define NODE_MIN_UP_CONNECTIONS   25 /**< Min 25 peer connections for UP */
 Min 25 peer connections for UP.

#define NODE_MIN_UPTIME   3600 /**< Minumum uptime to become an UP */
 Minumum uptime to become an UP.

#define NODE_MIN_AVG_UPTIME   10800 /**< Average uptime to become an UP */
 Average uptime to become an UP.

#define NODE_AVG_LEAF_MEM   262144 /**< Average memory used by leaf */
 Average memory used by leaf.

#define NODE_CASUAL_FD   10 /**< # of fds we might use casually */
 # of fds we might use casually

#define NODE_UPLOAD_QUEUE_FD   5 /**< # of fds/upload slot we can queue */
 # of fds/upload slot we can queue

#define NODE_TX_BUFSIZ   1024 /**< Buffer size for TX deflation */
 Buffer size for TX deflation.

#define NODE_TX_FLUSH   16384 /**< Flush deflator every 16K */
 Flush deflator every 16K.

#define NODE_AUTO_SWITCH_MIN   1800 /**< Don't switch too often UP - leaf */
 Don't switch too often UP - leaf.

#define NODE_AUTO_SWITCH_MAX   61200 /**< Max between switches (17 hours) */
 Max between switches (17 hours).

#define NODE_TSYNC_WAIT_MS   5000 /**< Wait time after connecting (5s) */
 Wait time after connecting (5s).

#define NODE_TSYNC_PERIOD_MS   300000 /**< Synchronize every 5 minutes */
 Synchronize every 5 minutes.

#define NODE_TSYNC_CHECK   15 /**< 15 secs before a timeout */
 15 secs before a timeout

#define TCP_CRAWLER_FREQ   300 /**< once every 5 minutes */
 once every 5 minutes

#define UDP_CRAWLER_FREQ   120 /**< once every 2 minutes */
 once every 2 minutes

#define NO_METADATA   GUINT_TO_POINTER(1) /**< No metadata for host */
 No metadata for host.

#define node_find_by_handle(n)   (gnutella_node_t *) idtable_get_value(node_handle_map, n)
#define node_request_handle(n)   idtable_new_id(node_handle_map, n)
#define node_drop_handle(n)   idtable_free_id(node_handle_map, n);
#define OK(b)   ((b) ? ok : no)
#define NODE(x)   ((struct gnutella_node *) (x))

Typedefs

typedef node_bad_client node_bad_client_t

Enumerations

enum  node_bad { NODE_BAD_OK = 0, NODE_BAD_IP, NODE_BAD_VENDOR, NODE_BAD_NO_VENDOR }
 Types of bad nodes for node_is_bad(). More...


Functions

 RCSID ("$Id:nodes.c, v 1.158 2006/02/10 18:55:28 rmanfredi Exp $")
void node_disable_read (struct gnutella_node *n)
 Disable reading callback.

void node_data_ind (rxdrv_t *rx, pmsg_t *mb)
 RX data indication callback used to give us some new Gnet traffic in a low-level message structure (which can contain several Gnet messages).

void node_bye_sent (struct gnutella_node *n)
 Called when the Bye message has been successfully sent.

void call_node_process_handshake_ack (gpointer obj, header_t *header)
void node_send_qrt (struct gnutella_node *n, gpointer query_table)
 Initiate sending of the query routing table.

void node_send_patch_step (struct gnutella_node *n)
 Incrementally send the routing table patch to our Ultrapeer.

void node_bye_flags (guint32 mask, gint code, gchar *message)
 Send a BYE message to all the nodes matching the specified flags.

void node_bye_all_but_one (struct gnutella_node *nskip, gint code, gchar *message)
 Send a BYE message to all the nodes but the one supplied as argument.

void node_set_current_peermode (node_peer_t mode)
 Called from the node timer when the current peermode has changed.

enum node_bad node_is_bad (struct gnutella_node *n)
 Check whether node has been identified as having a bad IP or vendor string.

gnutella_node_tnode_udp_create (void)
 Create a "fake" node that is used as a placeholder when processing Gnutella messages received from UDP.

gnutella_node_tnode_browse_create (void)
 Create a "fake" node that is used as a placeholder when processing Gnutella messages received via host browsing.

gboolean node_remove_useless_leaf (void)
 Try to spot a "useless" leaf node.

void node_add_node_added_listener (node_added_listener_t l)
void node_remove_node_added_listener (node_added_listener_t l)
void node_add_node_removed_listener (node_removed_listener_t l)
void node_remove_node_removed_listener (node_removed_listener_t l)
void node_add_node_info_changed_listener (node_info_changed_listener_t l)
void node_remove_node_info_changed_listener (node_info_changed_listener_t l)
void node_add_node_flags_changed_listener (node_flags_changed_listener_t l)
void node_remove_node_flags_changed_listener (node_flags_changed_listener_t l)
void node_fire_node_added (gnutella_node_t *n)
void node_fire_node_removed (gnutella_node_t *n)
void node_fire_node_info_changed (gnutella_node_t *n)
void node_fire_node_flags_changed (gnutella_node_t *n)
void free_key (gpointer key, gpointer unused_val, gpointer unused_x)
 Free atom string key from hash table.

gboolean free_key_true (gpointer key, gpointer unused_val, gpointer unused_x)
 Free atom string key from hash table and return TRUE.

void string_table_clear (GHashTable *ht)
 Clear hash table whose keys are atoms and values ignored.

void string_table_free (GHashTable *ht)
 Dispose of hash table whose keys are atoms and values ignored.

void node_tsync_udp (cqueue_t *unused_cq, gpointer obj)
 Send "Time Sync" via UDP if we know the remote IP:port, via TCP otherwise.

void node_can_tsync (gnutella_node_t *n)
 Invoked when we determined that the node supports Time Sync.

void node_tsync_tcp (gnutella_node_t *n)
 Sent "probe" time sync via TCP to the specified node to compute the RTT...

gboolean node_ht_connected_nodes_has (const host_addr_t addr, guint16 port)
 Check whether we already have the host.

gnet_host_tnode_ht_connected_nodes_find (const host_addr_t addr, guint16 port)
 Check whether we already have the host.

void node_ht_connected_nodes_add (const host_addr_t addr, guint16 port)
 Add host to the hash table host cache.

void node_ht_connected_nodes_remove (const host_addr_t addr, guint16 port)
 Remove host from the hash table host cache.

void message_dump (const struct gnutella_node *n)
 Dumps a gnutella message (debug).

void node_extract_host (const struct gnutella_node *n, host_addr_t *ha, guint16 *port)
 Extract IP/port information out of the Query Hit into `ip' and `port'.

gboolean can_become_ultra (time_t now)
 Check the Ultrapeer requirements, returning TRUE if we can become an UP.

void node_slow_timer (time_t now)
 Low frequency node timer.

void node_error_cleanup (void)
void node_timer (time_t now)
 Periodic node heartbeat timer.

void node_init (void)
 Network init.

void node_post_init (void)
 Post GUI initialization.

void node_set_socket_rx_size (gint rx_size)
 Change the socket RX buffer size for all the currently connected nodes.

guint connected_nodes (void)
guint node_count (void)
guint node_keep_missing (void)
 Amount of node connections we would like to keep.

guint node_missing (void)
 Amount of node connections we would like to have.

guint node_leaves_missing (void)
 Amount of leaves we're missing (0 if not in ultra mode).

guint node_outdegree (void)
void get_protocol_version (const gchar *handshake, guint *major, guint *minor)
 Parse the first handshake line to determine the protocol version.

void node_type_count_dec (struct gnutella_node *n)
 Decrement the proper node count property, depending on the peermode.

void node_real_remove (gnutella_node_t *n)
 Physically dispose of node.

 G_GNUC_PRINTF (2, 0)
 The vectorized (message-wise) version of node_remove().

void node_recursive_shutdown_v (struct gnutella_node *n, const gchar *where, const gchar *reason, va_list ap)
 Called when node_bye() or node_shutdown() is called during the time we're in shutdown mode, processing the messages we might still read from the socket.

void node_remove_by_handle (gnet_node_t n)
 Removes or shuts down the given node.

void node_mark_bad_vendor (struct gnutella_node *n)
 Gives a specific vendor a bad mark.

gboolean node_avoid_monopoly (struct gnutella_node *n)
 Make sure that the vendor of the connecting node does not already use more than "unique_nodes" percent of the slots of its kind.

gboolean node_reserve_slot (struct gnutella_node *n)
 When we only have "reserve_gtkg_nodes" percent slots left, make sure the connecting node is a GTKG node or refuse the connection.

void node_remove (struct gnutella_node *n, const gchar *reason,...)
 Terminate connection with remote node, but keep structure around for a while, for displaying purposes, and also to prevent the node from being physically reclaimed within this stack frame.

void node_eof_v (struct gnutella_node *n, const gchar *reason, va_list args)
 The vectorized version of node_eof().

void node_eof (struct gnutella_node *n, const gchar *reason,...)
 Got an EOF condition, or a read error, whilst reading Gnet data from node.

void node_shutdown_mode (struct gnutella_node *n, guint32 delay)
 Enter shutdown mode: prevent further writes, drop read broadcasted messages, and make sure we flush the buffers at the fastest possible speed.

void node_shutdown_v (struct gnutella_node *n, const gchar *reason, va_list args)
 The vectorized version of node_shutdown().

void node_shutdown (struct gnutella_node *n, const gchar *reason,...)
 Stop sending data to node, but keep reading buffered data from it, until we hit a Bye packet or EOF.

void node_bye_v (struct gnutella_node *n, gint code, const gchar *reason, va_list ap)
 The vectorized version of node_bye().

void node_bye (gnutella_node_t *n, gint code, const gchar *reason,...)
 Terminate connection by sending a bye message to the remote node.

void node_bye_if_writable (struct gnutella_node *n, gint code, const gchar *reason,...)
 If node is writable, act as if node_bye() had been called.

gboolean node_is_connected (const host_addr_t addr, guint16 port, gboolean incoming)
 Is there a node connected with this IP/port?

gboolean node_host_is_connected (const host_addr_t addr, guint16 port)
 Are we directly connected to that host?

gchar * formatted_connection_pongs (gchar *field, host_type_t htype, gint num)
 Build CONNECT_PONGS_COUNT pongs to emit as an X-Try header.

gint node_gtkg_cmp (const void *np1, const void *np2)
 qsort() callback for sorting GTKG nodes at the front.

gchar * node_crawler_headers (struct gnutella_node *n)
 Generate the "Peers:" and "Leaves:" headers in a static buffer.

void send_error (struct gnutella_socket *s, struct gnutella_node *n, int code, const gchar *msg, va_list ap)
 Send error message to remote end, a node presumably.

void send_node_error (struct gnutella_socket *s, int code, const gchar *msg,...)
 Send error message to remote end, a node presumably.

void node_send_error (struct gnutella_node *n, int code, const gchar *msg,...)
 Send error message to remote node.

void send_proxy_request (gnutella_node_t *n)
 Request that node becomes our push-proxy.

void node_became_firewalled (void)
 Called when we were not firewalled and suddenly become firewalled.

void node_became_udp_firewalled (void)
 Called when we were not firewalled and suddenly become UDP firewalled.

void node_add_tx_deflated (gpointer o, gint amount)
void node_tx_shutdown (gpointer o, const gchar *reason,...)
void node_add_tx_written (gpointer o, gint amount)
void node_tx_eof_remove (gpointer o, const gchar *reason,...)
void node_tx_eof_shutdown (gpointer o, const gchar *reason,...)
void node_tx_unflushq (gpointer o)
void node_add_rx_inflated (gpointer o, gint amount)
void node_rx_inflate_error (gpointer o, const gchar *reason,...)
void node_add_rx_given (gpointer o, gint amount)
void node_rx_read_error (gpointer o, const gchar *reason,...)
void node_rx_got_eof (gpointer o)
void node_is_now_connected (struct gnutella_node *n)
 Called when we know that we're connected to the node, at the end of the handshaking (both for incoming and outgoing connections).

void node_got_bye (struct gnutella_node *n)
 Received a Bye message from remote node.

void node_set_online_mode (gboolean on)
 Whether they want to be "online" within Gnutella or not.

void node_current_peermode_changed (node_peer_t mode)
 Called from the property system when current peermode is changed.

guint feed_host_cache_from_string (const gchar *s, host_type_t type, const gchar *name)
guint feed_host_cache_from_headers (header_t *header, host_type_t sender, gboolean gnet, const host_addr_t peer)
 Extract host:port information out of a header field and add those to our pong cache.

void extract_header_pongs (header_t *header, struct gnutella_node *n)
 Extract the header pongs from the header (X-Try lines).

host_addr_t extract_my_addr (header_t *header)
 Try to determine whether headers contain an indication of our own IP.

void node_check_remote_ip_header (const host_addr_t peer, header_t *head)
 Checks for a Remote-IP or X-Remote-IP header and updates our IP address if the current IP address is not enforced.

gboolean analyse_status (struct gnutella_node *n, gint *code)
 Analyses status lines we get from incoming handshakes (final ACK) or outgoing handshakes (inital REPLY, after our HELLO).

gboolean node_can_accept_connection (struct gnutella_node *n, gboolean handshaking)
 Can node accept connection?

gboolean node_can_accept_protocol (struct gnutella_node *n, header_t *head)
 Check whether we can accept a servent supporting a foreign protocol.

void node_process_handshake_ack (struct gnutella_node *n, header_t *head)
 This routine is called to process the whole 0.6+ final handshake header acknowledgement we get back after welcoming an incoming node.

gchar * node_query_routing_header (struct gnutella_node *n)
void node_process_handshake_header (struct gnutella_node *n, header_t *head)
 This routine is called to process a 0.6+ handshake header.

void err_line_too_long (gpointer obj)
void err_header_error_tell (gpointer obj, gint error)
void err_header_error (gpointer obj, gint error)
void err_input_exception (gpointer obj)
void err_input_buffer_full (gpointer obj)
void err_header_read_error (gpointer obj, gint error)
void err_header_read_eof (gpointer obj)
void err_header_extra_data (gpointer obj)
void call_node_process_handshake_header (gpointer obj, header_t *header)
gnutella_node_tnode_browse_prepare (gnet_host_t *host, const gchar *vendor, struct gnutella_header *header, gchar *data, guint32 size)
 Let the "browse host" node hold the supplied Gnutella message as if coming from the host and from a servent with the supplied vendor string.

void node_browse_cleanup (gnutella_node_t *n)
 Cleanup the "browse host" node.

void node_udp_enable (void)
 Enable UDP transmission via pseudo node.

void node_udp_disable (void)
 Disable UDP transmission via pseudo node.

gnutella_node_tnode_udp_get (struct gnutella_socket *s)
 Get "fake" node after reception of a datagram and return its address.

mqueue_tnode_udp_get_outq (void)
 Get the message queue attached to the UDP node.

gnutella_node_tnode_udp_get_addr_port (const host_addr_t addr, guint16 port)
 Get "fake" node for UDP transmission.

void node_udp_gui_show (void)
 Show UDP node in the GUI.

void node_udp_gui_remove (void)
 Remove UDP node from the GUI.

void node_add (const host_addr_t addr, guint16 port, guint32 flags)
 Add new node.

void node_add_socket (struct gnutella_socket *s, const host_addr_t addr, guint16 port, guint32 flags)
 Add new node, to which we possibly have an existing connection if the socket is not NULL (incoming connection).

gboolean node_check_ggep (struct gnutella_node *n, gint maxsize, gint regsize)
 Check that current message has an extra payload made of GGEP only, and whose total size is not exceeding `maxsize'.

void node_parse (struct gnutella_node *node)
 Processing of messages.

void node_drain_hello (gpointer data, gint source, inputevt_cond_t cond)
void node_udp_process (struct gnutella_socket *s)
 Process incoming Gnutella datagram.

void node_init_outgoing (struct gnutella_node *n)
 Called when asynchronous connection to an outgoing node is established.

void node_flushq (struct gnutella_node *n)
 Called by queue when it's not empty and it went through the service routine and yet has more data enqueued.

void node_unflushq (struct gnutella_node *n)
 Called by queue to disable the flush mode.

void node_tx_service (struct gnutella_node *n, gboolean unused_on)
 Called when the queue service routine is switched ON/OFF.

void node_tx_enter_warnzone (struct gnutella_node *n)
 Called by message queue when the node enters the warn zone.

void node_tx_leave_warnzone (struct gnutella_node *n)
 Called by message queue when the node leaves the warn zone.

void node_tx_enter_flowc (struct gnutella_node *n)
 Called by message queue when the node enters TX flow control.

void node_tx_leave_flowc (struct gnutella_node *n)
 Called by message queue when the node leaves TX flow control.

void node_tx_swift_changed (struct gnutella_node *n)
 Called by message queue when swift mode changes.

gboolean node_read (struct gnutella_node *n, pmsg_t *mb)
 Read data from the message buffer we just received.

void node_sent_ttl0 (struct gnutella_node *n)
 Called when a node sends a message with TTL=0.

void node_bye_all (void)
 Send a BYE message to all the nodes.

gboolean node_bye_pending (void)
gboolean node_remove_worst (gboolean non_local)
 Removes the node with the worst stats, considering the number of weird, bad and duplicate packets.

void node_qrt_discard (struct gnutella_node *n)
 Invoked when remote sends us a RESET message, making the existing routing table obsolete.

void node_qrt_install (struct gnutella_node *n, gpointer query_table)
 Invoked for ultra nodes to install new Query Routing Table.

void node_qrt_patched (struct gnutella_node *n, gpointer query_table)
 Invoked for ultra nodes when the Query Routing Table of remote node was fully patched (i.e.

void node_qrt_changed (gpointer query_table)
 Invoked for nodes when our Query Routing Table changed.

void node_close (void)
 Final cleanup when application terminates.

void node_add_sent (gnutella_node_t *n, gint x)
void node_add_txdrop (gnutella_node_t *n, gint x)
void node_add_rxdrop (gnutella_node_t *n, gint x)
void node_set_vendor (gnutella_node_t *n, const gchar *vendor)
 Record vendor name (user-agent string).

void node_set_hops_flow (gnutella_node_t *n, guint8 hops)
 Called when a vendor-specific "hops-flow" message was received to tell us to update the hops-flow counter for the connection: no query whose hop count is greater or equal to the specified `hops' should be sent to that node.

gnet_node_info_tnode_get_info (const gnet_node_t n)
 Fetches information about a given node.

void node_clear_info (gnet_node_info_t *info)
 Clear dynamically allocated information from the info structure.

void node_free_info (gnet_node_info_t *info)
 Frees the gnet_node_info_t data returned by node_get_info.

void node_fill_info (const gnet_node_t n, gnet_node_info_t *info)
 Fill in supplied info structure.

void node_fill_flags (const gnet_node_t n, gnet_node_flags_t *flags)
 Fill in supplied flags structure.

void node_get_status (const gnet_node_t n, gnet_node_status_t *status)
 Fetch node status for the GUI display.

void node_remove_nodes_by_handle (GSList *node_list)
 Disconnect from the given list of node handles.

const gchar * node_addr (const gnutella_node_t *n)
const gchar * node_gnet_addr (const gnutella_node_t *n)
void node_connect_back (const gnutella_node_t *n, guint16 port)
 Connect back to node on specified port and emit a "\n\n" sequence.

void node_connected_back (struct gnutella_socket *s)
 Callback invoked from the socket layer when we are finally connected.

void node_proxying_remove (gnutella_node_t *n, gboolean discard)
 Remove push proxy indication for the node, i.e.

gboolean node_proxying_add (gnutella_node_t *n, gchar *guid)
 Record that node wants us to be his push proxy.

void node_proxy_add (gnutella_node_t *n, const host_addr_t addr, guint16 port)
 Add node to our list of push-proxies.

void node_proxy_cancel_all (void)
 Cancel all our known push-proxies.

void node_http_proxies_add (gchar *buf, gint *retval, gpointer unused_arg, guint32 unused_flags)
 HTTP status callback.

GSList * node_push_proxies (void)
const GSList * node_all_nodes (void)
const GSList * node_all_but_broken_gtkg (void)
gnutella_node_tnode_active_by_id (guint32 id)
gint node_ua_cmp (const void *np1, const void *np2)
 qsort() callback for sorting nodes by user-agent.

void node_crawl_append_vendor (GString *ua, gchar *vendor)
 Append user-agent string to the string holding them, each value being separated from the previous with NODE_CR_SEPARATOR.

gint node_crawl_fill (pmsg_t *mb, gnutella_node_t **ary, gint start, gint len, gint want, guint8 features, time_t now, GString *ua, gboolean gtkg)
 Fill message with the selected crawling information.

void node_crawl (gnutella_node_t *n, gint ucnt, gint lcnt, guint8 features)
 Received an UDP crawler ping, requesting information about `ucnt' ultra nodes and `lcnt' leaves.

void node_update_udp_socket (void)
 This has to be called once the UDP socket (e.g., due to a changed port number) was changed because some internal references have to be updated.


Variables

gchar * start_rfc822_date = NULL
 RFC822 format of start_time.

GSList * sl_nodes = NULL
GSList * sl_nodes_without_broken_gtkg = NULL
GHashTable * nodes_by_id = NULL
gnutella_node_tudp_node = NULL
gnutella_node_tbrowse_node = NULL
GHashTable * ht_connected_nodes = NULL
guint32 connected_node_count = 0
GHashTable * unstable_servent = NULL
GSList * unstable_servents = NULL
gpointer tcp_crawls = NULL
gpointer udp_crawls = NULL
int node_error_threshold = 6
 This requires an average uptime of 1 hour for an ultrapeer.

time_t node_error_cleanup_timer = 6 * 3600
 6 hours

GSList * sl_proxies = NULL
idtable_tnode_handle_map = NULL
guint32 shutdown_nodes = 0
guint32 node_id = 1
 Reserve 0 for the local node.

gboolean allow_gnet_connections = FALSE
GHookList node_added_hook_list
gnutella_nodenode_added
 For use by node_added_hook_list hooks, since we can't add a parameter at list invoke time.

struct {
   gboolean   changed
   node_peer_t   new
peermode
 Structure used for asynchronous reaction to peer mode changes.

guint connected_node_cnt = 0
guint compressed_node_cnt = 0
guint compressed_leaf_cnt = 0
gint pending_byes = 0
gboolean in_shutdown = FALSE
guint32 leaf_to_up_switch = NODE_AUTO_SWITCH_MIN
const gchar no_reason [] = "<no reason>"
query_hashvec_tquery_hashvec = NULL
listeners_t node_added_listeners = NULL
listeners_t node_removed_listeners = NULL
listeners_t node_info_changed_listeners = NULL
listeners_t node_flags_changed_listeners = NULL
tx_deflate_cb node_tx_deflate_cb
tx_link_cb node_tx_link_cb
tx_dgram_cb node_tx_dgram_cb
rx_inflate_cb node_rx_inflate_cb
rx_link_cb node_rx_link_cb
io_error node_io_error


Define Documentation

#define ALIVE_MAX_PENDING   6 /**< Max unanswered pings in a row */
 

Max unanswered pings in a row.

#define ALIVE_MAX_PENDING_LEAF   4 /**< Max unanswered pings in a row (leaves) */
 

Max unanswered pings in a row (leaves).

#define ALIVE_PERIOD   20 /**< Seconds between each alive ping */
 

Seconds between each alive ping.

#define ALIVE_PERIOD_LEAF   120 /**< Idem, for leaves <-> ultrapeers */
 

Idem, for leaves <-> ultrapeers.

#define BYE_GRACE_DELAY   30 /**< Bye sent, give time to propagate */
 

Bye sent, give time to propagate.

#define BYE_MAX_SIZE   4096 /**< Maximum size for the Bye message */
 

Maximum size for the Bye message.

#define CONNECT_PONGS_COUNT   10 /**< Amoung of pongs to send */
 

Amoung of pongs to send.

#define CONNECT_PONGS_LOW   5 /**< Amoung of pongs sent if saturated */
 

Amoung of pongs sent if saturated.

#define MAX_GGEP_PAYLOAD   1536 /**< In ping, pong, push */
 

In ping, pong, push.

#define MAX_HOP_COUNT   255 /**< Architecturally defined maximum */
 

Architecturally defined maximum.

#define MAX_MSG_SIZE   65536 /**< Absolute maximum message length */
 

Absolute maximum message length.

#define MAX_TX_RX_RATIO   70 /**< Max TX/RX ratio for shortage */
 

Max TX/RX ratio for shortage.

#define MAX_WEIRD_MSG   5 /**< End link after so much weirds */
 

End link after so much weirds.

#define MIN_TX_FOR_RATIO   500 /**< TX packets before enforcing ratio */
 

TX packets before enforcing ratio.

#define NO_METADATA   GUINT_TO_POINTER(1) /**< No metadata for host */
 

No metadata for host.

#define NODE  )     ((struct gnutella_node *) (x))
 

#define NODE_AUTO_SWITCH_MAX   61200 /**< Max between switches (17 hours) */
 

Max between switches (17 hours).

#define NODE_AUTO_SWITCH_MIN   1800 /**< Don't switch too often UP - leaf */
 

Don't switch too often UP - leaf.

#define NODE_AVG_LEAF_MEM   262144 /**< Average memory used by leaf */
 

Average memory used by leaf.

#define NODE_CASUAL_FD   10 /**< # of fds we might use casually */
 

# of fds we might use casually

#define node_drop_handle  )     idtable_free_id(node_handle_map, n);
 

#define node_find_by_handle  )     (gnutella_node_t *) idtable_get_value(node_handle_map, n)
 

#define NODE_LEGACY_DEGREE   8 /**< Older node without X-Degree */
 

Older node without X-Degree.

#define NODE_LEGACY_TTL   7 /**< Older node without X-Max-TTL */
 

Older node without X-Max-TTL.

#define NODE_MIN_AVG_UPTIME   10800 /**< Average uptime to become an UP */
 

Average uptime to become an UP.

#define NODE_MIN_UP_CONNECTIONS   25 /**< Min 25 peer connections for UP */
 

Min 25 peer connections for UP.

#define NODE_MIN_UPTIME   3600 /**< Minumum uptime to become an UP */
 

Minumum uptime to become an UP.

#define node_request_handle  )     idtable_new_id(node_handle_map, n)
 

#define NODE_SEND_BUFSIZE   4096 /**< TCP send buffer size - 4K */
 

TCP send buffer size - 4K.

#define NODE_SEND_LEAF_BUFSIZE   1024 /**< TCP send buffer size for leaves */
 

TCP send buffer size for leaves.

#define NODE_TSYNC_CHECK   15 /**< 15 secs before a timeout */
 

15 secs before a timeout

#define NODE_TSYNC_PERIOD_MS   300000 /**< Synchronize every 5 minutes */
 

Synchronize every 5 minutes.

#define NODE_TSYNC_WAIT_MS   5000 /**< Wait time after connecting (5s) */
 

Wait time after connecting (5s).

#define NODE_TX_BUFSIZ   1024 /**< Buffer size for TX deflation */
 

Buffer size for TX deflation.

#define NODE_TX_FLUSH   16384 /**< Flush deflator every 16K */
 

Flush deflator every 16K.

#define NODE_UPLOAD_QUEUE_FD   5 /**< # of fds/upload slot we can queue */
 

# of fds/upload slot we can queue

#define NODE_USELESS_GRACE   20 /**< No kick if condition too recent */
 

No kick if condition too recent.

#define OK  )     ((b) ? ok : no)
 

#define SHUTDOWN_GRACE_DELAY   120 /**< Grace time for shutdowning nodes */
 

Grace time for shutdowning nodes.

#define TCP_CRAWLER_FREQ   300 /**< once every 5 minutes */
 

once every 5 minutes

#define UDP_CRAWLER_FREQ   120 /**< once every 2 minutes */
 

once every 2 minutes


Typedef Documentation

typedef struct node_bad_client node_bad_client_t
 


Enumeration Type Documentation

enum node_bad
 

Types of bad nodes for node_is_bad().

Enumeration values:
NODE_BAD_OK  Node is fine.
NODE_BAD_IP  Node has a bad (unstable) IP.
NODE_BAD_VENDOR  Node has a bad vendor string.
NODE_BAD_NO_VENDOR  Node has no vendor string.


Function Documentation

gboolean analyse_status struct gnutella_node n,
gint *  code
[static]
 

Analyses status lines we get from incoming handshakes (final ACK) or outgoing handshakes (inital REPLY, after our HELLO).

Returns:
TRUE if acknowledgment was OK, FALSE if an error occurred, in which case the node was removed with proper status.
If `code' is not NULL, it is filled with the returned code, or -1 if we were unable to parse the status.

void call_node_process_handshake_ack gpointer  obj,
header_t header
[static]
 

void call_node_process_handshake_header gpointer  obj,
header_t header
[static]
 

gboolean can_become_ultra time_t  now  )  [static]
 

Check the Ultrapeer requirements, returning TRUE if we can become an UP.

guint connected_nodes void   ) 
 

void err_header_error gpointer  obj,
gint  error
[static]
 

void err_header_error_tell gpointer  obj,
gint  error
[static]
 

void err_header_extra_data gpointer  obj  )  [static]
 

void err_header_read_eof gpointer  obj  )  [static]
 

void err_header_read_error gpointer  obj,
gint  error
[static]
 

void err_input_buffer_full gpointer  obj  )  [static]
 

void err_input_exception gpointer  obj  )  [static]
 

void err_line_too_long gpointer  obj  )  [static]
 

void extract_header_pongs header_t header,
struct gnutella_node n
[static]
 

Extract the header pongs from the header (X-Try lines).

The node is only given for tracing purposes.

host_addr_t extract_my_addr header_t header  )  [static]
 

Try to determine whether headers contain an indication of our own IP.

Returns:
0 if none found, or the indicated IP address.

guint feed_host_cache_from_headers header_t header,
host_type_t  sender,
gboolean  gnet,
const host_addr_t  peer
 

Extract host:port information out of a header field and add those to our pong cache.

If ``gnet'' is TRUE, the header names without a leading "X-" are checked as variants as well.

Parameters:
header a valid header_t.
sender the host_type_t of the sender, if unknown use HOST_ANY.
gnet should be set to TRUE if the headers come from a Gnutella handshake.
peer the peer address who sent the headers.
Returns:
the amount of valid peer addresses we parsed.
The syntax we expect is:

: ("," )*

peer = [":" ] [any except ","]* header = "Alt" | Listen-Ip" | "Listen-Ip" | "My-Address" | "Node" | "Try" | "Try-Ultrapeers"

guint feed_host_cache_from_string const gchar *  s,
host_type_t  type,
const gchar *  name
[static]
 

gchar* formatted_connection_pongs gchar *  field,
host_type_t  htype,
gint  num
[static]
 

Build CONNECT_PONGS_COUNT pongs to emit as an X-Try header.

We stick to strict formatting rules: no line of more than 76 chars.

Returns:
a pointer to static data.

Bug:
XXX Refactoring note: there is a need for generic header formatting routines, and especially the dumping routing, which could be taught basic formatting and splitting so that very long lines are dumped using continuations. --RAM, 10/01/2002

void free_key gpointer  key,
gpointer  unused_val,
gpointer  unused_x
[static]
 

Free atom string key from hash table.

gboolean free_key_true gpointer  key,
gpointer  unused_val,
gpointer  unused_x
[static]
 

Free atom string key from hash table and return TRUE.

G_GNUC_PRINTF ,
[static]
 

The vectorized (message-wise) version of node_remove().

void get_protocol_version const gchar *  handshake,
guint *  major,
guint *  minor
[static]
 

Parse the first handshake line to determine the protocol version.

The major and minor are returned in `major' and `minor' respectively.

void message_dump const struct gnutella_node n  )  [static]
 

Dumps a gnutella message (debug).

gnutella_node_t* node_active_by_id guint32  id  ) 
 

Returns:
writable node given its ID, or NULL if we can't reach that node.

void node_add const host_addr_t  addr,
guint16  port,
guint32  flags
 

Add new node.

void node_add_node_added_listener node_added_listener_t  l  ) 
 

void node_add_node_flags_changed_listener node_flags_changed_listener_t  l  ) 
 

void node_add_node_info_changed_listener node_info_changed_listener_t  l  ) 
 

void node_add_node_removed_listener node_removed_listener_t  l  ) 
 

void node_add_rx_given gpointer  o,
gint  amount
[static]
 

void node_add_rx_inflated gpointer  o,
gint  amount
[static]
 

void node_add_rxdrop gnutella_node_t n,
gint  x
[inline]
 

void node_add_sent gnutella_node_t n,
gint  x
[inline]
 

void node_add_socket struct gnutella_socket s,
const host_addr_t  addr,
guint16  port,
guint32  flags
 

Add new node, to which we possibly have an existing connection if the socket is not NULL (incoming connection).

void node_add_tx_deflated gpointer  o,
gint  amount
[static]
 

void node_add_tx_written gpointer  o,
gint  amount
[static]
 

void node_add_txdrop gnutella_node_t n,
gint  x
[inline]
 

const gchar* node_addr const gnutella_node_t n  ) 
 

Returns:
the address:port of a node

const GSList* node_all_but_broken_gtkg void   ) 
 

Returns:
list of all nodes without any broken GTKG (those nodes that must not be forwarded any duplicate message, even with a higher TTL than previously sent).

const GSList* node_all_nodes void   ) 
 

Returns:
list of all nodes.

gboolean node_avoid_monopoly struct gnutella_node n  )  [static]
 

Make sure that the vendor of the connecting node does not already use more than "unique_nodes" percent of the slots of its kind.

Returns:
TRUE if accepting the node would make us use more slots than what the user has configured as acceptable.
Note:
when low on pongs, monopoly protection is disabled to avoid the host contacting the web caches just because it cannot fulfill its anti-monopoly requirements.

void node_became_firewalled void   ) 
 

Called when we were not firewalled and suddenly become firewalled.

Send proxy requests to our current connections.

void node_became_udp_firewalled void   ) 
 

Called when we were not firewalled and suddenly become UDP firewalled.

Send UDP connect back requests to our current connections.

void node_browse_cleanup gnutella_node_t n  ) 
 

Cleanup the "browse host" node.

gnutella_node_t * node_browse_create void   )  [static]
 

Create a "fake" node that is used as a placeholder when processing Gnutella messages received via host browsing.

The node instance is shared but needs to be filled with the received message before parsing of the Gnutella query hit can occur.

gnutella_node_t* node_browse_prepare gnet_host_t host,
const gchar *  vendor,
struct gnutella_header header,
gchar *  data,
guint32  size
 

Let the "browse host" node hold the supplied Gnutella message as if coming from the host and from a servent with the supplied vendor string.

Returns:
the shared instance, suitable for parsing the received message.

void node_bye gnutella_node_t n,
gint  code,
const gchar *  reason,
... 
 

Terminate connection by sending a bye message to the remote node.

Upon reception of that message, the connection will be closed by the remote party.

This is otherwise equivalent to the node_shutdown() call.

void node_bye_all void   ) 
 

Send a BYE message to all the nodes.

void node_bye_all_but_one struct gnutella_node nskip,
gint  code,
gchar *  message
[static]
 

Send a BYE message to all the nodes but the one supplied as argument.

void node_bye_flags guint32  mask,
gint  code,
gchar *  message
[static]
 

Send a BYE message to all the nodes matching the specified flags.

void node_bye_if_writable struct gnutella_node n,
gint  code,
const gchar *  reason,
... 
 

If node is writable, act as if node_bye() had been called.

Otherwise, act as if node_remove() had been called.

gboolean node_bye_pending void   ) 
 

Returns:
true whilst there are some connections with a pending BYE.

void node_bye_sent struct gnutella_node n  )  [static]
 

Called when the Bye message has been successfully sent.

void node_bye_v struct gnutella_node n,
gint  code,
const gchar *  reason,
va_list  ap
[static]
 

The vectorized version of node_bye().

gboolean node_can_accept_connection struct gnutella_node n,
gboolean  handshaking
[static]
 

Can node accept connection?

If `handshaking' is true, we're still in the handshaking phase, otherwise we're already connected and can send a BYE.

Returns:
TRUE if we can accept the connection, FALSE otherwise, with the node being removed.

gboolean node_can_accept_protocol struct gnutella_node n,
header_t head
[static]
 

Check whether we can accept a servent supporting a foreign protocol.

Must be called during handshaking.

Returns:
TRUE if OK, FALSE if connection was denied.

void node_can_tsync gnutella_node_t n  ) 
 

Invoked when we determined that the node supports Time Sync.

gboolean node_check_ggep struct gnutella_node n,
gint  maxsize,
gint  regsize
[static]
 

Check that current message has an extra payload made of GGEP only, and whose total size is not exceeding `maxsize'.

Parameters:
`n' no brief description.
`maxsize' no brief description.
`regsize' value is the normal payload length of the message (e.g. 0 for a ping).
Returns:
TRUE if there is a GGEP extension block, and only that after the regular payload, with a size no greater than `maxsize'.
Note:
parsed extensions are left in the node's `extensions' structure.

void node_check_remote_ip_header const host_addr_t  peer,
header_t head
 

Checks for a Remote-IP or X-Remote-IP header and updates our IP address if the current IP address is not enforced.

Note that settings_addr_changed() doesn't trust a single source.

Parameters:
peer the IPv4 address of the peer who sent the header
head a header_t holding headers sent by the peer

void node_clear_info gnet_node_info_t info  ) 
 

Clear dynamically allocated information from the info structure.

void node_close void   ) 
 

Final cleanup when application terminates.

void node_connect_back const gnutella_node_t n,
guint16  port
 

Connect back to node on specified port and emit a "\n\n" sequence.

This is called when a "Connect Back" vendor-specific message (BEAR/7v1) is received. This scheme is used by servents to detect whether they are firewalled.

void node_connected_back struct gnutella_socket s  ) 
 

Callback invoked from the socket layer when we are finally connected.

guint node_count void   ) 
 

void node_crawl gnutella_node_t n,
gint  ucnt,
gint  lcnt,
guint8  features
 

Received an UDP crawler ping, requesting information about `ucnt' ultra nodes and `lcnt' leaves.

Processing is further customized with some `features', a set of flags.

void node_crawl_append_vendor GString *  ua,
gchar *  vendor
[static]
 

Append user-agent string to the string holding them, each value being separated from the previous with NODE_CR_SEPARATOR.

The LimeWire crawler expects a very simple escaping whereby every separator found in the vendor string is preceded by NODE_CR_ESCAPE_CHAR. We further escape the escape character with itself, if found.

gint node_crawl_fill pmsg_t mb,
gnutella_node_t **  ary,
gint  start,
gint  len,
gint  want,
guint8  features,
time_t  now,
GString *  ua,
gboolean  gtkg
[static]
 

Fill message with the selected crawling information.

Parameters:
mb the message into which we're writing
ary the node array
start the starting index in the array
len the array length
want the amount of entries they want
features the selected features to insert
now current time, for connection time computation
ua the concatenated user-agent string
gtkg if TRUE only Gtk-Gnutella nodes are added, otherwise only nodes of other vendors are added.
Returns:
the amount of entries successfully written

gchar* node_crawler_headers struct gnutella_node n  )  [static]
 

Generate the "Peers:" and "Leaves:" headers in a static buffer.

Returns:
ready-to-insert header chunk, with all lines ending with "\r\n".

void node_current_peermode_changed node_peer_t  mode  ) 
 

Called from the property system when current peermode is changed.

void node_data_ind rxdrv_t rx,
pmsg_t mb
[static]
 

RX data indication callback used to give us some new Gnet traffic in a low-level message structure (which can contain several Gnet messages).

void node_disable_read struct gnutella_node n  )  [static]
 

Disable reading callback.

void node_drain_hello gpointer  data,
gint  source,
inputevt_cond_t  cond
[static]
 

void node_eof struct gnutella_node n,
const gchar *  reason,
... 
 

Got an EOF condition, or a read error, whilst reading Gnet data from node.

Terminate connection with remote node, but keep structure around for a while, for displaying purposes.

void node_eof_v struct gnutella_node n,
const gchar *  reason,
va_list  args
[static]
 

The vectorized version of node_eof().

void node_error_cleanup void   )  [inline, static]
 

void node_extract_host const struct gnutella_node n,
host_addr_t ha,
guint16 *  port
[static]
 

Extract IP/port information out of the Query Hit into `ip' and `port'.

void node_fill_flags const gnet_node_t  n,
gnet_node_flags_t flags
 

Fill in supplied flags structure.

void node_fill_info const gnet_node_t  n,
gnet_node_info_t info
 

Fill in supplied info structure.

void node_fire_node_added gnutella_node_t n  )  [static]
 

void node_fire_node_flags_changed gnutella_node_t n  )  [static]
 

void node_fire_node_info_changed gnutella_node_t n  )  [static]
 

void node_fire_node_removed gnutella_node_t n  )  [static]
 

void node_flushq struct gnutella_node n  ) 
 

Called by queue when it's not empty and it went through the service routine and yet has more data enqueued.

void node_free_info gnet_node_info_t info  ) 
 

Frees the gnet_node_info_t data returned by node_get_info.

gnet_node_info_t* node_get_info const gnet_node_t  n  ) 
 

Fetches information about a given node.

The returned information must be freed manually by the caller using the node_free_info call.

O(1): Since the gnet_node_t is actually a pointer to the gnutella_node struct, this call is O(1). It would be safer to have gnet_node be an index in a list or a number, but depending on the underlying container structure of sl_nodes, that would have O(log(n)) (balanced tree) or O(n) (list) runtime.

void node_get_status const gnet_node_t  n,
gnet_node_status_t status
 

Fetch node status for the GUI display.

const gchar* node_gnet_addr const gnutella_node_t n  ) 
 

Returns:
the advertised Gnutella ip:port of a node

void node_got_bye struct gnutella_node n  )  [static]
 

Received a Bye message from remote node.

gint node_gtkg_cmp const void *  np1,
const void *  np2
[static]
 

qsort() callback for sorting GTKG nodes at the front.

gboolean node_host_is_connected const host_addr_t  addr,
guint16  port
 

Are we directly connected to that host?

void node_ht_connected_nodes_add const host_addr_t  addr,
guint16  port
[static]
 

Add host to the hash table host cache.

gnet_host_t* node_ht_connected_nodes_find const host_addr_t  addr,
guint16  port
[static]
 

Check whether we already have the host.

gboolean node_ht_connected_nodes_has const host_addr_t  addr,
guint16  port
[static]
 

Check whether we already have the host.

void node_ht_connected_nodes_remove const host_addr_t  addr,
guint16  port
[static]
 

Remove host from the hash table host cache.

void node_http_proxies_add gchar *  buf,
gint *  retval,
gpointer  unused_arg,
guint32  unused_flags
 

HTTP status callback.

If we are still firewalled and have push-proxies, let the downloader know about them via the X-Push-Proxy header.

void node_init void   ) 
 

Network init.

void node_init_outgoing struct gnutella_node n  ) 
 

Called when asynchronous connection to an outgoing node is established.

enum node_bad node_is_bad struct gnutella_node n  )  [static]
 

Check whether node has been identified as having a bad IP or vendor string.

Returns:
NODE_BAD_OK if node is OK, the reason why the node is bad otherwise.
Note:
when we're low on pongs, we never refuse a connection, so this routine always returns NODE_BAD_OK.

gboolean node_is_connected const host_addr_t  addr,
guint16  port,
gboolean  incoming
 

Is there a node connected with this IP/port?

The port is tested only when `incoming' is FALSE, i.e. we allow only one incoming connection per IP, even when there are several instances, all on different ports.

void node_is_now_connected struct gnutella_node n  )  [static]
 

Called when we know that we're connected to the node, at the end of the handshaking (both for incoming and outgoing connections).

guint node_keep_missing void   ) 
 

Amount of node connections we would like to keep.

Returns:
0 if none.

guint node_leaves_missing void   ) 
 

Amount of leaves we're missing (0 if not in ultra mode).

void node_mark_bad_vendor struct gnutella_node n  ) 
 

Gives a specific vendor a bad mark.

If a vendor + version gets to many marks, we won't try to connect to it anymore.

guint node_missing void   ) 
 

Amount of node connections we would like to have.

Returns:
0 if none.

guint node_outdegree void   ) 
 

Returns:
this node's outdegree, i.e. the maximum amount of peer connections that we can support.

void node_parse struct gnutella_node node  )  [static]
 

Processing of messages.

Attention:
NB: callers of this routine must not use the node structure upon return, since we may invalidate that node during the processing.

void node_post_init void   ) 
 

Post GUI initialization.

void node_process_handshake_ack struct gnutella_node n,
header_t head
[static]
 

This routine is called to process the whole 0.6+ final handshake header acknowledgement we get back after welcoming an incoming node.

void node_process_handshake_header struct gnutella_node n,
header_t head
[static]
 

This routine is called to process a 0.6+ handshake header.

It is either called to process the reply to our sending a 0.6 handshake (outgoing connections) or to parse the initial 0.6 headers (incoming connections).

void node_proxy_add gnutella_node_t n,
const host_addr_t  addr,
guint16  port
 

Add node to our list of push-proxies.

void node_proxy_cancel_all void   ) 
 

Cancel all our known push-proxies.

gboolean node_proxying_add gnutella_node_t n,
gchar *  guid
 

Record that node wants us to be his push proxy.

Returns:
TRUE if we can act as this node's proxy.

void node_proxying_remove gnutella_node_t n,
gboolean  discard
 

Remove push proxy indication for the node, i.e.

we're no longer acting as its push-proxy from now on. If `discard' is true, get rid of the GUID and route information.

GSList* node_push_proxies void   ) 
 

Returns:
list of our push-proxies.

void node_qrt_changed gpointer  query_table  ) 
 

Invoked for nodes when our Query Routing Table changed.

void node_qrt_discard struct gnutella_node n  ) 
 

Invoked when remote sends us a RESET message, making the existing routing table obsolete.

void node_qrt_install struct gnutella_node n,
gpointer  query_table
 

Invoked for ultra nodes to install new Query Routing Table.

void node_qrt_patched struct gnutella_node n,
gpointer  query_table
 

Invoked for ultra nodes when the Query Routing Table of remote node was fully patched (i.e.

we got a new generation).

gchar* node_query_routing_header struct gnutella_node n  )  [static]
 

Returns:
the header string that should be used to advertise our QRP version in the reply to their handshake, as a pointer to static data.

gboolean node_read struct gnutella_node n,
pmsg_t mb
[static]
 

Read data from the message buffer we just received.

Returns:
TRUE whilst we think there is more data to read in the buffer.

void node_real_remove gnutella_node_t n  ) 
 

Physically dispose of node.

void node_recursive_shutdown_v struct gnutella_node n,
const gchar *  where,
const gchar *  reason,
va_list  ap
[static]
 

Called when node_bye() or node_shutdown() is called during the time we're in shutdown mode, processing the messages we might still read from the socket.

void node_remove struct gnutella_node n,
const gchar *  reason,
... 
 

Terminate connection with remote node, but keep structure around for a while, for displaying purposes, and also to prevent the node from being physically reclaimed within this stack frame.

It will be reclaimed on the "idle" stack frame, via node_real_remove().

void node_remove_by_handle gnet_node_t  n  ) 
 

Removes or shuts down the given node.

void node_remove_node_added_listener node_added_listener_t  l  ) 
 

void node_remove_node_flags_changed_listener node_flags_changed_listener_t  l  ) 
 

void node_remove_node_info_changed_listener node_info_changed_listener_t  l  ) 
 

void node_remove_node_removed_listener node_removed_listener_t  l  ) 
 

void node_remove_nodes_by_handle GSList *  node_list  ) 
 

Disconnect from the given list of node handles.

The list may not contain NULL elements or duplicate elements.

gboolean node_remove_useless_leaf void   )  [static]
 

Try to spot a "useless" leaf node.

i.e. one that is either not sharing anything or which is preventing us from sending queries via hops-flow. We remove the ones flow-controlling for the greatest amount of time, or which are not sharing anything, based on the QRP.

Returns:
TRUE if we were able to remove one connection.

gboolean node_remove_worst gboolean  non_local  ) 
 

Removes the node with the worst stats, considering the number of weird, bad and duplicate packets.

If `non_local' is TRUE, we're removing this node because it is not a local node, and we're having a connection from the local LAN. Otherwise, we're just removing a bad node (the BYE code is different).

gboolean node_reserve_slot struct gnutella_node n  )  [static]
 

When we only have "reserve_gtkg_nodes" percent slots left, make sure the connecting node is a GTKG node or refuse the connection.

Returns:
TRUE if we should reserve the slot for GTKG, i.e. refuse `n'.

void node_rx_got_eof gpointer  o  )  [static]
 

void node_rx_inflate_error gpointer  o,
const gchar *  reason,
... 
[static]
 

void node_rx_read_error gpointer  o,
const gchar *  reason,
... 
[static]
 

void node_send_error struct gnutella_node n,
int  code,
const gchar *  msg,
... 
[static]
 

Send error message to remote node.

void node_send_patch_step struct gnutella_node n  )  [static]
 

Incrementally send the routing table patch to our Ultrapeer.

void node_send_qrt struct gnutella_node n,
gpointer  query_table
[static]
 

Initiate sending of the query routing table.

void node_sent_ttl0 struct gnutella_node n  ) 
 

Called when a node sends a message with TTL=0.

Returns:
TRUE if node was removed (due to a duplicate bye, probably), FALSE otherwise.

void node_set_current_peermode node_peer_t  mode  )  [static]
 

Called from the node timer when the current peermode has changed.

We call this "asynchronously" because the current peermode can change during handshaking, when we accept the guidance of the remote ultrapeer to become a leaf node.

void node_set_hops_flow gnutella_node_t n,
guint8  hops
 

Called when a vendor-specific "hops-flow" message was received to tell us to update the hops-flow counter for the connection: no query whose hop count is greater or equal to the specified `hops' should be sent to that node.

void node_set_online_mode gboolean  on  ) 
 

Whether they want to be "online" within Gnutella or not.

void node_set_socket_rx_size gint  rx_size  ) 
 

Change the socket RX buffer size for all the currently connected nodes.

void node_set_vendor gnutella_node_t n,
const gchar *  vendor
 

Record vendor name (user-agent string).

Parameters:
n The gnutella node.
vendor The payload of the User-Agent header; the assumed character encoding is ISO-8859-1.

void node_shutdown struct gnutella_node n,
const gchar *  reason,
... 
 

Stop sending data to node, but keep reading buffered data from it, until we hit a Bye packet or EOF.

In that mode, we don't relay Queries we may read, but replies and pushes are still routed back to other nodes.

This is mostly called when a fatal write error happens, but we want to see whether the node did not send us a Bye we haven't read yet.

void node_shutdown_mode struct gnutella_node n,
guint32  delay
[static]
 

Enter shutdown mode: prevent further writes, drop read broadcasted messages, and make sure we flush the buffers at the fastest possible speed.

void node_shutdown_v struct gnutella_node n,
const gchar *  reason,
va_list  args
[static]
 

The vectorized version of node_shutdown().

void node_slow_timer time_t  now  ) 
 

Low frequency node timer.

void node_timer time_t  now  ) 
 

Periodic node heartbeat timer.

void node_tsync_tcp gnutella_node_t n  )  [static]
 

Sent "probe" time sync via TCP to the specified node to compute the RTT...

void node_tsync_udp cqueue_t unused_cq,
gpointer  obj
[static]
 

Send "Time Sync" via UDP if we know the remote IP:port, via TCP otherwise.

void node_tx_enter_flowc struct gnutella_node n  ) 
 

Called by message queue when the node enters TX flow control.

void node_tx_enter_warnzone struct gnutella_node n  ) 
 

Called by message queue when the node enters the warn zone.

void node_tx_eof_remove gpointer  o,
const gchar *  reason,
... 
[static]
 

void node_tx_eof_shutdown gpointer  o,
const gchar *  reason,
... 
[static]
 

void node_tx_leave_flowc struct gnutella_node n  ) 
 

Called by message queue when the node leaves TX flow control.

void node_tx_leave_warnzone struct gnutella_node n  ) 
 

Called by message queue when the node leaves the warn zone.

void node_tx_service struct gnutella_node n,
gboolean  unused_on
 

Called when the queue service routine is switched ON/OFF.

void node_tx_shutdown gpointer  o,
const gchar *  reason,
... 
[static]
 

void node_tx_swift_changed struct gnutella_node n  ) 
 

Called by message queue when swift mode changes.

void node_tx_unflushq gpointer  o  )  [static]
 

void node_type_count_dec struct gnutella_node n  )  [static]
 

Decrement the proper node count property, depending on the peermode.

gint node_ua_cmp const void *  np1,
const void *  np2
[static]
 

qsort() callback for sorting nodes by user-agent.

gnutella_node_t * node_udp_create void   )  [static]
 

Create a "fake" node that is used as a placeholder when processing Gnutella messages received from UDP.

void node_udp_disable void   ) 
 

Disable UDP transmission via pseudo node.

void node_udp_enable void   ) 
 

Enable UDP transmission via pseudo node.

gnutella_node_t* node_udp_get struct gnutella_socket s  )  [static]
 

Get "fake" node after reception of a datagram and return its address.

gnutella_node_t* node_udp_get_addr_port const host_addr_t  addr,
guint16  port
 

Get "fake" node for UDP transmission.

mqueue_t* node_udp_get_outq void   ) 
 

Get the message queue attached to the UDP node.

Returns:
the UDP message queue, or NULL if UDP has been disabled.

void node_udp_gui_remove void   ) 
 

Remove UDP node from the GUI.

void node_udp_gui_show void   ) 
 

Show UDP node in the GUI.

void node_udp_process struct gnutella_socket s  ) 
 

Process incoming Gnutella datagram.

void node_unflushq struct gnutella_node n  ) 
 

Called by queue to disable the flush mode.

void node_update_udp_socket void   ) 
 

This has to be called once the UDP socket (e.g., due to a changed port number) was changed because some internal references have to be updated.

RCSID "$Id:nodes.  c,
v 1.158 2006/02/10 18:55:28 rmanfredi Exp $" 
 

void send_error struct gnutella_socket s,
struct gnutella_node n,
int  code,
const gchar *  msg,
va_list  ap
[static]
 

Send error message to remote end, a node presumably.

Parameters:
s the connected socket (mandatory)
n the node (optional, NULL if not available)
code the error code to report
msg the error message (printf format)
ap variable argument pointer, arguments for the error message

void send_node_error struct gnutella_socket s,
int  code,
const gchar *  msg,
... 
 

Send error message to remote end, a node presumably.

Attention:
NB: We don't need a node to call this routine, only a socket.

void send_proxy_request gnutella_node_t n  )  [static]
 

Request that node becomes our push-proxy.

void string_table_clear GHashTable *  ht  )  [static]
 

Clear hash table whose keys are atoms and values ignored.

void string_table_free GHashTable *  ht  )  [static]
 

Dispose of hash table whose keys are atoms and values ignored.


Variable Documentation

gboolean allow_gnet_connections = FALSE [static]
 

gnutella_node_t* browse_node = NULL [static]
 

gboolean changed
 

guint compressed_leaf_cnt = 0 [static]
 

guint compressed_node_cnt = 0 [static]
 

guint connected_node_cnt = 0 [static]
 

guint32 connected_node_count = 0 [static]
 

GHashTable* ht_connected_nodes = NULL [static]
 

gboolean in_shutdown = FALSE [static]
 

guint32 leaf_to_up_switch = NODE_AUTO_SWITCH_MIN [static]
 

node_peer_t new
 

const gchar no_reason[] = "<no reason>" [static]
 

struct gnutella_node* node_added
 

For use by node_added_hook_list hooks, since we can't add a parameter at list invoke time.

GHookList node_added_hook_list
 

listeners_t node_added_listeners = NULL [static]
 

time_t node_error_cleanup_timer = 6 * 3600 [static]
 

6 hours

int node_error_threshold = 6 [static]
 

This requires an average uptime of 1 hour for an ultrapeer.

listeners_t node_flags_changed_listeners = NULL [static]
 

idtable_t* node_handle_map = NULL [static]
 

guint32 node_id = 1 [static]
 

Reserve 0 for the local node.

listeners_t node_info_changed_listeners = NULL [static]
 

struct io_error node_io_error [static]
 

Initial value:

 {
    err_line_too_long,
    err_header_error_tell,
    err_header_error,
    err_input_exception,
    err_input_buffer_full,
    err_header_read_error,
    err_header_read_eof,
    err_header_extra_data,
}

listeners_t node_removed_listeners = NULL [static]
 

struct rx_inflate_cb node_rx_inflate_cb [static]
 

Initial value:

 {
    node_add_rx_inflated,       
    node_rx_inflate_error,      
}

struct rx_link_cb node_rx_link_cb [static]
 

Initial value:

 {
    node_add_rx_given,          
    node_rx_read_error,         
    node_rx_got_eof,            
}

struct tx_deflate_cb node_tx_deflate_cb [static]
 

Initial value:

 {
    node_add_tx_deflated,       
    node_tx_shutdown,           
}

struct tx_dgram_cb node_tx_dgram_cb [static]
 

Initial value:

 {
    node_add_tx_written,        
}

struct tx_link_cb node_tx_link_cb [static]
 

Initial value:

 {
    node_add_tx_written,        
    node_tx_eof_remove,         
    node_tx_eof_shutdown,       
    node_tx_unflushq,           
}

GHashTable* nodes_by_id = NULL [static]
 

struct { ... } peermode [static]
 

Structure used for asynchronous reaction to peer mode changes.

gint pending_byes = 0 [static]
 

query_hashvec_t* query_hashvec = NULL [static]
 

guint32 shutdown_nodes = 0 [static]
 

GSList* sl_nodes = NULL [static]
 

GSList* sl_nodes_without_broken_gtkg = NULL [static]
 

GSList* sl_proxies = NULL [static]
 

gchar* start_rfc822_date = NULL
 

RFC822 format of start_time.

gpointer tcp_crawls = NULL [static]
 

gpointer udp_crawls = NULL [static]
 

gnutella_node_t* udp_node = NULL [static]
 

GHashTable* unstable_servent = NULL [static]
 

GSList* unstable_servents = NULL [static]
 


Generated on Sun Feb 12 10:50:05 2006 for Gtk-Gnutella by doxygen 1.3.6