00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00039 #ifndef _core_sockets_h_
00040 #define _core_sockets_h_
00041
00042 #include "common.h"
00043
00044 #include "tls_common.h"
00045
00046 #include "if/core/wrap.h"
00047 #include "if/core/sockets.h"
00048
00049 #include "lib/inputevt.h"
00050
00051 enum socket_tls_stage {
00052 SOCK_TLS_NONE = 0,
00053 SOCK_TLS_INITIALIZED = 1,
00054 SOCK_TLS_ESTABLISHED = 2
00055 };
00056
00057 struct socket_tls_ctx {
00058 tls_context_t ctx;
00059 gboolean enabled;
00060 enum socket_tls_stage stage;
00061 size_t snarf;
00063 inputevt_cond_t cb_cond;
00064 inputevt_handler_t cb_handler;
00065 gpointer cb_data;
00066 };
00067
00068 struct sockaddr;
00069
00070
00071
00072
00073
00074 enum socket_direction {
00075 SOCK_CONN_INCOMING,
00076 SOCK_CONN_OUTGOING,
00077 SOCK_CONN_LISTENING,
00078 SOCK_CONN_PROXY_OUTGOING
00079 };
00080
00085 enum socket_type {
00086 SOCK_TYPE_UNKNOWN = 0,
00087 SOCK_TYPE_CONTROL,
00088 SOCK_TYPE_DOWNLOAD,
00089 SOCK_TYPE_UPLOAD,
00090 SOCK_TYPE_HTTP,
00091 SOCK_TYPE_SHELL,
00092 SOCK_TYPE_CONNBACK,
00093 SOCK_TYPE_PPROXY,
00094 SOCK_TYPE_DESTROYING,
00095 SOCK_TYPE_UDP
00096 };
00097
00098 typedef enum {
00099 SOCKET_MAGIC = 0x1fb7ddeb
00100 } socket_magic_t;
00101
00102 struct gnutella_socket {
00103 socket_magic_t magic;
00104 gint file_desc;
00105 guint32 flags;
00106 guint gdk_tag;
00108 enum socket_direction direction;
00109 enum socket_type type;
00110 enum net_type net;
00111 gboolean omit_token;
00112 gboolean corked;
00113 gboolean was_shutdown;
00114 gint adns;
00115 const gchar *adns_msg;
00117 host_addr_t addr;
00118 guint16 port;
00120 guint16 local_port;
00122 time_t last_update;
00124 struct wrap_io wio;
00126 #ifdef HAS_GNUTLS
00127 struct socket_tls_ctx tls;
00128 #endif
00129
00130 union {
00131 struct gnutella_node *node;
00132 struct download *download;
00133 struct upload *upload;
00134 struct pproxy *pproxy;
00135 struct cproxy *cproxy;
00136 gpointer handle;
00137 } resource;
00138
00139 struct getline *getline;
00141 size_t pos;
00142 size_t buf_size;
00143 gchar *buf;
00144 };
00145
00146 static inline void
00147 socket_check(const struct gnutella_socket * const s)
00148 {
00149 g_assert(s);
00150 g_assert(SOCKET_MAGIC == s->magic);
00151 }
00152
00153
00154
00155
00156
00157 extern struct gnutella_socket *s_tcp_listen;
00158 extern struct gnutella_socket *s_tcp_listen6;
00159 extern struct gnutella_socket *s_udp_listen;
00160 extern struct gnutella_socket *s_udp_listen6;
00161 extern struct gnutella_socket *s_local_listen;
00162
00163
00168 static inline gboolean
00169 socket_with_tls(const struct gnutella_socket *s)
00170 #ifdef HAS_GNUTLS
00171 {
00172 return s->tls.enabled && s->tls.stage >= SOCK_TLS_INITIALIZED;
00173 }
00174 #else
00175 {
00176 (void) s;
00177 return FALSE;
00178 }
00179 #endif
00180
00181 static inline gboolean
00182 socket_uses_tls(const struct gnutella_socket *s)
00183 #ifdef HAS_GNUTLS
00184 {
00185 return s->tls.enabled && s->tls.stage >= SOCK_TLS_ESTABLISHED;
00186 }
00187 #else
00188 {
00189 (void) s;
00190 return FALSE;
00191 }
00192 #endif
00193
00194 static inline gboolean
00195 sock_is_corked(const struct gnutella_socket *s)
00196 {
00197 return s->corked;
00198 }
00199
00204 static inline gboolean
00205 udp_active(void)
00206 {
00207 return NULL != s_udp_listen || NULL != s_udp_listen6;
00208 }
00209
00210 static inline guint16
00211 socket_listen_port(void)
00212 {
00213 if (s_tcp_listen)
00214 return s_tcp_listen->local_port;
00215 if (s_tcp_listen6)
00216 return s_tcp_listen6->local_port;
00217 return 0;
00218 }
00219
00220
00221
00222
00223
00224 void socket_init(void);
00225 void socket_register_fd_reclaimer(reclaim_fd_t callback);
00226 void socket_eof(struct gnutella_socket *s);
00227 void socket_free_null(struct gnutella_socket **s_ptr);
00228 struct gnutella_socket *socket_connect(const host_addr_t, guint16,
00229 enum socket_type, guint32 flags);
00230 struct gnutella_socket *socket_connect_by_name(
00231 const gchar *host, guint16, enum socket_type, guint32 flags);
00232 struct gnutella_socket *socket_tcp_listen(const host_addr_t, guint16);
00233 struct gnutella_socket *socket_udp_listen(const host_addr_t, guint16);
00234 struct gnutella_socket *socket_local_listen(const gchar *pathname);
00235
00236 void socket_evt_set(struct gnutella_socket *s,
00237 inputevt_cond_t cond, inputevt_handler_t handler, gpointer data);
00238 void socket_evt_clear(struct gnutella_socket *s);
00239
00240 void sock_cork(struct gnutella_socket *s, gboolean on);
00241 void sock_send_buf(struct gnutella_socket *s, gint size, gboolean shrink);
00242 void sock_recv_buf(struct gnutella_socket *s, gint size, gboolean shrink);
00243 void sock_nodelay(struct gnutella_socket *s, gboolean on);
00244 void sock_tx_shutdown(struct gnutella_socket *s);
00245 void socket_tos_default(const struct gnutella_socket *s);
00246 void socket_tos_throughput(const struct gnutella_socket *s);
00247 void socket_tos_lowdelay(const struct gnutella_socket *s);
00248 void socket_tos_normal(const struct gnutella_socket *s);
00249 gboolean socket_bad_hostname(struct gnutella_socket *s);
00250 void socket_disable_token(struct gnutella_socket *s);
00251 gboolean socket_omit_token(struct gnutella_socket *s);
00252 void socket_set_bind_address(const host_addr_t addr);
00253 gint socket_evt_fd(struct gnutella_socket *s);
00254 gboolean socket_is_local(const struct gnutella_socket *s);
00255
00256 void socket_timer(time_t now);
00257 void socket_shutdown(void);
00258
00259 ssize_t safe_readv(wrap_io_t *wio, struct iovec *iov, gint iovcnt);
00260 ssize_t safe_readv_fd(gint fd, struct iovec *iov, gint iovcnt);
00261 ssize_t safe_writev(wrap_io_t *wio, const struct iovec *iov, gint iovcnt);
00262 ssize_t safe_writev_fd(gint fd, const struct iovec *iov, gint iovcnt);
00263
00264 #endif
00265
00266