Comment changes.
[silc.git] / lib / silcutil / silcnet.h
1 /*
2
3   silcnet.h
4
5   Author: Pekka Riikonen <priikone@silcnet.org>
6
7   Copyright (C) 1997 - 2006 Pekka Riikonen
8
9   This program is free software; you can redistribute it and/or modify
10   it under the terms of the GNU General Public License as published by
11   the Free Software Foundation; version 2 of the License.
12
13   This program is distributed in the hope that it will be useful,
14   but WITHOUT ANY WARRANTY; without even the implied warranty of
15   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16   GNU General Public License for more details.
17
18 */
19
20 /****h* silcutil/SILC Net Interface
21  *
22  * DESCRIPTION
23  *
24  * SILC Net API provides various network routines for applications. It
25  * can be used to create TCP/IP and UDP/IP connections and listeners.
26  * Various utility functions for resolving various information is also
27  * provided.
28  *
29  * On WIN32 systems the SILC Net API must initialized by calling the
30  * silc_net_win32_init and uninitialized when the application ends by
31  * calling the silc_net_win32_uninit function. The initializing must be
32  * done in order to assure that the SILC Net API works correctly.
33  *
34  ***/
35
36 #ifndef SILCNET_H
37 #define SILCNET_H
38
39 /* Prototypes */
40
41 /****s* silcutil/SilcNetAPI/SilcNetListener
42  *
43  * NAME
44  *
45  *    typedef struct SilcNetListenerStruct *SilcNetListener;
46  *
47  * DESCRIPTION
48  *
49  *    The network listenr context.  This context is created with the
50  *    silc_net_create_listener function and destroyed with
51  *    silc_net_close_listener function.
52  *
53  ***/
54 typedef struct SilcNetListenerStruct *SilcNetListener;
55
56 /****d* silcutil/SilcNetAPI/SilcNetStatus
57  *
58  * NAME
59  *
60  *    typedef enum { ... } SilcNetStatus;
61  *
62  * DESCRIPTION
63  *
64  *    Status to indicate the result of the network operation creation.  This
65  *    type is returned in the SilcNetCallback callback function.
66  *
67  * SOURCE
68  */
69 typedef enum {
70   SILC_NET_OK,                         /* Everything Ok */
71   SILC_NET_UNKNOWN_IP,                 /* Unknown IP address */
72   SILC_NET_UNKNOWN_HOST,               /* Unknown hostname */
73   SILC_NET_HOST_UNREACHABLE,           /* Destination unreachable */
74   SILC_NET_CONNECTION_REFUSED,         /* Connection refused */
75   SILC_NET_CONNECTION_TIMEOUT,         /* Connection timedout */
76   SILC_NET_NO_MEMORY,                  /* System out of memory */
77   SILC_NET_ERROR,                      /* Unknown error */
78 } SilcNetStatus;
79 /***/
80
81 /****f* silcutil/SilcNetAPI/SilcNetCallback
82  *
83  * SYNOPSIS
84  *
85  *    typedef void (*SilcNetCallback)(SilcNetStatus status,
86  *                                    SilcStream stream, void *context);
87  *
88  * DESCRIPTION
89  *
90  *    A callback of this type is returned by silc_net_tcp_create_listener
91  *    and silc_net_tcp_connect functions.  For silc_net_tcp_create_listener
92  *    this callback means that new incoming connection was accepted, and the
93  *    `stream' is the socket stream representing the socket connection.
94  *
95  *    For silc_net_tcp_connect this means that we have connected to the
96  *    remote host and the `stream' is the socket stream for the socket
97  *    connection.  The SILC Stream API (such as silc_stream_read, etc.) can
98  *    be used to read and write to the stream.  The created stream is socket
99  *    stream so various SilcSocketStream API functions can be used with
100  *    the `stream'.
101  *
102  ***/
103 typedef void (*SilcNetCallback)(SilcNetStatus status,
104                                 SilcStream stream, void *context);
105
106 /****f* silcutil/SilcNetAPI/silc_net_tcp_create_listener
107  *
108  * SYNOPSIS
109  *
110  *    SilcNetListener
111  *    silc_net_tcp_create_listener(const char **local_ip_addr,
112  *                                 SilcUInt32 local_ip_count, int port,
113  *                                 SilcBool lookup, SilcBool require_fqdn,
114  *                                 SilcSchedule schedule,
115  *                                 SilcNetCallback callback, void *context);
116  *
117  * DESCRIPTION
118  *
119  *    This function creates TCP listener.  This is used to create network
120  *    listener for incoming connections, and `callback' will be called
121  *    everytime new connection is received.  If `local_ip_addr' is NULL any
122  *    address is used.  If provided it can be used bind the listener to
123  *    `local_ip_count' many IP addresses provided in `local_ip_addr' table.
124  *    On success returns the SilcNetListener context, or NULL on error.
125  *    If `require_fqdn' is TRUE the listener will require that the incoming
126  *    connection has FQDN to be able to connect.  If the `lookup' is TRUE
127  *    then the incoming connection hostname will be resolved.
128  *
129  ***/
130 SilcNetListener
131 silc_net_tcp_create_listener(const char **local_ip_addr,
132                              SilcUInt32 local_ip_count, int port,
133                              SilcBool lookup, SilcBool require_fqdn,
134                              SilcSchedule schedule,
135                              SilcNetCallback callback, void *context);
136
137 /****f* silcutil/SilcNetAPI/silc_net_close_listener
138  *
139  * SYNOPSIS
140  *
141  *    void silc_net_close_listener(SilcNetListener listener);
142  *
143  * DESCRIPTION
144  *
145  *    Closes the network listener indicated by `listener'.
146  *
147  ***/
148 void silc_net_close_listener(SilcNetListener listener);
149
150 /****f* silcutil/SilcNetAPI/silc_net_tcp_connect
151  *
152  * SYNOPSIS
153  *
154  *    SilcAsyncOperation silc_net_tcp_connect(const char *local_ip_addr,
155  *                                            const char *remote_ip_addr,
156  *                                            int remote_port,
157  *                                            SilcSchedule schedule,
158  *                                            SilcNetCallback callback,
159  *                                            void *context);
160  *
161  * DESCRIPTION
162  *
163  *    Creates TCP/IP connection to the remote host indicated by `remote_host'
164  *    which may be hostname or IP address, on the port indicated by
165  *    `remote_port'.  If the `local_ip_addr' is provided the local host is
166  *    bound to that address before creating the connection.  This is
167  *    asynchronous call, and this function returns before the connection is
168  *    actually established.  The `callback' will be called after the
169  *    connection is created to deliver the SilcStream for the created
170  *    connection.  This function supports IPv6 if the platform supports it.
171  *
172  *    The returned SilcAsyncOperation context can be used to control the
173  *    asynchronous connecting, such as to abort it.  If it is aborted
174  *    using silc_async_abort the `callback' will not be called.  If NULL
175  *    is returned the operation cannot be aborted.
176  *
177  */
178 SilcAsyncOperation silc_net_tcp_connect(const char *local_ip_addr,
179                                         const char *remote_ip_addr,
180                                         int remote_port,
181                                         SilcSchedule schedule,
182                                         SilcNetCallback callback,
183                                         void *context);
184
185 /****f* silcutil/SilcNetAPI/silc_net_udp_connect
186  *
187  * SYNOPSIS
188  *
189  *    SilcStream
190  *    silc_net_udp_connect(const char *local_ip_addr, int local_port,
191  *                         const char *remote_ip_addr, int remote_port,
192  *                         SilcSchedule schedule);
193  *
194  * DESCRIPTION
195  *
196  *    This function creates UDP stream.  The UDP stream is bound to the
197  *    `local_ip_addr' if it is specified.  If `local_port' is non-zero the
198  *    stream is bound to that port.  If the `remote_ip_addr' and `remote_port'
199  *    is also provided, packets may be sent to that address using
200  *    silc_stream_write function and packets may be received using
201  *    silc_stream_read function.
202  *
203  *    If the remote address is not provided then packets may only be received
204  *    by using silc_net_udp_receive and sent only by using the function
205  *    silc_net_udp_send.
206  *
207  *    To receive packets the silc_stream_set_notifier must be called for the
208  *    returned SilcStream.  The packets are always received in the notifier
209  *    callback when the SILC_STREAM_CAN_READ is returned to the callback
210  *    To read the packet use silc_stream_read if the remote address was
211  *    provided, and silc_net_udp_receive if it was not.
212  *
213  *    Supports IPv6 if the platform supports it.
214  *
215  * EXAMPLE
216  *
217  *    SilcStream udpstream;
218  *
219  *    // Create UDP stream and prepare to receive packets
220  *    udpstream = silc_net_udp_connect("10.2.1.7", 5000,
221  *                                     "10.2.1.100, 5000, schedule);
222  *    silc_stream_set_notifier(udpstream, schedule, receive_callback, context);
223  *
224  *    // Send packet to remote host
225  *    silc_stream_write(udpstream, data, data_len);
226  *
227  *    Create UDP listener:
228  *
229  *    udpstream = silc_net_udp_connect("0.0.0.0", 500, NULL, 0, schedule);
230  *    silc_stream_set_notifier(udpstream, schedule, receive_callback, context);
231  *
232  ***/
233 SilcStream silc_net_udp_connect(const char *local_ip_addr, int local_port,
234                                 const char *remote_ip_addr, int remote_port,
235                                 SilcSchedule schedule);
236
237 /****f* silcutil/SilcNetAPI/silc_net_udp_receive
238  *
239  * SYNOPSIS
240  *
241  *    int
242  *    silc_net_udp_receive(SilcStream stream, char *remote_ip_addr,
243  *                         SilcUInt32 remote_ip_addr_size, int *remote_port,
244  *                         unsigned char *ret_data, SilcUInt32 data_size)
245  *
246  * DESCRIPTION
247  *
248  *    Receive a UDP packet from the `stream'.  The IP address and port of
249  *    the sender is returned into `remote_ip_addr' buffer and `remote_port'
250  *    pointer.  The packet data is returned into the `ret_data' buffer.
251  *
252  *    Returns the length of the packet, or -1 on error or 0 in case of EOF.
253  *
254  ***/
255 int silc_net_udp_receive(SilcStream stream, char *remote_ip_addr,
256                          SilcUInt32 remote_ip_addr_size, int *remote_port,
257                          unsigned char *ret_data, SilcUInt32 data_size);
258
259 /****f* silcutil/SilcNetAPI/silc_net_udp_send
260  *
261  * SYNOPSIS
262  *
263  *    void silc_net_udp_send(SilcStream stream,
264  *                           const char *remote_ip_addr, int remote_port,
265  *                           const unsigned char *data, SilcUInt32 data_len);
266  *
267  * DESCRIPTION
268  *
269  *    Sends an UDP packet to remote host `remote_ip_addr' on `remote_port'.
270  *    This may be used with UDP streams that are not connected to any
271  *    specific remote host.  With those stream silc_stream_write cannot be
272  *    used.  In those cases, this function must be used.  This may also be
273  *    used even if the stream is connected.
274  *
275  *    This function always succeeds, however there is no guarantee that the
276  *    packet is delivered, as UDP is unreliable transport protocol.
277  *
278  ***/
279 void silc_net_udp_send(SilcStream stream,
280                        const char *remote_ip_addr, int remote_port,
281                        const unsigned char *data, SilcUInt32 data_len);
282
283 /****f* silcutil/SilcNetAPI/silc_net_close_connection
284  *
285  * SYNOPSIS
286  *
287  *    void silc_net_close_connection(int sock);
288  *
289  * DESCRIPTION
290  *
291  *    Closes the connection by closing the socket connection.
292  *
293  ***/
294 void silc_net_close_connection(int sock);
295
296 /****f* silcutil/SilcNetAPI/silc_net_accept_connection
297  *
298  * SYNOPSIS
299  *
300  *    int silc_net_accept_connection(int sock);
301  *
302  * DESCRIPTION
303  *
304  *    Accepts a connection from a particular socket.
305  *
306  ***/
307 int silc_net_accept_connection(int sock);
308
309 /****f* silcutil/SilcNetAPI/silc_net_set_socket_nonblock
310  *
311  * SYNOPSIS
312  *
313  *    int silc_net_set_socket_nonblock(int sock);
314  *
315  * DESCRIPTION
316  *
317  *    Sets the socket to non-blocking mode.
318  *
319  ***/
320 int silc_net_set_socket_nonblock(int sock);
321
322 /****f* silcutil/SilcNetAPI/silc_net_set_socket_opt
323  *
324  * SYNOPSIS
325  *
326  *    int silc_net_set_socket_opt(int sock, int level, int option, int on);
327  *
328  * DESCRIPTION
329  *
330  *    Sets a option for a socket.  This function can be used to set
331  *    various options for the socket.  Some of the options might be
332  *    system specific.
333  *
334  ***/
335 int silc_net_set_socket_opt(int sock, int level, int option, int on);
336
337 /****f* silcutil/SilcNetAPI/silc_net_get_socket_opt
338  *
339  * SYNOPSIS
340  *
341  *    int silc_net_get_socket_opt(int sock, int level, int option,
342  *                                void *optval, int *opt_len);
343  *
344  * DESCRIPTION
345  *
346  *    Return socket options to the `optval' and `opt_len'.
347  *
348  ***/
349 int silc_net_get_socket_opt(int sock, int level, int option,
350                             void *optval, int *opt_len);
351
352 /****f* silcutil/SilcNetAPI/silc_net_is_ip4
353  *
354  * SYNOPSIS
355  *
356  *    SilcBool silc_net_is_ip4(const char *addr);
357  *
358  * DESCRIPTION
359  *
360  *    Checks whether IP address sent as argument is valid IPv4 address.
361  *
362  ***/
363 SilcBool silc_net_is_ip4(const char *addr);
364
365 /****f* silcutil/SilcNetAPI/silc_net_is_ip6
366  *
367  * SYNOPSIS
368  *
369  *    SilcBool silc_net_is_ip6(const char *addr);
370  *
371  * DESCRIPTION
372  *
373  *    Checks whether IP address sent as argument is valid IPv6 address.
374  *
375  ***/
376 SilcBool silc_net_is_ip6(const char *addr);
377
378 /****f* silcutil/SilcNetAPI/silc_net_is_ip
379  *
380  * SYNOPSIS
381  *
382  *    SilcBool silc_net_is_ip(const char *addr);
383  *
384  * DESCRIPTION
385  *
386  *    Checks whether IP address sent as argument is valid IP address.
387  *    This supports both IPv4 and IPv6 addresses.
388  *
389  ***/
390 SilcBool silc_net_is_ip(const char *addr);
391
392 /****f* silcutil/SilcNetAPI/silc_net_addr2bin
393  *
394  * SYNOPSIS
395  *
396  *    SilcBool silc_net_addr2bin(const char *addr, void *bin, SilcUInt32 bin_len);
397  *
398  * DESCRIPTION
399  *
400  *    Converts the IP number string from numbers-and-dots notation to
401  *    binary form in network byte order.  The address can be either
402  *    IPv4 or IPv6 address.
403  *
404  ***/
405 SilcBool silc_net_addr2bin(const char *addr, void *bin, SilcUInt32 bin_len);
406
407 /****f* silcutil/SilcNetAPI/SilcNetResolveCallback
408  *
409  * SYNOPSIS
410  *
411  *    typedef void (*SilcNetResolveCallback)(const char *result,
412  *                                           void *context);
413  *
414  * DESCRIPTION
415  *
416  *    A callback function of this type is called after the asynchronous
417  *    resolving operation has been completed.  This callback is used
418  *    when asynchronously resolving IP addresses and hostnames.
419  *
420  ***/
421 typedef void (*SilcNetResolveCallback)(const char *result, void *context);
422
423 /****f* silcutil/SilcNetAPI/silc_net_gethostbyname
424  *
425  * SYNOPSIS
426  *
427  *    SilcBool silc_net_gethostbyname(const char *name, SilcBool prefer_ipv6,
428  *                                char *address, SilcUInt32 address_len);
429  *
430  * DESCRIPTION
431  *
432  *    Resolves the IP address of the hostname indicated by the `name'.
433  *    This returns TRUE and the IP address of the host to the `address'
434  *    buffer, or FALSE if the address could not be resolved.  This is
435  *    synchronous function and will block the calling process.  If the
436  *    `prefer_ipv6' is TRUE then this will return IPv6 address if it
437  *    finds.  If FALSE if returns IPv4 address even if it found IPv6
438  *    address also.
439  *
440  ***/
441 SilcBool silc_net_gethostbyname(const char *name, SilcBool prefer_ipv6,
442                                 char *address, SilcUInt32 address_len);
443
444 /****f* silcutil/SilcNetAPI/silc_net_gethostbyname_async
445  *
446  * SYNOPSIS
447  *
448  *    void silc_net_gethostbyname_async(const char *name,
449  *                                      SilcBool prefer_ipv6,
450  *                                      SilcSchedule schedule,
451  *                                      SilcNetResolveCallback completion,
452  *                                      void *context)
453  *
454  * DESCRIPTION
455  *
456  *    Asynchronously resolves the IP address of the hostname indicated
457  *    by the `name'.  This function returns immediately, and the
458  *    `completion' callback will be called after the resolving is
459  *    completed.
460  *
461  *    If the `prefer_ipv6' is TRUE then this will return IPv6 address if it
462  *    finds.  If FALSE if returns IPv4 address even if it found IPv6
463  *    address also.
464  *
465  ***/
466 void silc_net_gethostbyname_async(const char *name,
467                                   SilcBool prefer_ipv6,
468                                   SilcSchedule schedule,
469                                   SilcNetResolveCallback completion,
470                                   void *context);
471
472 /****f* silcutil/SilcNetAPI/silc_net_gethostbyaddr
473  *
474  * SYNOPSIS
475  *
476  *   SilcBool silc_net_gethostbyaddr(const char *addr, char *name,
477  *                               SilcUInt32 name_len);
478  *
479  * DESCRIPTION
480  *
481  *    Resolves the hostname for the IP address indicated by the `addr'
482  *    This returns TRUE and the resolved hostname to the `name' buffer,
483  *    or FALSE on error. The `addr' may be either IPv4 or IPv6 address.
484  *    This is synchronous function and will block the calling process.
485  *
486  ***/
487 SilcBool silc_net_gethostbyaddr(const char *addr, char *name,
488                                 SilcUInt32 name_len);
489
490 /****f* silcutil/SilcNetAPI/silc_net_gethostbyaddr_async
491  *
492  * SYNOPSIS
493  *
494  *    void silc_net_gethostbyaddr_async(const char *addr,
495  *                                      SilcSchedule schedule,
496  *                                      SilcNetResolveCallback completion,
497  *                                      void *context)
498  *
499  * DESCRIPTION
500  *
501  *    Asynchronously resolves the hostname for the IP address indicated
502  *    by the `addr'.  This function returns immediately, and the
503  *    `completion' callback will be called after the resolving is
504  *    completed.
505  *
506  ***/
507 void silc_net_gethostbyaddr_async(const char *addr,
508                                   SilcSchedule schedule,
509                                   SilcNetResolveCallback completion,
510                                   void *context);
511
512 /****f* silcutil/SilcNetAPI/silc_net_check_host_by_sock
513  *
514  * SYNOPSIS
515  *
516  *    SilcBool silc_net_check_host_by_sock(int sock, char **hostname,
517  *                                         char **ip);
518  *
519  * DESCRIPTION
520  *
521  *    Performs lookups for remote name and IP address. This peforms reverse
522  *    lookup as well to verify that the IP has FQDN.
523  *
524  ***/
525 SilcBool silc_net_check_host_by_sock(int sock, char **hostname, char **ip);
526
527 /****f* silcutil/SilcNetAPI/silc_net_check_local_by_sock
528  *
529  * SYNOPSIS
530  *
531  *    SilcBool silc_net_check_local_by_sock(int sock, char **hostname,
532  *                                          char **ip);
533  *
534  * DESCRIPTION
535  *
536  *    Performs lookups for local name and IP address. This peforms reverse
537  *    lookup as well to verify that the IP has FQDN.
538  *
539  ***/
540 SilcBool silc_net_check_local_by_sock(int sock, char **hostname, char **ip);
541
542 /****f* silcutil/SilcNetAPI/silc_net_get_remote_port
543  *
544  * SYNOPSIS
545  *
546  *    SilcUInt16 silc_net_get_remote_port(int sock);
547  *
548  * DESCRIPTION
549  *
550  *    Return remote port by socket.
551  *
552  ***/
553 SilcUInt16 silc_net_get_remote_port(int sock);
554
555 /****f* silcutil/SilcNetAPI/silc_net_get_local_port
556  *
557  * SYNOPSIS
558  *
559  *    SilcUInt16 silc_net_get_local_port(int sock);
560  *
561  * DESCRIPTION
562  *
563  *    Return local port by socket.
564  *
565  ***/
566 SilcUInt16 silc_net_get_local_port(int sock);
567
568 /****f* silcutil/SilcNetAPI/silc_net_localhost
569  *
570  * SYNOPSIS
571  *
572  *    char *silc_net_localhost(void);
573  *
574  * DESCRIPTION
575  *
576  *    Return name of localhost.  This will also attempt to resolve
577  *    the real hostname by the local host's IP address.  If unsuccessful
578  *    the first found hostname is returned.  The caller must free
579  *    returned hostname.
580  *
581  ***/
582 char *silc_net_localhost(void);
583
584 /****f* silcutil/SilcNetAPI/silc_net_localip
585  *
586  * SYNOPSIS
587  *
588  *    char *silc_net_localip(void)
589  *
590  * DESCRIPTION
591  *
592  *    Return IP of localhost.  The caller must free the returned IP.
593  *
594  ***/
595 char *silc_net_localip(void);
596
597 /****f* silcutil/SilcNetAPI/silc_net_win32_init
598  *
599  * SYNOPSIS
600  *
601  *    SilcBool silc_net_win32_init(void);
602  *
603  * DESCRIPTION
604  *
605  *    This is WIN32 system specific function and is used to initialize
606  *    the network.  This must be called by all WIN32 applications.  It
607  *    is usually called at the application's main() or WinMain() before
608  *    calling any other SILC routine.  The application must also call
609  *    the silc_net_win32_uninit when exiting the application.  Returns
610  *    FALSE on error.  The network will not work if this function returns
611  *    FALSE.
612  *
613  * NOTES
614  *
615  *    This routines is available only on Win32 platform.
616  *
617  ***/
618 SilcBool silc_net_win32_init(void);
619
620 /****f* silcutil/SilcNetAPI/silc_net_win32_uninit
621  *
622  * SYNOPSIS
623  *
624  *    void silc_net_win32_init(void);
625  *
626  * DESCRIPTION
627  *
628  *    This is WIN32 system specific function and is used to uninitialize
629  *    the network.  This must be called by all WIN32 applications.  It
630  *    is usually called when the application is exiting.  After calling
631  *    this function the SILC Net API routines will not work anymore.
632  *
633  * NOTES
634  *
635  *    This routines is available only on Win32 platform.
636  *
637  ***/
638 void silc_net_win32_uninit(void);
639
640 #include "silcnet_i.h"
641
642 #endif /* SILCNET_H */