#include "tools.h"
#include <sys/socket.h>
#include <netdb.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <net/if.h>
Go to the source code of this file.
Defines | |
#define | _WINSOCK_DEPRECATED_NO_WARNINGS |
#define | SEND_TIMEOUTED -97 |
#define | RECV_TIMEOUTED -98 |
#define | TRANS_TIMEOUTED -99 |
#define | MAXIFNO 10 |
取り扱うネットワークインターフェイスの最大数 | |
#define | udp_send_mesg(sock, smsg, sv_addr) udp_send((sock), (smsg), 0, (sv_addr)) |
#define | tcp_send_mesg(sock, smsg) tcp_send((sock), (smsg), 0) |
#define | get_localip() get_localip_bydest("202.26.158.1") |
自分の IPアドレス(文字列) | |
Functions | |
int | init_network (void) |
void | cleanup_network (void) |
int | udp_server_socket (int) |
call socket(), bind() | |
int | udp_server_socket_setopt (int, int, const void *, int) |
call socket(), setsockopt(), bind() | |
int | udp_client_socket (char *, int, struct sockaddr_in *) |
call socket() | |
int | udp_bind (int, int) |
call bind() | |
int | udp_bind_setopt (int, int, int, const void *, int) |
call setsockopt(), bind() | |
int | tcp_server_socket (int port) |
call socket(), bind(), listen() | |
int | tcp_server_socket_setopt (int port, int, const void *, int) |
call socket(), setsockopt(), bind(), listen() | |
int | tcp_server_bind (int port) |
call socket(), bind() | |
int | tcp_server_bind_setopt (int port, int, const void *, int) |
call socket(), setsockopt(), bind() | |
int | tcp_client_socket (char *hname, int port) |
call socket(), connect() | |
int | tcp_client_bind_socket (char *host, int sport, int cport) |
call socket(), bind(), connect() | |
int | tcp_bind (int, int) |
call bind() | |
int | tcp_bind_setopt (int, int, int, const void *, int) |
call setsockopt(), bind() | |
int | tcp_connect (int sock, char *host, int port) |
call connect() | |
int | accept_intr (int, struct sockaddr *, socklen_t *) |
call accept() | |
int | socket_close (int sock) |
call shutdown(), close() | |
int | get_valid_udp_socket (int min, int max, unsigned short *port) |
int | get_valid_tcp_server_socket (int min, int max, unsigned short *port) |
int | get_valid_tcp_client_socket (int min, int max, char *hostname, unsigned short sport, unsigned short *cport) |
int | udp_recv (int, char *, int, struct sockaddr_in *) |
int | udp_send (int, char *, int, struct sockaddr_in *) |
int | tcp_recv (int, char *, int) |
int | tcp_send (int, char *, int) |
int | tcp_recv_wait (int sock, char *data, int sz, int tm) |
int | udp_recv_wait (int sock, char *data, int size, struct sockaddr_in *sv_addr, int tm) |
int | tcp_send_mesgln (int, char *) |
int | tcp_recv_mstream (int sock, char *mesg, int sz, mstream *sb, int tm) |
int | recv_wait (int sock, int tm) |
int | recv_wait_twin (int sock1, int sock2, int tm) |
int | send_wait (int sock, int tm) |
void | udp_hole_punching (int sock, struct sockaddr_in addr, int nm) |
char * | get_ipaddr (struct in_addr) |
構造体 → IPv4アドレス(文字列) | |
char * | get_ipaddr_byname (char *) |
ホスト名 → IPv4アドレス(文字列) | |
char * | get_mynetaddr (void) |
自分の IPv4ネットワークアドレス(文字列) | |
char * | get_localip_bydest (char *dest) |
自分の IPv4アドレス(文字列) | |
char * | get_hostname_bynum (unsigned char *) |
IPv4アドレス(数字) → ホスト名(文字列). | |
char * | get_hostname (char *) |
IPv4アドレス(文字列)→ ホスト名(文字列). | |
unsigned char * | get_ipaddr_num (struct in_addr) |
構造体 → IPv4アドレス(数字4byte) | |
unsigned char * | get_ipaddr_byname_num (char *) |
ホスト名 → IPv4アドレス(数字4byte) | |
unsigned char * | get_mynetaddr_num (void) |
自分の IPv4ネットワークアドレス(数字) | |
char * | get_myipaddr (void) |
自分の [IPアドレス]/[ネットマスク](文字列) | |
unsigned char * | get_myipaddr_num (void) |
自分の [IPアドレス],[ネットマスク](数字) | |
struct sockaddr_in | get_sockaddr (char *hostname, unsigned short cport) |
struct sockaddr_in | get_sockaddr_bynum (char *ipnum, unsigned short cport) |
struct sockaddr_in | get_local_sockaddr (unsigned short cport) |
int | is_same_sockaddr (struct sockaddr_in addr1, struct sockaddr_in addr2) |
unsigned char * | to_address_num8 (char *addr, int mode) |
IPアドレス(文字列)→ [IPアドレス],[ネットマスク](数字8byte). | |
char * | to_address_char8 (unsigned char *addr) |
[IPアドレス],[ネットマスク](数字8byte)→ IPアドレス(文字列) | |
unsigned char * | to_address_num4 (char *addr, int mode) |
IPアドレス(文字列)→ [IPアドレス](数字4byte). | |
char * | to_address_char4 (unsigned char *addr) |
[IPアドレス](数字4byte)→ IPアドレス(文字列) | |
int | is_same_network_num (unsigned char *addr1, unsigned char *addr2, unsigned char *mask) |
int | is_same_network (char *addr1, char *addr2, char *mask) |
#define _WINSOCK_DEPRECATED_NO_WARNINGS |
Definition at line 20 of file network4.h.
#define get_localip | ( | ) | get_localip_bydest("202.26.158.1") |
char* get_localip(void)
自分自身の IPアドレスを得るもう一つの方法.
リモートマシンに接続(ダミー)を試み,そのインターフェイス情報を獲得する.
Definition at line 180 of file network4.h.
#define MAXIFNO 10 |
Definition at line 69 of file network4.h.
Referenced by get_myipaddr_num().
#define RECV_TIMEOUTED -98 |
Definition at line 63 of file network4.h.
Referenced by tcp_recv_wait(), and udp_recv_wait().
#define SEND_TIMEOUTED -97 |
Definition at line 62 of file network4.h.
#define tcp_send_mesg | ( | sock, | |||
smsg | ) | tcp_send((sock), (smsg), 0) |
int tcp_send_mesg(int sock, char* smsg)
TCP経由でメッセージ(文字列)を送信する.
sock | ソケット記述子 | |
smsg | 送信用メッセージ |
0以上 | 送信したバイト数. | |
-1 | 失敗. |
Definition at line 153 of file network4.h.
#define TRANS_TIMEOUTED -99 |
Definition at line 64 of file network4.h.
#define udp_send_mesg | ( | sock, | |||
smsg, | |||||
sv_addr | ) | udp_send((sock), (smsg), 0, (sv_addr)) |
int udp_send_mesg(int sock, char* smsg, struct sockaddr_in* sv_addr)
UDPで文字列データを送る.
sock | ソケット記述子 | |
smsg | 送信するデータ | |
sv_addr | サーバの情報を格納する sockaddar_in 構造体へのポインタ. |
0以上 | 送信したバイト数. | |
-1 | 失敗. |
Definition at line 141 of file network4.h.
int accept_intr | ( | int | sock, | |
struct sockaddr * | cl_addr, | |||
socklen_t * | cdlen | |||
) |
int accept_intr(int sock, struct sockaddr* cl_addr, socklen_t* cdlen)
accept()でブロック中に割り込みが掛かって,accept()が失敗で終了しても 再施行できるようにするためのラッパー関数 (for Solaris)
sock | ソケット | |
cl_addr | ソケットの情報が入る sockaddr 構造体へのポインタ | |
cdlen | sockaddr 構造体(*cl_addr)のサイズ |
0以上 | accept() で作成されたソケット記述子. | |
-1 | エラー. |
void cleanup_network | ( | void | ) |
char* get_hostname | ( | char * | ipaddr | ) |
char* get_hostname(char* ipaddr)
IPアドレス(文字列)からホスト名を逆引きする.
FQDNを指定した場合は,正引きして逆引きするので,FQDNのチェックに使用できる.
ipaddr | IPアドレス(文字列)または FQDN |
Definition at line 1040 of file network4.c.
References get_hostname_bynum(), and to_address_num4().
01041 { 01042 char* name; 01043 unsigned char* num; 01044 01045 num = to_address_num4(ipaddr, 1); 01046 if (num==NULL) return NULL; 01047 01048 name = get_hostname_bynum(num); 01049 free(num); 01050 01051 return name; 01052 }
char* get_hostname_bynum | ( | unsigned char * | num | ) |
char* get_hostname_bynum(unsigned char* num)
バイナリのIPアドレス(長さ4byte)からホスト名を逆引きする.
num | バイナリのIPアドレス(長さ4byte). |
Definition at line 1003 of file network4.c.
01004 { 01005 int len; 01006 char* hname; 01007 struct hostent* hent; 01008 01009 #ifdef WIN32 01010 hent = gethostbyaddr((const char*)num, 4, AF_INET); 01011 #else 01012 hent = gethostbyaddr(num, 4, AF_INET); 01013 #endif 01014 01015 if (hent==NULL) return NULL; 01016 01017 len = (int)strlen(hent->h_name); 01018 hname = (char*)malloc(len+1); 01019 if (hname==NULL) { 01020 free(hent); 01021 return NULL; 01022 } 01023 memcpy(hname, hent->h_name, len+1); 01024 01025 return hname; 01026 }
char* get_ipaddr | ( | struct in_addr | sin_addr | ) |
char* get_ipaddr(struct in_addr sin_addr)
in_addr構造体から IPアドレスを獲得する.
sin_addr | sockaddr_in 構造体の sin_addr メンバ. |
struct sockaddr_in addr .........; ipaddr = get_ipaddr(addr.sin_addr);
Definition at line 1293 of file network4.c.
Referenced by get_localip_bydest().
01294 { 01295 char* ip; 01296 unsigned char* pp; 01297 01298 pp = (unsigned char*)&(sin_addr); 01299 if (pp[0]==0) return NULL; 01300 01301 ip = (char*)malloc(16); 01302 if (ip==NULL) return NULL; 01303 memset(ip, 0, 16); 01304 01305 snprintf(ip, 15, "%d.%d.%d.%d", pp[0], pp[1], pp[2], pp[3]); 01306 01307 return ip; 01308 }
char* get_ipaddr_byname | ( | char * | hostname | ) |
char* get_ipaddr_byname(char* hostname)
ホスト名から IPアドレスを獲得する.
hostname | ホスト名 |
Definition at line 1350 of file network4.c.
01351 { 01352 struct hostent *host; 01353 char* ip; 01354 unsigned char* pp; 01355 01356 host = gethostbyname(hostname); 01357 if (host==NULL) return NULL; 01358 01359 ip = (char*)malloc(16); 01360 if (ip==NULL) return NULL; 01361 memset(ip, 0, 16); 01362 01363 pp = (unsigned char*)(host->h_addr); 01364 snprintf(ip, 15, "%d.%d.%d.%d", pp[0], pp[1], pp[2], pp[3]); 01365 01366 return ip; 01367 }
unsigned char* get_ipaddr_byname_num | ( | char * | hostname | ) |
unsigned char* get_ipaddr_byname_num(char* hostname)
ホスト名から IPアドレスを獲得する.
hostname | ホスト名 |
Definition at line 1379 of file network4.c.
01380 { 01381 struct hostent *host; 01382 unsigned char* ip; 01383 unsigned char* pp; 01384 01385 host = gethostbyname(hostname); 01386 if (host==NULL) return NULL; 01387 ip = (unsigned char*)malloc(4); 01388 if (ip==NULL) return NULL; 01389 01390 pp = (unsigned char*)(host->h_addr); 01391 memcpy(ip, pp, 4); 01392 01393 return ip; 01394 }
unsigned char* get_ipaddr_num | ( | struct in_addr | sin_addr | ) |
unsigned char* get_ipaddr_num(struct in_addr sin_addr)
in_addr 構造体から IPアドレスを獲得する.
sin_addr | sockaddr_in 構造体の sin_addr メンバ. |
struct sockaddr_in addr .........; ipaddr = get_ipaddr_num(addr.sin_addr);
Definition at line 1326 of file network4.c.
struct sockaddr_in get_local_sockaddr | ( | unsigned short | cport | ) | [read] |
Definition at line 1501 of file network4.c.
01502 { 01503 struct sockaddr_in ss_addr; 01504 struct hostent *shost; 01505 01506 01507 // localhost の情報を ss_addrに格納 01508 shost = gethostbyname("127.0.0.1"); 01509 01510 memset(&ss_addr, 0, sizeof(ss_addr)); 01511 ss_addr.sin_family = AF_INET; 01512 ss_addr.sin_port = htons(cport); 01513 memcpy(&(ss_addr.sin_addr), shost->h_addr, shost->h_length); 01514 01515 return ss_addr; 01516 }
char* get_localip_bydest | ( | char * | dest | ) |
char* get_localip_bydest(char* dest)
接続先を指定して,そこへ接続する インターフェイスのIPアドレスを得る.自分自身の IPアドレスを得るもう一つの方法.
dest | 接続先の IPアドレス または FQDN |
Definition at line 1236 of file network4.c.
References get_ipaddr(), get_ipaddr_byname(), and socket_close().
01237 { 01238 int err, sofd; 01239 socklen_t len; 01240 char* addr; 01241 char* ip; 01242 struct sockaddr_in localif; 01243 struct sockaddr_in remote; 01244 01245 if (dest==NULL) return NULL; 01246 ip = get_ipaddr_byname(dest); 01247 if (ip ==NULL) return NULL; 01248 01249 memset(&localif, 0, sizeof(struct sockaddr_in)); 01250 memset(&remote, 0, sizeof(struct sockaddr_in)); 01251 remote.sin_family = AF_INET; 01252 remote.sin_addr.s_addr = inet_addr(ip); 01253 remote.sin_port = htons(9999); 01254 free(ip); 01255 01256 sofd = (int)socket(AF_INET, SOCK_DGRAM, 0); 01257 if (sofd<0) return NULL; 01258 01259 err = connect(sofd, (struct sockaddr*)&remote, sizeof(remote)); 01260 if (err<0) { 01261 socket_close(sofd); 01262 return NULL; 01263 } 01264 01265 len = sizeof(localif); 01266 err = getsockname(sofd, (struct sockaddr *)&localif, &len); 01267 if (err<0) { 01268 socket_close(sofd); 01269 return NULL; 01270 } 01271 socket_close(sofd); 01272 01273 addr = get_ipaddr(localif.sin_addr); 01274 return addr; 01275 }
char* get_myipaddr | ( | ) |
char* get_myipaddr()
ネットワークインターフェイスを検索し,一番最初に見つけた UP状態で, ループバックでないインターフェイスのIPアドレスと ネットマスクを返す.
ただし,検索するインターフェイスの数は MAXIFNO 以内であり,それより多いものは無視する.
ネットマスクが必要ないなら get_localip() を使用しても良い.
Definition at line 1202 of file network4.c.
References get_myipaddr_num().
01203 { 01204 char* addr; 01205 unsigned char* n; 01206 01207 n = get_myipaddr_num(); 01208 if (n==NULL) return NULL; 01209 01210 addr = (char*)malloc(32); 01211 if (addr==NULL) { 01212 free(n); 01213 return NULL; 01214 } 01215 memset(addr, 0, 32); 01216 01217 snprintf(addr, 31, "%d.%d.%d.%d/%d.%d.%d.%d", n[0], n[1], n[2], n[3], n[4], n[5], n[6], n[7]); 01218 01219 free(n); 01220 return addr; 01221 }
unsigned char* get_myipaddr_num | ( | ) |
unsigned char* get_myipaddr_num()
ネットワークインターフェイスを検索し,一番最初に見つけた UP状態で, ループバックでないインターフェイスのIPアドレスとネットマスクを返す.
ただし,検索するインターフェイスの数は MAXIFNO 以内であり,それ以上は無視する.
自分自身のIPアドレスを知る方法としては, gethostname() と gethostbyname() を使う方法もある.
struct hostent *shost; ..................... gethostname(hostname, sizeof(hostname)); shost = gethostbyname(hostname);
また,get_localip() の方法も使える.
Definition at line 1107 of file network4.c.
References MAXIFNO, and socket_close().
01108 { 01109 int i, sofd, len; 01110 01111 unsigned char* addr = NULL; 01112 struct ifconf ifc; 01113 struct ifreq* ifq; 01114 struct ifreq* ifp; 01115 01116 01117 len = sizeof(struct ifreq)*MAXIFNO; 01118 ifp = ifq = (struct ifreq*)malloc(len); 01119 if (ifq==NULL) return NULL; 01120 ifc.ifc_len = len; 01121 ifc.ifc_req = ifq; 01122 01123 sofd = socket(AF_INET, SOCK_DGRAM, 0); 01124 if (sofd<0) { 01125 perror("get_myipaddr_num: socket"); 01126 return NULL; 01127 } 01128 01129 01130 // インターフェイス名の取得 01131 if (ioctl(sofd, SIOCGIFCONF, &ifc)<0) { 01132 socket_close(sofd); 01133 free(ifq); 01134 return NULL; 01135 } 01136 01137 01138 ifp = ifq; 01139 for (i=0; i<MAXIFNO; i++) { 01140 01141 // インターフェイスのフラグ取得 01142 if (ioctl(sofd, SIOCGIFFLAGS, ifp)<0) { 01143 socket_close(sofd); 01144 free(ifq); 01145 return NULL; 01146 } 01147 01148 if ((ifp->ifr_flags&IFF_UP) && !(ifp->ifr_flags&IFF_LOOPBACK)) { 01149 int j; 01150 unsigned char* p = (unsigned char*)ifp->ifr_addr.sa_data; 01151 01152 addr = (unsigned char*)malloc(8); 01153 if (addr==NULL) { 01154 socket_close(sofd); 01155 free(ifq); 01156 return NULL; 01157 } 01158 01159 // アドレス取得 01160 if (ioctl(sofd, SIOCGIFADDR, ifp)<0) { 01161 socket_close(sofd); 01162 free(ifq); 01163 free(addr); 01164 return NULL; 01165 } 01166 for (j=0; j<4; j++) addr[j] = p[j+2]; 01167 01168 // ネットマスク取得 01169 if (ioctl(sofd, SIOCGIFNETMASK, ifp)<0) { 01170 socket_close(sofd); 01171 free(ifq); 01172 free(addr); 01173 return NULL; 01174 } 01175 for (j=0; j<4; j++) addr[j+4] = p[j+2]; 01176 01177 return addr; 01178 } 01179 ifp++; 01180 } 01181 01182 socket_close(sofd); 01183 free(ifq); 01184 return NULL; 01185 }
char* get_mynetaddr | ( | ) |
char* get_mynetaddr()
自分のネットワークアドレスを返す
Definition at line 1405 of file network4.c.
References get_mynetaddr_num().
01406 { 01407 char* net; 01408 unsigned char* pp; 01409 01410 pp = get_mynetaddr_num(); 01411 if (pp==NULL) return NULL; 01412 01413 net = (char*)malloc(16); 01414 if (net==NULL) { 01415 free(pp); 01416 return NULL; 01417 } 01418 memset(net, 0, 16); 01419 01420 snprintf(net, 15, "%d.%d.%d.%d", pp[0], pp[1], pp[2], pp[3]); 01421 01422 free(pp); 01423 return net; 01424 }
unsigned char* get_mynetaddr_num | ( | ) |
unsigned char* get_mynetaddr_num()
自分のネットワークアドレスを返す
Definition at line 1435 of file network4.c.
References get_myipaddr_num().
01436 { 01437 int i; 01438 unsigned char* net; 01439 unsigned char* ip; 01440 unsigned char* mk; 01441 01442 ip = get_myipaddr_num(); 01443 if (ip==NULL) return NULL; 01444 mk = &(ip[4]); 01445 01446 net = (unsigned char*)malloc(4); 01447 if (net==NULL) { 01448 free(ip); 01449 return NULL; 01450 } 01451 01452 for (i=0; i<4; i++) net[i] = ip[i] & mk[i]; 01453 01454 free(ip); 01455 return net; 01456 }
struct sockaddr_in get_sockaddr | ( | char * | hostname, | |
unsigned short | cport | |||
) | [read] |
Definition at line 1464 of file network4.c.
01465 { 01466 struct sockaddr_in ss_addr; 01467 struct hostent *shost; 01468 01469 // Serverの情報を ss_addrに格納 01470 shost = gethostbyname(hostname); 01471 if (shost==NULL) { 01472 ss_addr.sin_family = 0; 01473 ss_addr.sin_port = 0; 01474 return ss_addr; 01475 } 01476 01477 memset(&ss_addr, 0, sizeof(ss_addr)); 01478 ss_addr.sin_family = AF_INET; 01479 ss_addr.sin_port = htons(cport); 01480 memcpy(&(ss_addr.sin_addr), shost->h_addr, shost->h_length); 01481 01482 return ss_addr; 01483 }
struct sockaddr_in get_sockaddr_bynum | ( | char * | ipnum, | |
unsigned short | cport | |||
) | [read] |
Definition at line 1487 of file network4.c.
int get_valid_tcp_client_socket | ( | int | min, | |
int | max, | |||
char * | hostname, | |||
unsigned short | sport, | |||
unsigned short * | cport | |||
) |
Definition at line 1140 of file network.c.
01141 { 01142 int i, sock, range; 01143 01144 range = max - min + 1; 01145 *cport = rand()%range + min; 01146 01147 i = 1; 01148 sock = tcp_client_bind_socket(hname, (int)sport, (int)*cport); 01149 while(sock<0 && i<range) { 01150 (*cport)++; 01151 if (*cport>max) *cport = ((int)*cport)%max + min - 1; 01152 sock = tcp_client_bind_socket(hname, (int)sport, (int)*cport); 01153 i++; 01154 } 01155 01156 if (sock<=0) *cport = 0; 01157 01158 return sock; 01159 }
int get_valid_tcp_server_socket | ( | int | min, | |
int | max, | |||
unsigned short * | port | |||
) |
Definition at line 1118 of file network.c.
01119 { 01120 int i, sock, range; 01121 01122 range = max - min + 1; 01123 *port = rand()%range + min; 01124 01125 i = 1; 01126 sock = tcp_server_socket((int)*port); 01127 while(sock<=0 && i<range) { 01128 (*port)++; 01129 if (*port>max) *port = ((int)*port)%max + min - 1; 01130 sock = tcp_server_socket((int)*port); 01131 i++; 01132 } 01133 01134 if (sock<=0) *port = 0; 01135 01136 return sock; 01137 }
int get_valid_udp_socket | ( | int | min, | |
int | max, | |||
unsigned short * | port | |||
) |
Definition at line 1094 of file network.c.
01095 { 01096 int i, sock, range; 01097 struct addrinfo* address; 01098 01099 range = max - min + 1; 01100 *port = rand()%range + min; 01101 01102 i = 1; 01103 sock = udp_server_socket((int)*port, &address); 01104 while(sock<=0 && i<range) { 01105 (*port)++; 01106 if (*port>max) *port = ((int)*port)%max + min - 1; 01107 sock = udp_server_socket((int)*port, &address); 01108 i++; 01109 } 01110 01111 if (sock<=0) *port = 0; 01112 01113 freeaddrinfo(address); 01114 return sock; 01115 }
int init_network | ( | void | ) |
int is_same_network | ( | char * | addr1, | |
char * | addr2, | |||
char * | mask | |||
) |
int is_same_network(char* addr1, char* addr2, char* mask)
文字型アドレス addr1 と addr2が同じネットワークに属しているかどうかチェックする.
addr1, addr2 は FQDNでも可.
addr1 | 比較するアドレス(文字型).FQDN は不可 | |
addr2 | 比較するアドレス(文字型).FQDN は不可 | |
mask | ネットマスク(文字型) |
TRUE | 同じネットワークである. | |
FALSE | 同じネットワークでない. |
int is_same_network(char* addr1, char* addr2, char* mask)
文字型アドレス addr1 と addr2が同じネットワークに属しているかどうかチェックする.
addr1, addr2 は FQDNでも可.
addr1 | 比較するアドレス(文字型) | |
addr2 | 比較するアドレス(文字型) | |
mask | ネットマスク(文字型) |
TRUE | 同じネットワークである. | |
FALSE | 同じネットワークでない. |
Definition at line 2322 of file network.c.
02323 { 02324 int ret, family; 02325 unsigned char* a1; 02326 unsigned char* a2; 02327 unsigned char* mk; 02328 02329 if (addr1==NULL || addr2==NULL || mask==NULL) return FALSE; 02330 02331 a1 = (unsigned char*)strstr(addr1, ":"); 02332 a2 = (unsigned char*)strstr(addr1, ":"); 02333 mk = (unsigned char*)strstr(mask, ":"); 02334 if (a1!=NULL && a2!=NULL && mask!=NULL) family = AF_INET6; 02335 else if (a1==NULL && a2==NULL && mask==NULL) family = AF_INET; 02336 else return FALSE; 02337 02338 a1 = to_address_num(addr1, 0, 0, family); 02339 a2 = to_address_num(addr2, 0, 0, family); 02340 mk = to_address_num(mask, 0, 0, family); 02341 if (a1==NULL || a2==NULL || mk==NULL) { 02342 freeNull(a1); 02343 freeNull(a2); 02344 freeNull(mk); 02345 return FALSE; 02346 } 02347 02348 ret = is_same_network_num(a1, a2, mk, family); 02349 freeNull(a1); 02350 freeNull(a2); 02351 freeNull(mk); 02352 02353 return ret; 02354 }
int is_same_network_num | ( | unsigned char * | addr1, | |
unsigned char * | addr2, | |||
unsigned char * | mask | |||
) |
int is_same_network_num(unsigned char* addr1, unsigned char* addr2, unsigned char* mask)
数字型アドレス addr1 と addr2が同じネットワークに属しているかどうかチェックする.
addr1 | 比較するアドレス(数字型)4Byte | |
addr2 | 比較するアドレス(数字型)4Byte | |
mask | ネットマスク(数字型)4Byte |
TRUE | 同じネットワークである. | |
FALSE | 同じネットワークでない |
Definition at line 1569 of file network4.c.
01570 { 01571 int i; 01572 01573 if (addr1==NULL || addr2==NULL) return FALSE; 01574 01575 if (mask==NULL) { 01576 for (i=0; i<4; i++) { 01577 if (addr1[i] != addr2[i]) return FALSE; 01578 } 01579 } 01580 else { 01581 for (i=0; i<4; i++) { 01582 if ((addr1[i]&mask[i]) != (addr2[i]&mask[i])) return FALSE; 01583 } 01584 } 01585 return TRUE; 01586 }
int is_same_sockaddr | ( | struct sockaddr_in | addr1, | |
struct sockaddr_in | addr2 | |||
) |
int is_same_sockaddr(struct sockaddr_in addr1, struct sockaddr_in addr2)
addr1 と addr2が格納する IPアドレスとポート番号が同じかどうか検査する
addr1 | 比較する sockaddr_in 構造体 | |
addr2 | 比較する sockaddr_in 構造体 |
TRUE | 同じホスト | |
FALSE | 違うホスト |
Definition at line 1531 of file network4.c.
01532 { 01533 int i, len; 01534 unsigned char *p1, *p2; 01535 01536 p1 = (unsigned char*)&(addr1.sin_addr); 01537 p2 = (unsigned char*)&(addr2.sin_addr); 01538 len = sizeof(addr1.sin_addr); 01539 01540 for (i=0; i<len; i++) { 01541 if (p1[i]!=p2[i]) return FALSE; 01542 } 01543 01544 p1 = (unsigned char*)&(addr1.sin_port); 01545 p2 = (unsigned char*)&(addr2.sin_port); 01546 len = sizeof(addr1.sin_port); 01547 01548 for (i=0; i<len; i++) { 01549 if (p1[i]!=p2[i]) return FALSE; 01550 } 01551 01552 return TRUE; 01553 }
int recv_wait | ( | int | sock, | |
int | tm | |||
) |
int recv_wait(int sock, int tm)
簡易 受信 wait. ソケットにデータが受信されるまで待つ.スレッド対応
sock | 監視するソケット | |
tm | タイムアウトの秒数 |
TRUE | バッファにデータがある. | |
FALSE | タイムアウトした. |
int recv_wait(int sock, int tm)
簡易 受信wait. ソケットにデータが受信されるまで待つ.スレッド対応
sock | 監視するソケット | |
tm | タイムアウトの秒数 |
TRUE | バッファにデータがある. | |
FALSE | タイムアウトした. |
Definition at line 1468 of file network.c.
01469 { 01470 int nd; 01471 fd_set mask; 01472 struct timeval timeout; 01473 time_t otm, ntm; 01474 01475 otm = time(NULL); 01476 do { 01477 timeout.tv_sec = tm; 01478 timeout.tv_usec = 0; 01479 FD_ZERO(&mask); 01480 FD_SET(sock, &mask); 01481 01482 //DEBUG_MESG("Waiting sock = %d for %ds.\n", sock, tm); 01483 nd = select(sock+1, &mask, NULL, NULL, &timeout); 01484 ntm = time(NULL); 01485 } while ((nd<0 || !FD_ISSET(sock, &mask)) && (int)(ntm-otm)<=tm); 01486 01487 return FD_ISSET(sock, &mask); 01488 }
int recv_wait_twin | ( | int | sock1, | |
int | sock2, | |||
int | tm | |||
) |
int recv_wait_twin(int sock1, int sock2, int tm)
簡易 受信 wait. 二つのソケット sock1, sock2 にデータが受信されるまで待つ.スレッド対応
sock1 | 監視するソケット その1 | |
sock2 | 監視するソケット その2 | |
tm | タイムアウトの秒数 |
0 | タイムアウトした. | |
1 | sock1 のバッファにデータがある. | |
2 | sock2 のバッファにデータがある. | |
3 | sock1 と sock2 のバッファにデータがある. |
Definition at line 1506 of file network.c.
01507 { 01508 int ret = 0; 01509 int nm, nd; 01510 fd_set mask; 01511 struct timeval timeout; 01512 time_t otm, ntm; 01513 01514 nm = Max(sock1, sock2); 01515 otm = time(NULL); 01516 do { 01517 timeout.tv_sec = tm; 01518 timeout.tv_usec = 0; 01519 FD_ZERO(&mask); 01520 FD_SET(sock1, &mask); 01521 FD_SET(sock2, &mask); 01522 nd = select(nm+1, &mask, NULL, NULL, &timeout); 01523 ntm = time(NULL); 01524 } while ((nd<0 || (!FD_ISSET(sock1, &mask) && !FD_ISSET(sock2, &mask))) && (int)(ntm-otm)<=tm); 01525 01526 if (FD_ISSET(sock1, &mask)) ret += 1; 01527 if (FD_ISSET(sock2, &mask)) ret += 2; 01528 01529 return ret; 01530 }
int send_wait | ( | int | sock, | |
int | tm | |||
) |
int send_wait(int sock, int tm)
簡易 送信 wait. データが送信可能になるまで待つ.スレッド対応
sock | 監視するソケット | |
tm | タイムアウトの秒数 |
TRUE | バッファにデータがある. | |
FALSE | タイムアウトした. |
int send_wait(int sock, int tm)
簡易 送信wait. データが送信可能になるまで待つ.スレッド対応
sock | 監視するソケット | |
tm | タイムアウトの秒数 |
TRUE | バッファにデータがある. | |
FALSE | タイムアウトした. |
Definition at line 1545 of file network.c.
01546 { 01547 int nd; 01548 fd_set mask; 01549 struct timeval timeout; 01550 time_t otm, ntm; 01551 01552 otm = time(NULL); 01553 do { 01554 timeout.tv_sec = tm; 01555 timeout.tv_usec = 0; 01556 FD_ZERO(&mask); 01557 FD_SET(sock, &mask); 01558 01559 //DEBUG_MESG("Waiting sock = %d for %ds.\n", sock, tm); 01560 nd = select(sock+1, NULL, &mask, NULL, &timeout); 01561 ntm = time(NULL); 01562 } while ((nd<0 || !FD_ISSET(sock, &mask)) && (int)(ntm-otm)<=tm); 01563 01564 return FD_ISSET(sock, &mask); 01565 }
int socket_close | ( | int | sofd | ) |
未送信のデータを破棄して,ソケットを完全に閉じる.
sofd | クローズしたいソケット記述子を指定. |
1以上 | 最後に受信したバイト数 | |
0 | 正常切断. | |
-1 | エラー |
int tcp_bind | ( | int | sofd, | |
int | port | |||
) |
int tcp_bind(int sofd, int port)
TCPソケットにポートをバインドする.
sofd | バインドするソケットの記述子. | |
port | ポート番号 |
sofd | 成功 | |
-3 | 失敗 |
Definition at line 547 of file network4.c.
References socket_close().
00548 { 00549 int err; 00550 struct sockaddr_in sv_addr; 00551 00552 if (sofd<=0) return sofd; 00553 00554 memset(&sv_addr, 0, sizeof(sv_addr)); 00555 sv_addr.sin_family = AF_INET; 00556 sv_addr.sin_port = htons(port); 00557 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00558 00559 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00560 if (err<0) { 00561 socket_close(sofd); 00562 return -3; 00563 } 00564 00565 return sofd; 00566 }
int tcp_bind_setopt | ( | int | sofd, | |
int | port, | |||
int | opt, | |||
const void * | optval, | |||
int | optlen | |||
) |
int tcp_bind_setopt(int sofd, int port, int opt, const void* optval, int optlen)
TCPソケットにポートをバインドする.オプションの指定(setsockopt)が可能.
sofd | バインドするソケットの記述子. | |
port | ポート番号 | |
opt | オプションの種類 | |
optval | オプションデータ | |
optlen | optval の長さ |
0以上 | 作成されたソケット記述子. | |
-2 | ソケットオプションの設定に失敗. | |
-3 | バインドに失敗. |
Definition at line 584 of file network4.c.
References socket_close().
00585 { 00586 int err; 00587 struct sockaddr_in sv_addr; 00588 00589 if (sofd<=0) return sofd; 00590 00591 if (opt>0) { 00592 #ifdef WIN32 00593 err = setsockopt(sofd, SOL_SOCKET, opt, (const char*)optval, optlen); 00594 #else 00595 err = setsockopt(sofd, SOL_SOCKET, opt, optval, optlen); 00596 #endif 00597 if (err<0) { 00598 socket_close(sofd); 00599 return -2; 00600 } 00601 } 00602 00603 memset(&sv_addr, 0, sizeof(sv_addr)); 00604 sv_addr.sin_family = AF_INET; 00605 sv_addr.sin_port = htons(port); 00606 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00607 00608 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00609 if (err<0) { 00610 socket_close(sofd); 00611 return -3; 00612 } 00613 00614 return sofd; 00615 }
int tcp_client_bind_socket | ( | char * | hostname, | |
int | sport, | |||
int | cport | |||
) |
int tcp_client_bind_socket(char* hostname, int sport, int cport)
TCPのクライアントソケットを作り,サーバに接続する.
この関数内で呼び出されるネットワーク関数: socket(), bind(), gethostbyname(), connect()
hostname | サーバ名 | |
sport | サーバポート番号 | |
cport | 自分のポート番号 |
0以上 | 作成されたソケット記述子. | |
-1 | ソケットの作成に失敗. | |
-3 | バインドに失敗. | |
-4 | サーバ情報の取得に失敗. | |
-5 | サーバへの接続に失敗. |
Definition at line 495 of file network4.c.
References socket_close().
00496 { 00497 int sofd, err; 00498 struct hostent *shost; 00499 struct sockaddr_in sv_addr; 00500 00501 sofd = (int)socket(AF_INET, SOCK_STREAM, 0); 00502 if (sofd<0) return -1; 00503 00504 memset(&sv_addr, 0, sizeof(sv_addr)); 00505 sv_addr.sin_family = AF_INET; 00506 sv_addr.sin_port = htons(cport); 00507 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00508 00509 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00510 if (err<0) { 00511 socket_close(sofd); 00512 return -3; 00513 } 00514 00515 shost = gethostbyname(hostname); 00516 if (shost==NULL) { 00517 socket_close(sofd); 00518 return -4; 00519 } 00520 00521 memset(&sv_addr, 0, sizeof(sv_addr)); 00522 sv_addr.sin_family = AF_INET; 00523 sv_addr.sin_port = htons(sport); 00524 memcpy(&sv_addr.sin_addr, shost->h_addr, shost->h_length); 00525 00526 err = connect(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00527 if (err<0) { 00528 socket_close(sofd); 00529 return -5; 00530 } 00531 00532 return sofd; 00533 }
int tcp_client_socket | ( | char * | hostname, | |
int | port | |||
) |
int tcp_client_socket(char* hostname, int port)
TCPのクライアントソケットを作り,サーバに接続する.
この関数内で呼び出されるネットワーク関数: socket(), gethostbyname(), connect()
hostname | サーバ名 | |
port | サーバポート番号 |
0以上 | 作成されたソケット記述子. | |
-1 | ソケットの作成に失敗. | |
-4 | サーバ情報の取得に失敗. | |
-5 | サーバへの接続に失敗. |
Definition at line 448 of file network4.c.
References socket_close().
00449 { 00450 int sofd, err; 00451 struct hostent *shost; 00452 struct sockaddr_in sv_addr; 00453 00454 sofd = (int)socket(AF_INET, SOCK_STREAM, 0); 00455 if (sofd<0) return -1; 00456 00457 shost = gethostbyname(hostname); 00458 if (shost==NULL) { 00459 socket_close(sofd); 00460 return -4; 00461 } 00462 00463 memset(&sv_addr, 0, sizeof(sv_addr)); 00464 sv_addr.sin_family = AF_INET; 00465 sv_addr.sin_port = htons(port); 00466 memcpy(&sv_addr.sin_addr, shost->h_addr, shost->h_length); 00467 00468 err = connect(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00469 if (err<0) { 00470 socket_close(sofd); 00471 return -5; 00472 } 00473 00474 return sofd; 00475 }
int tcp_connect | ( | int | sock, | |
char * | host, | |||
int | port | |||
) |
Definition at line 660 of file network4.c.
00661 { 00662 int err; 00663 struct hostent *shost; 00664 struct sockaddr_in sv_addr; 00665 00666 shost = gethostbyname(hostname); 00667 if (shost==NULL) return -4; 00668 00669 memset(&sv_addr, 0, sizeof(sv_addr)); 00670 sv_addr.sin_family = AF_INET; 00671 sv_addr.sin_port = htons(port); 00672 memcpy(&sv_addr.sin_addr, shost->h_addr, shost->h_length); 00673 00674 err = connect(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00675 if (err<0) return -5; 00676 return 0; 00677 }
int tcp_recv | ( | int | sock, | |
char * | rmsg, | |||
int | size | |||
) |
int tcp_recv(int sock, char* rmsg, int size)
recv()をラッピングした関数.TCP経由でデータを受信する.
sock | ソケット記述子 | |
rmsg | 受信用データバッファ.関数内で初期化される. | |
size | データバッファのサイズ |
1以上 | 受信したバイト数. | |
0 | 正常切断. | |
JBXL_NET_RECV_ERROR | 失敗 |
int tcp_recv(int sock, char* rmsg, int size)
recv()をラッピングした関数.TCP経由でデータを受信する.
sock | ソケット記述子 | |
rmsg | 受信用データバッファ | |
size | データバッファのサイズ |
1以上 | 受信したバイト数. | |
0 | 正常切断. | |
-1 | 失敗 |
Definition at line 1245 of file network.c.
01246 { 01247 int cc; 01248 01249 memset(rmsg, 0, size); 01250 cc = recv(sock, rmsg, size, 0); 01251 01252 if (cc<0) cc = JBXL_NET_RECV_ERROR; 01253 return cc; 01254 }
int tcp_recv_mstream | ( | int | sock, | |
char * | mesg, | |||
int | sz, | |||
mstream * | sb, | |||
int | tm | |||
) |
int tcp_recv_mstream(int sock, char* mesg, int sz, mstream* sb, int tm)
TCP経由でメッセージ(文字列)を受信する.受信メッセージはメッセージストリームバッファに一旦バッファリングされ, この関数により一行ずつ読み出される.mesgには最大 sz-1文字が格納される. もし,バッファ中の一行のデータが sz-1より大きい場合は,はみ出した部分は捨てられる.
mesgに格納される時,行中の改行コードは削除され,行末には必ず '\0' が入る. タイムアウトの設定が可能でタイムアウトに 0を指定した場合, 呼び出した時点で 読み込み可能データがなければすぐにタイムアウトとなる (JBXL_NET_RECV_TIMEOUT が返る).
メッセージストリームのバッファ部が確保されていない場合は,最初に呼び出された時点で確保される. 一旦この関数を使用して,受信データをバッファリングしたら,ソケットをクローズするまで, 読み取りには必ず同じストリームを使用してこの関数を呼び出さばければならない. そうで無い場合は受信データの整合性は保証されない.
sock | ソケット記述子 | |
mesg | 受信用データバッファ.予め十分なメモリ領域を確保しておく. | |
sz | データバッファのサイズ | |
sb | リングバッファ型のストリームバッファ. バッファ部が確保されていなければ,自動的に確保される. | |
tm | タイムアウト時間.秒単位. |
1以上 | mesgに格納したメッセージのバイト数. | |
0 | おそらくは相手側がセッションをクローズした. | |
JBXL_NET_RECV_ERROR | 受信エラー. | |
JBXL_ARGS_ERROR | 引数に NULLのデータがある. | |
JBXL_MALLOC_ERROR | メッセージバッファ部が無いので確保しようとしたが,確保に失敗した. | |
JBXL_NET_BUF_ERROR | メッセージバッファにデータは存在するはずだが,原因不明の理由により獲得に失敗した. | |
JBXL_NET_BUFSZ_ERROR | メッセージバッファ中のデータの長さが,mesgの長さより大きい.はみ出した部分は捨てられた. | |
JBXL_NET_RECV_TIMEOUT | タイムアウト. |
int tcp_recv_mstream(int sock, char* mesg, int sz, mstream* sb, int tm)
TCP経由でメッセージ(文字列)を受信する.受信メッセージはメッセージストリームバッファに一旦バッファリングされ, この関数により一行ずつ読み出される.mesgには最大 sz-1文字が格納される. もし,バッファ中の一行のデータが sz-1より大きい場合は,はみ出した部分は捨てられる.
mesgに格納される時,行中の改行コードは削除され,行末には必ず '\0' が入る. タイムアウトの設定が可能でタイムアウトに 0を指定した場合, 呼び出した時点で 読み込み可能データがなければすぐにタイムアウトとなる (RECV_TIMEOUTED が返る).
メッセージストリームのバッファ部が確保されていない場合は,最初に呼び出された時点で確保される. 一旦この関数を使用して,受信データをバッファリングしたら,ソケットをクローズするまで, 読み取りには必ず同じストリームを使用してこの関数を呼び出さばければならない. そうで無い場合は受信データの整合性は保証されない.
sock | ソケット記述子 | |
mesg | 受信用データバッファ.予め十分なメモリ領域を確保しておく. | |
sz | データバッファのサイズ | |
sb | リングバッファ型のストリームバッファ. バッファ部が確保されていなければ,自動的に確保される. | |
tm | タイムアウト時間.秒単位. |
1以上 | mesgに格納したメッセージのバイト数. | |
0 | おそらくは相手側がセッションをクローズした. | |
-1 | 受信エラー. | |
-2 | 引数に NULLのデータがある. | |
-3 | メッセージバッファ部が無いので確保しようとしたが,確保に失敗した. | |
-4 | メッセージバッファにデータは存在するはずだが,原因不明の理由により獲得に失敗した. | |
-5 | メッセージバッファ中のデータの長さが,mesgの長さより大きい.はみ出した部分は捨てられた. | |
RECV_TIMEOUTED | タイムアウト. |
Definition at line 1419 of file network.c.
01420 { 01421 int cc; 01422 unsigned char* pp; 01423 01424 if (mesg==NULL || sb==NULL) return JBXL_ARGS_ERROR; 01425 //memset(mesg, 0, sz); 01426 01427 if (sb->buf==NULL) { 01428 *sb = make_mstream(RECVBUFSZ); 01429 if (sb->buf==NULL) return JBXL_MALLOC_ERROR; 01430 } 01431 01432 while (sb->datano==0) { 01433 cc = tcp_recv_wait(sock, mesg, sz, tm); 01434 if (cc<=0) { 01435 if (cc<0) cc = JBXL_NET_RECV_ERROR; 01436 return cc; 01437 } 01438 put_mstream(sb, (unsigned char*)mesg); 01439 //memset(mesg, 0, sz); 01440 } 01441 01442 pp = get_mstream(sb); 01443 if (pp==NULL) return JBXL_NET_BUF_ERROR; 01444 if (strlen((const char*)pp)>=(unsigned int)sz) { 01445 memcpy(mesg, pp, sz-1); 01446 free(pp); 01447 return JBXL_NET_BUFSZ_ERROR; 01448 } 01449 memcpy(mesg, pp, strlen((const char*)pp)); 01450 01451 free(pp); 01452 return (int)strlen(mesg); 01453 }
int tcp_recv_wait | ( | int | sock, | |
char * | mesg, | |||
int | sz, | |||
int | tm | |||
) |
int tcp_recv_wait(int sock, char* mesg, int sz, int tm)
TCP経由でデータを受信する.
タイムアウトの設定が可能.タイムアウトに 0を指定した場合, recv_wait() 関数を呼び出した時点で読み込み可能データがなければすぐにタイムアウトとなる (JBXL_NET_RECV_TIMEOUT が返る).
sock | ソケット記述子 | |
mesg | 受信用データバッファ.関数内で初期化される. | |
sz | データバッファのサイズ | |
tm | タイムアウト時間.秒単位. |
1以上 | 受信したバイト数. | |
0 | おそらくは相手側がセッションをクローズした. | |
JBXL_NET_RECV_ERROR | 受信エラー. | |
JBXL_NET_RECV_TIMEOUT | タイムアウト. |
int tcp_recv_wait(int sock, char* mesg, int sz, int tm)
TCP経由でデータを受信する.
タイムアウトの設定が可能.タイムアウトに 0を指定した場合, recv_wait() 関数を呼び出した時点で読み込み可能データがなければすぐにタイムアウトとなる (RECV_TIMEOUTED が返る).
sock | ソケット記述子 | |
mesg | 受信用データバッファ | |
sz | データバッファのサイズ | |
tm | タイムアウト時間.秒単位. |
1以上 | 受信したバイト数. | |
0 | おそらくは相手側がセッションをクローズした. | |
-1 | 受信エラー. | |
RECV_TIMEOUTED | タイムアウト. |
Definition at line 1339 of file network.c.
01340 { 01341 int cc; 01342 01343 memset(mesg, 0, sz); 01344 if (recv_wait(sock, tm)) { 01345 cc = recv(sock, mesg, sz, 0); 01346 } 01347 else { 01348 return JBXL_NET_RECV_TIMEOUT; 01349 } 01350 01351 if (cc<0) cc = JBXL_NET_RECV_ERROR; 01352 return cc; 01353 }
int tcp_send | ( | int | sock, | |
char * | smsg, | |||
int | size | |||
) |
int tcp_send(int sock, char* smsg, int size)
send()をラッピングした関数.TCP経由でデータを送る.
データ(smsg)のサイズ sizeに0以下を指定した場合は,smsgは文字列であると見なして,サイズを自動的に計算する.
sock | ソケット記述子 | |
smsg | 送信するデータ | |
size | 送信するデータ(smsg)のサイズ.サイズが 0以下の場合は smsgは文字列であるとみなす. |
0以上 | 送信したバイト数. | |
JBXL_NET_SEND_ERROR | 失敗 |
int tcp_send(int sock, char* smsg, int size)
send()をラッピングした関数.TCP経由でデータを送る.
データ(smsg)のサイズ sizeに0以下を指定した場合は,smsgは文字列であると見なして,サイズを自動的に計算する.
sock | ソケット記述子 | |
smsg | 送信するデータ | |
size | 送信するデータ(smsg)のサイズ.サイズが 0以下の場合は smsgは文字列であるとみなす. |
0以上 | 送信したバイト数. | |
-1 | 失敗. |
Definition at line 1272 of file network.c.
01273 { 01274 int cc; 01275 01276 if (size<=0) size = (int)strlen(smsg); 01277 cc = send(sock, smsg, size, 0); 01278 01279 if (cc<0) cc = JBXL_NET_SEND_ERROR; 01280 return cc; 01281 }
int tcp_send_mesgln | ( | int | sock, | |
char * | mesg | |||
) |
int tcp_send_mesgln(int sock, char* mesg)
TCPメッセージ(文字列)に改行(\r\n)を付け加えて送信する.
sock | ソケット記述子 | |
mesg | 送信用メッセージ |
0以上 | 送信したバイト数. | |
JBXL_NET_SEND_ERROR | 失敗. |
int tcp_send_mesgln(int sock, char* mesg)
TCPメッセージ(文字列)に改行(\r\n)を付け加えて送信する.
sock | ソケット記述子 | |
mesg | 送信用メッセージ |
0以上 | 送信したバイト数. | |
-1 | 失敗. |
Definition at line 1368 of file network.c.
01369 { 01370 int cc, sz; 01371 char* buf; 01372 01373 sz = (int)strlen(mesg) + 3; /* CR+LF+0x00 */ 01374 buf = (char*)malloc(sz); 01375 if (buf==NULL) return JBXL_NET_SEND_ERROR; 01376 01377 strncpy(buf, mesg, sz); 01378 strncat(buf, "\r\n", 2); 01379 cc = send(sock, buf, (int)strlen(buf), 0); 01380 01381 free(buf); 01382 if (cc<0) cc = JBXL_NET_SEND_ERROR; 01383 return cc; 01384 }
int tcp_server_bind | ( | int | port | ) |
TCPのサーバのソケット記述子を作り,バインドする. tcp_server_socket() との違いは listen()関数を呼び出さない点にある.
この関数内で呼び出されるネットワーク関数: socket(), bind()
port | ポート番号. |
0以上 | 作成されたソケット記述子. | |
-1 | ソケットの作成に失敗. | |
-3 | バインドに失敗. |
Definition at line 357 of file network4.c.
References socket_close().
00358 { 00359 int sofd, err; 00360 struct sockaddr_in sv_addr; 00361 00362 sofd = (int)socket(AF_INET, SOCK_STREAM, 0); 00363 if (sofd<0) return -1; 00364 00365 memset(&sv_addr, 0, sizeof(sv_addr)); 00366 sv_addr.sin_family = AF_INET; 00367 sv_addr.sin_port = htons(port); 00368 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00369 00370 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00371 if (err<0) { 00372 socket_close(sofd); 00373 return -3; 00374 } 00375 00376 return sofd; 00377 }
int tcp_server_bind_setopt | ( | int | port, | |
int | opt, | |||
const void * | optval, | |||
int | optlen | |||
) |
int tcp_server_bind_setopt(int port, int opt, const void* optval, int optlen)
TCPのサーバのソケット記述子を作り,バインドする.オプションの指定(setsockopt)が可能. tcp_server_socket() との違いは listen()関数を呼び出さない点にある.
この関数内で呼び出されるネットワーク関数: socket(), setsockopt(), bind()
port | ポート番号 | |
opt | オプションの種類 | |
optval | オプションデータ | |
optlen | optval の長さ |
0以上 | 作成されたソケット記述子. | |
-1 | ソケットの作成に失敗. | |
-2 | ソケットオプションの設定に失敗. | |
-3 | バインドに失敗. |
Definition at line 398 of file network4.c.
References socket_close().
00399 { 00400 int sofd, err; 00401 struct sockaddr_in sv_addr; 00402 00403 sofd = (int)socket(AF_INET, SOCK_STREAM, 0); 00404 if (sofd<0) return -1; 00405 00406 if (opt>0) { 00407 #ifdef WIN32 00408 err = setsockopt(sofd, SOL_SOCKET, opt, (const char*)optval, optlen); 00409 #else 00410 err = setsockopt(sofd, SOL_SOCKET, opt, optval, optlen); 00411 #endif 00412 if (err<0) { 00413 socket_close(sofd); 00414 return -2; 00415 } 00416 } 00417 00418 memset(&sv_addr, 0, sizeof(sv_addr)); 00419 sv_addr.sin_family = AF_INET; 00420 sv_addr.sin_port = htons(port); 00421 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00422 00423 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00424 if (err<0) { 00425 socket_close(sofd); 00426 return -3; 00427 } 00428 00429 return sofd; 00430 }
int tcp_server_socket | ( | int | port | ) |
int tcp_server_socket(int port)
TCPのサーバソケットを作り,リッスンにより接続要求を受けられる状態にする.
この関数に続いて accept()関数を呼ぶ事により,実際の接続待ち状態となる.
この関数内で呼び出されるネットワーク関数は socket(), bind(), listen()
port | ポート番号. |
0以上 | 作成されたソケット記述子. | |
-1 | ソケットの作成に失敗. | |
-3 | バインドに失敗. | |
-6 | リッスンの設定に失敗. |
Definition at line 252 of file network4.c.
References socket_close().
00253 { 00254 int sofd, err; 00255 struct sockaddr_in sv_addr; 00256 00257 sofd = (int)socket(AF_INET, SOCK_STREAM, 0); 00258 if (sofd<0) return -1; 00259 00260 memset(&sv_addr, 0, sizeof(sv_addr)); 00261 sv_addr.sin_family = AF_INET; 00262 sv_addr.sin_port = htons(port); 00263 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00264 00265 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00266 if (err<0) { 00267 socket_close(sofd); 00268 return -3; 00269 } 00270 00271 err = listen(sofd, 10); 00272 if (err==-1) { 00273 socket_close(sofd); 00274 return -6; 00275 } 00276 00277 return sofd; 00278 }
int tcp_server_socket_setopt | ( | int | port, | |
int | opt, | |||
const void * | optval, | |||
int | optlen | |||
) |
int tcp_server_socket_setopt(int port, int opt, const void* optval, int optlen)
TCPのサーバソケットを作り,リッスンにより接続要求を受けられる状態にする.
この関数に続いて accept()関数を呼ぶ事により,実際の接続待ち状態となる. オプションの指定(setsockopt)が可能.
この関数内で呼び出されるネットワーク関数は socket(), setsockopt(), bind(), listen()
port | ポート番号 | |
opt | オプションの種類 | |
optval | オプションデータ | |
optlen | optval の長さ |
0以上 | 作成されたソケット記述子. | |
-1 | ソケットの作成に失敗. | |
-2 | ソケットオプションの設定に失敗. | |
-3 | バインドに失敗. | |
-6 | リッスンの設定に失敗. |
Definition at line 302 of file network4.c.
References socket_close().
00303 { 00304 int sofd, err; 00305 struct sockaddr_in sv_addr; 00306 00307 sofd = (int)socket(AF_INET, SOCK_STREAM, 0); 00308 if (sofd<0) return -1; 00309 00310 memset(&sv_addr, 0, sizeof(sv_addr)); 00311 sv_addr.sin_family = AF_INET; 00312 sv_addr.sin_port = htons(port); 00313 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00314 00315 if (opt>0) { 00316 #ifdef WIN32 00317 err = setsockopt(sofd, SOL_SOCKET, opt, (const char*)optval, optlen); 00318 #else 00319 err = setsockopt(sofd, SOL_SOCKET, opt, optval, optlen); 00320 #endif 00321 if (err<0) { 00322 socket_close(sofd); 00323 return -2; 00324 } 00325 } 00326 00327 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00328 if (err<0) { 00329 socket_close(sofd); 00330 return -3; 00331 } 00332 00333 err = listen(sofd, 10); 00334 if (err==-1) { 00335 socket_close(sofd); 00336 return -6; 00337 } 00338 00339 return sofd; 00340 }
char* to_address_char4 | ( | unsigned char * | n | ) |
char* to_address_char4(unsigned char* n)
数字型の IPアドレス n 4Byteを文字型の [IPアドレス] に変換する.
n は必ず長さが 4Byteでないといけない.4Byteより少ない場合は恐らくセグメンテーションエラーを起こす.
to_address_num4()と対で使うのが安全.
n | 長さが 4byteのバイナリの [IPアドレス] |
Definition at line 1847 of file network4.c.
char* to_address_char8 | ( | unsigned char * | n | ) |
char* to_address_char8(unsigned char* n)
数字型の IPアドレス n 8Byteを文字型の [IPアドレス]/[ネットマスク] に変換する.
n は必ずネットマスクの情報を含み,長さが 8Byteでないといけない.8Byteより少ない場合は 恐らくセグメンテーションエラーを起こす.
to_address_num()と対で使うのが安全.
n | 長さが 8byteの バイナリの [IPアドレス],[ネットマスク] |
Definition at line 1756 of file network4.c.
unsigned char* to_address_num4 | ( | char * | addr, | |
int | mode | |||
) |
unsigned char* to_address_num4(char* addr, int mode)
文字型のアドレス [IPアドレス] (例:202.26.159.140)を 数字型のアドレス(unsigned char* num[4])4Byte へ変換する.
省略された場所は 0とみなされる(例:202.26 → 202.26.0.0)
addr | 変換する文字型のIPアドレス | |
mode | 0: IPアドレス以外のもの(英字)は NULL を返す. | |
mode | 0以外: FQDNはIPアドレスに変換して返す(時間がかかる) |
Definition at line 1786 of file network4.c.
References awk(), and get_ipaddr_byname_num().
Referenced by get_hostname(), and is_same_network().
01787 { 01788 unsigned char* num; 01789 char* pc; 01790 char* uc = NULL; 01791 int i; 01792 01793 if (addr==NULL) return NULL; 01794 01795 num = (unsigned char*)malloc(4); 01796 if (num==NULL) return NULL; 01797 memset(num, 0, 4); 01798 01799 // IPアドレス部の変換 01800 i = (int)strlen(addr) - 1; 01801 while (i>0 && addr[i]=='.') i--; 01802 if (i>0) { 01803 if (isalpha(addr[i])) { 01804 if (mode==0) { // mode==0なら FQDN->IPアドレス は行なわない. 01805 free(num); 01806 return NULL; 01807 } 01808 uc = (char*)get_ipaddr_byname_num(addr); 01809 if (uc==NULL) { 01810 free(num); 01811 return NULL; 01812 } 01813 } 01814 } 01815 01816 if (uc==NULL) { // IPアドレス表記の処理 01817 for (i=0; i<4; i++) { 01818 pc = awk(addr, '.', i+1); 01819 if (pc==NULL) break; 01820 num[i] = (unsigned char)atoi(pc); 01821 free(pc); 01822 } 01823 } 01824 else { // ホスト名表記の処理 01825 for (i=0; i<4; i++) num[i] = uc[i]; 01826 free(uc); 01827 } 01828 01829 return num; 01830 }
unsigned char* to_address_num8 | ( | char * | addr, | |
int | mode | |||
) |
unsigned char* to_address_num8(char* addr, int mode)
文字型のアドレス [IPアドレス]/[ネットマスク] (例:202.26.159.140/255.255.255.0)を 数字型のアドレス(unsigned char* num[8])8Byte へ変換する.
省略された場所は 0とみなされる(例:202.26/255 → 202.26.0.0/255.0.0.0)
ネットマスク部全体が省略された場合は IPアドレス部に依存する.(202.26. → 202.26.0.0/255.255.0.0)
CIDER形式にも対応.ただし,ネットマスク部の妥当性はチェックしない.
addr | 変換する文字型のIPアドレス | |
mode | 0: IPアドレス以外のもの(英字)は NULL を返す. | |
mode | 0以外: FQDNはIPアドレスに変換して返す(時間がかかる) |
Definition at line 1648 of file network4.c.
References awk(), get_ipaddr_byname_num(), Max, Min, OFF, and ON.
01649 { 01650 unsigned char* num; 01651 char* ps; 01652 char* pc; 01653 char* uc = NULL; 01654 int i; 01655 01656 if (addr==NULL) return NULL; 01657 01658 num = (unsigned char*)malloc(8); 01659 if (num==NULL) return NULL; 01660 memset(num, 0, 8); 01661 01662 01663 // IPアドレス部の変換 01664 ps = awk(addr, '/', 1); 01665 if (ps==NULL) { 01666 free(num); 01667 return NULL; 01668 } 01669 01670 i = (int)strlen(ps) - 1; 01671 while (i>0 && ps[i]=='.') i--; 01672 if (i>0) { 01673 if (isalpha(ps[i])) { 01674 if (mode==0) { // mode==0なら FQDN->IPアドレス は行なわない. 01675 free(num); 01676 free(ps); 01677 return NULL; 01678 } 01679 uc = (char*)get_ipaddr_byname_num(ps); 01680 if (uc==NULL) { 01681 free(num); 01682 free(ps); 01683 return NULL; 01684 } 01685 } 01686 } 01687 01688 if (uc==NULL) { // IPアドレス表記の処理 01689 for (i=0; i<4; i++) { 01690 pc = awk(ps, '.', i+1); 01691 if (pc==NULL) break; 01692 num[i] = (unsigned char)atoi(pc); 01693 free(pc); 01694 } 01695 } 01696 else { // ホスト名表記の処理 01697 for (i=0; i<4; i++) num[i] = uc[i]; 01698 free(uc); 01699 } 01700 free(ps); 01701 01702 ps = awk(addr, '/', 2); 01703 01704 // サブネットマスク部が省略された場合の処理 01705 if (ps==NULL) { 01706 int f = OFF; 01707 for (i=3; i>=0; i--) { 01708 if (num[i]!=0 || f==ON) { 01709 num[i+4] = 0xff; 01710 f = ON; 01711 } 01712 else { 01713 num[i+4] = 0; 01714 } 01715 } 01716 return num; 01717 } 01718 01719 // サブネットマスク部の処理 01720 for (i=0; i<4; i++) { 01721 pc = awk(ps, '.', i+1); 01722 if (pc==NULL) break; 01723 num[i+4] = (unsigned char)atoi(pc); 01724 free(pc); 01725 } 01726 free(ps); 01727 01728 // CIDER形式対応 01729 if (num[4]<=32 && num[5]==0 && num[6]==0 && num[7]==0) { 01730 int nn, cl = (int)num[4]; 01731 for (i=0; i<4; i++) { 01732 nn = 8 - Max(0, Min(8, cl-8*i)); 01733 num[i+4] = 0xff<<nn; 01734 } 01735 } 01736 01737 return num; 01738 }
int udp_bind | ( | int | sofd, | |
int | port | |||
) |
int udp_bind(int sofd, int port)
UDPソケットにポートをバインドする.
sofd | バインドするソケットの記述子. | |
port | ポート番号 |
sofd | 成功 | |
-3 | 失敗 |
Definition at line 166 of file network4.c.
References socket_close().
00167 { 00168 int err; 00169 struct sockaddr_in sv_addr; 00170 00171 if (sofd<=0) return sofd; 00172 00173 memset(&sv_addr, 0, sizeof(sv_addr)); 00174 sv_addr.sin_family = AF_INET; 00175 sv_addr.sin_port = htons(port); 00176 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00177 00178 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00179 if (err<0) { 00180 socket_close(sofd); 00181 return -3; 00182 } 00183 00184 return sofd; 00185 }
int udp_bind_setopt | ( | int | sofd, | |
int | port, | |||
int | opt, | |||
const void * | optval, | |||
int | optlen | |||
) |
int udp_bind_setopt(int sofd, int port, int opt, const void* optval, int optlen)
UDPソケットにポートをバインドする.オプションの指定(setsockopt)が可能.
sofd | バインドするソケットの記述子. | |
port | ポート番号 | |
opt | オプションの種類 | |
optval | オプションデータ | |
optlen | optval の長さ |
0以上 | 作成されたソケット記述子. | |
-2 | ソケットオプションの設定に失敗 | |
-3 | バインドに失敗. |
Definition at line 203 of file network4.c.
References socket_close().
00204 { 00205 int err; 00206 struct sockaddr_in sv_addr; 00207 00208 if (sofd<=0) return sofd; 00209 00210 memset(&sv_addr, 0, sizeof(sv_addr)); 00211 sv_addr.sin_family = AF_INET; 00212 sv_addr.sin_port = htons(port); 00213 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00214 00215 if (opt>0) { 00216 #ifdef WIN32 00217 err = setsockopt(sofd, SOL_SOCKET, opt, (const char*)optval, optlen); 00218 #else 00219 err = setsockopt(sofd, SOL_SOCKET, opt, optval, optlen); 00220 #endif 00221 if (err<0) { 00222 socket_close(sofd); 00223 return -2; 00224 } 00225 } 00226 00227 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00228 if (err<0) { 00229 socket_close(sofd); 00230 return -3; 00231 } 00232 00233 return sofd; 00234 }
int udp_client_socket | ( | char * | hostname, | |
int | port, | |||
struct sockaddr_in * | sv_addr | |||
) |
int udp_client_socket(char* hostname, int port, struct sockaddr_in* sv_addr)
UDPのクライアントソケットを作る. 正常終了した場合, *sv_addrにサーバの情報が格納される.
この関数内で呼び出されるネットワーク関数: socket(), gethostbyname()
hostname | サーバ名 | |
port | サーバポート番号 | |
sv_addr | sockaddr_in 構造体へのポインタ |
0以上 | 作成されたソケット記述子. | |
-1 | ソケットが作成できなかった. | |
-4 | サーバ情報の取得に失敗. |
Definition at line 132 of file network4.c.
References socket_close().
00133 { 00134 int sofd; 00135 struct hostent* shost; 00136 00137 sofd = (int)socket(AF_INET, SOCK_DGRAM, 0); 00138 if (sofd<0) return -1; 00139 00140 shost = gethostbyname(hostname); 00141 if (shost==NULL) { 00142 socket_close(sofd); 00143 return -4 00144 } 00145 00146 memset(sv_addr, 0, sizeof(*sv_addr)); 00147 sv_addr->sin_family = AF_INET; 00148 sv_addr->sin_port = htons(port); 00149 memcpy(&(sv_addr->sin_addr), shost->h_addr, shost->h_length); 00150 00151 return sofd; 00152 }
void udp_hole_punching | ( | int | sock, | |
struct sockaddr_in | addr, | |||
int | nm | |||
) |
void udp_hole_punching(int sock, struct sockaddr_in addr, int nm)
sock を使って,addrへ nmバイトの NULLデータを送信する.
sock | ソケット記述子 | |
addr | 相手のホストの情報が格納されて sockaddr_in 構造体 | |
nm | 送信するデータ(NULL)の長さ |
Definition at line 1970 of file network4.c.
References LBUF, and udp_send().
01971 { 01972 char data[LBUF]; 01973 01974 if (nm<=0) nm = 4; // for SLVoice 01975 else if (nm>LBUF) nm = LBUF; 01976 01977 memset(data, 0, nm); 01978 udp_send(sock, data, nm, &addr); 01979 01980 return; 01981 }
int udp_recv | ( | int | sock, | |
char * | rmsg, | |||
int | size, | |||
struct sockaddr_in * | sv_addr | |||
) |
int udp_recv(int sock, char* rmsg, int size, struct sockaddr_in* sv_addr)
recvform() をラッピングした関数.UDPデータを受信する.
sock | ソケット記述子 | |
rmsg | 受信用データバッファ | |
size | データバッファのサイズ | |
sv_addr | サーバの情報が格納された sockaddr_in 構造体へのポインタ. |
1以上 | 受信したバイト数. | |
0 | 正常切断. | |
-1 | 失敗 |
Definition at line 730 of file network4.c.
int udp_recv_wait | ( | int | sock, | |
char * | rmsg, | |||
int | size, | |||
struct sockaddr_in * | sv_addr, | |||
int | tm | |||
) |
int udp_recv_wait(int sock, char* rmsg, int size, struct sockaddr_in* sv_addr, int tm)
UDP経由でデータを受信する.
タイムアウトの設定が可能.タイムアウトに 0を指定した場合, recv_wait() 関数を呼び出した時点で読み込み可能データがなければすぐにタイムアウトとなる (RECV_TIMEOUTED が返る).
sock | ソケット記述子 | |
rmsg | 受信用データバッファ | |
size | データバッファのサイズ | |
sv_addr | サーバの情報が格納された sockaddar_in 構造体へのポインタ. | |
tm | タイムアウト時間.秒単位. |
1以上 | 受信したバイト数. | |
0 | 正常切断. | |
-1 | 失敗. | |
RECV_TIMEOUTED | タイムアウト. |
Definition at line 843 of file network4.c.
References RECV_TIMEOUTED, recv_wait(), and udp_recv().
00844 { 00845 int cc; 00846 00847 if (recv_wait(sock, tm)) { 00848 cc = udp_recv(sock, rmsg, size, sv_addr); 00849 } 00850 else { 00851 return RECV_TIMEOUTED; 00852 } 00853 return cc; 00854 }
int udp_send | ( | int | sock, | |
char * | smsg, | |||
int | size, | |||
struct sockaddr_in * | sv_addr | |||
) |
int udp_send(int sock, char* smsg, int size, struct sockaddr_in* sv_addr)
sendto() をラッピングした関数.UDP経由でデータを送る.
データ(smsg)のサイズ sizeに0以下を指定した場合は,smsgは文字列で あると見なしてサイズを自動的に計算する.
sock | ソケット記述子 | |
smsg | 送信するデータ | |
size | 送信するデータ(smsg)のサイズ.サイズが 0以下の場合は smsgは文字列であるとみなす. | |
sv_addr | サーバの情報を格納する sockaddar_in 構造体へのポインタ. |
0以上 | 送信したバイト数. | |
-1 | 失敗 |
Definition at line 760 of file network4.c.
int udp_server_socket | ( | int | port | ) |
int udp_server_socket(int port)
UDPのサーバソケットを作り,接続待ち状態になる.
この関数内で呼び出されるネットワーク関数: socket(), bind()
port | ポート番号 |
0以上 | 作成されたソケット記述子. | |
-1 | ソケットが作成できなかった. | |
-3 | バインドに失敗. |
Definition at line 31 of file network4.c.
References socket_close().
00032 { 00033 int sofd, err; 00034 struct sockaddr_in sv_addr; 00035 00036 sofd = (int)socket(AF_INET, SOCK_DGRAM, 0); 00037 if (sofd<0) return -1; 00038 00039 memset(&sv_addr, 0, sizeof(sv_addr)); 00040 sv_addr.sin_family = AF_INET; 00041 sv_addr.sin_port = htons(port); 00042 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00043 00044 // TIME_WAIT しない設定. 00045 /* struct linger lg; 00046 lg.l_onoff = 1; 00047 lg.l_linger = 0; 00048 err = setsockopt(sofd, SOL_SOCKET, SO_LINGER, &lg, sizeof(lg)); 00049 if (err<0) { 00050 socket_close(sofd); 00051 return -2; 00052 } 00053 */ 00054 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00055 if (err<0) { 00056 socket_close(sofd); 00057 return -3; 00058 } 00059 00060 return sofd; 00061 }
int udp_server_socket_setopt | ( | int | port, | |
int | opt, | |||
const void * | optval, | |||
int | optlen | |||
) |
int udp_server_socket_setopt(int port, int opt, const void* optval, int optlen)
UDPのサーバソケットを作り,接続待ち状態になる.オプションの指定(setsockopt)が可能.
この関数内で呼び出されるネットワーク関数: socket(), setsockopt(), bind()
port | ポート番号 | |
opt | オプションの種類 | |
optval | オプションデータ | |
optlen | optval の長さ |
0以上 | 作成されたソケット記述子. | |
-1 | ソケットが作成できなかった. | |
-2 | ソケットオプションの設定に失敗. | |
-3 | バインドに失敗. |
Definition at line 81 of file network4.c.
References socket_close().
00082 { 00083 int sofd, err; 00084 struct sockaddr_in sv_addr; 00085 00086 sofd = (int)socket(AF_INET, SOCK_DGRAM, 0); 00087 if (sofd<0) return -1; 00088 00089 memset(&sv_addr, 0, sizeof(sv_addr)); 00090 sv_addr.sin_family = AF_INET; 00091 sv_addr.sin_port = htons(port); 00092 sv_addr.sin_addr.s_addr = htonl(INADDR_ANY); 00093 00094 if (opt>0) { 00095 #ifdef WIN32 00096 err = setsockopt(sofd, SOL_SOCKET, opt, (const char*)optval, optlen); 00097 #else 00098 err = setsockopt(sofd, SOL_SOCKET, opt, optval, optlen); 00099 #endif 00100 if (err<0) { 00101 socket_close(sofd); 00102 return -2; 00103 } 00104 } 00105 00106 err = bind(sofd, (struct sockaddr*)&sv_addr, sizeof(sv_addr)); 00107 if (err<0) { 00108 socket_close(sofd); 00109 return -3; 00110 } 00111 00112 return sofd; 00113 }