diff options
author | vda <vda@69ca8d6d-28ef-0310-b511-8ec308f3f277> | 2007-01-11 16:50:23 +0000 |
---|---|---|
committer | vda <vda@69ca8d6d-28ef-0310-b511-8ec308f3f277> | 2007-01-11 16:50:23 +0000 |
commit | 2aef1bcb59b97f647bf63b5025c069200f42ec97 (patch) | |
tree | 369636a4a765a571e1c6a6ecf2a52ca0131cc90e /libbb | |
parent | a4c67f25b5e304a1b0666bdf1ae3d4c96cecc1e7 (diff) | |
download | busybox-w32-2aef1bcb59b97f647bf63b5025c069200f42ec97.tar.gz busybox-w32-2aef1bcb59b97f647bf63b5025c069200f42ec97.tar.bz2 busybox-w32-2aef1bcb59b97f647bf63b5025c069200f42ec97.zip |
ipv6-ization efforts continue. Few bugs are found,
unknown number likely introduced...
git-svn-id: svn://busybox.net/trunk/busybox@17250 69ca8d6d-28ef-0310-b511-8ec308f3f277
Diffstat (limited to 'libbb')
-rw-r--r-- | libbb/xconnect.c | 60 |
1 files changed, 50 insertions, 10 deletions
diff --git a/libbb/xconnect.c b/libbb/xconnect.c index 6e85322cf..a5b16d982 100644 --- a/libbb/xconnect.c +++ b/libbb/xconnect.c | |||
@@ -83,8 +83,20 @@ int xconnect_tcp_v4(struct sockaddr_in *s_addr) | |||
83 | /* "New" networking API */ | 83 | /* "New" networking API */ |
84 | 84 | ||
85 | 85 | ||
86 | //extern int xsocket_stream_ip4or6(sa_family_t *fp); | 86 | void set_port(len_and_sockaddr *lsa, unsigned port) |
87 | //extern len_and_sockaddr* dotted2sockaddr(const char *dotted, int def_port); | 87 | { |
88 | #if ENABLE_FEATURE_IPV6 | ||
89 | if (lsa->sa.sa_family == AF_INET6) { | ||
90 | lsa->sin6.sin6_port = port; | ||
91 | return; | ||
92 | } | ||
93 | #endif | ||
94 | if (lsa->sa.sa_family == AF_INET) { | ||
95 | lsa->sin.sin_port = port; | ||
96 | return; | ||
97 | } | ||
98 | /* What? UNIX socket? IPX?? :) */ | ||
99 | } | ||
88 | 100 | ||
89 | /* peer: "1.2.3.4[:port]", "www.google.com[:port]" | 101 | /* peer: "1.2.3.4[:port]", "www.google.com[:port]" |
90 | * port: if neither of above specifies port # | 102 | * port: if neither of above specifies port # |
@@ -96,7 +108,6 @@ static len_and_sockaddr* str2sockaddr(const char *host, int port, int ai_flags) | |||
96 | struct addrinfo *result = NULL; | 108 | struct addrinfo *result = NULL; |
97 | const char *org_host = host; /* only for error msg */ | 109 | const char *org_host = host; /* only for error msg */ |
98 | const char *cp; | 110 | const char *cp; |
99 | char service[sizeof(int)*3 + 1]; | ||
100 | struct addrinfo hint; | 111 | struct addrinfo hint; |
101 | 112 | ||
102 | /* Ugly parsing of host:addr */ | 113 | /* Ugly parsing of host:addr */ |
@@ -119,9 +130,7 @@ static len_and_sockaddr* str2sockaddr(const char *host, int port, int ai_flags) | |||
119 | if (ENABLE_FEATURE_IPV6 && *cp != ':') | 130 | if (ENABLE_FEATURE_IPV6 && *cp != ':') |
120 | cp++; /* skip ']' */ | 131 | cp++; /* skip ']' */ |
121 | cp++; /* skip ':' */ | 132 | cp++; /* skip ':' */ |
122 | } else { | 133 | port = xatou16(cp); |
123 | utoa_to_buf(port, service, sizeof(service)); | ||
124 | cp = service; | ||
125 | } | 134 | } |
126 | 135 | ||
127 | memset(&hint, 0 , sizeof(hint)); | 136 | memset(&hint, 0 , sizeof(hint)); |
@@ -132,13 +141,14 @@ static len_and_sockaddr* str2sockaddr(const char *host, int port, int ai_flags) | |||
132 | /* Needed. Or else we will get each address thrice (or more) | 141 | /* Needed. Or else we will get each address thrice (or more) |
133 | * for each possible socket type (tcp,udp,raw...): */ | 142 | * for each possible socket type (tcp,udp,raw...): */ |
134 | hint.ai_socktype = SOCK_STREAM; | 143 | hint.ai_socktype = SOCK_STREAM; |
135 | hint.ai_flags = ai_flags | AI_NUMERICSERV; | 144 | hint.ai_flags = ai_flags; |
136 | rc = getaddrinfo(host, cp, &hint, &result); | 145 | rc = getaddrinfo(host, NULL, &hint, &result); |
137 | if (rc || !result) | 146 | if (rc || !result) |
138 | bb_error_msg_and_die("bad address '%s'", org_host); | 147 | bb_error_msg_and_die("bad address '%s'", org_host); |
139 | r = xmalloc(offsetof(len_and_sockaddr, sa) + result->ai_addrlen); | 148 | r = xmalloc(offsetof(len_and_sockaddr, sa) + result->ai_addrlen); |
140 | r->len = result->ai_addrlen; | 149 | r->len = result->ai_addrlen; |
141 | memcpy(&r->sa, result->ai_addr, result->ai_addrlen); | 150 | memcpy(&r->sa, result->ai_addr, result->ai_addrlen); |
151 | set_port(r, port); | ||
142 | freeaddrinfo(result); | 152 | freeaddrinfo(result); |
143 | return r; | 153 | return r; |
144 | } | 154 | } |
@@ -153,7 +163,7 @@ static len_and_sockaddr* dotted2sockaddr(const char *host, int port) | |||
153 | return str2sockaddr(host, port, NI_NUMERICHOST); | 163 | return str2sockaddr(host, port, NI_NUMERICHOST); |
154 | } | 164 | } |
155 | 165 | ||
156 | static int xsocket_stream_ip4or6(len_and_sockaddr *lsa) | 166 | static int xsocket_stream(len_and_sockaddr *lsa) |
157 | { | 167 | { |
158 | int fd; | 168 | int fd; |
159 | #if ENABLE_FEATURE_IPV6 | 169 | #if ENABLE_FEATURE_IPV6 |
@@ -186,7 +196,7 @@ int create_and_bind_stream_or_die(const char *bindaddr, int port) | |||
186 | USE_FEATURE_IPV6(sizeof(struct sockaddr_in6)) | 196 | USE_FEATURE_IPV6(sizeof(struct sockaddr_in6)) |
187 | SKIP_FEATURE_IPV6(sizeof(struct sockaddr_in)) | 197 | SKIP_FEATURE_IPV6(sizeof(struct sockaddr_in)) |
188 | ); | 198 | ); |
189 | fd = xsocket_stream_ip4or6(lsa); | 199 | fd = xsocket_stream(lsa); |
190 | } | 200 | } |
191 | setsockopt_reuseaddr(fd); | 201 | setsockopt_reuseaddr(fd); |
192 | xbind(fd, &lsa->sa, lsa->len); | 202 | xbind(fd, &lsa->sa, lsa->len); |
@@ -209,3 +219,33 @@ int create_and_connect_stream_or_die(const char *peer, int port) | |||
209 | free(lsa); | 219 | free(lsa); |
210 | return fd; | 220 | return fd; |
211 | } | 221 | } |
222 | |||
223 | int xconnect_stream(const len_and_sockaddr *lsa) | ||
224 | { | ||
225 | int fd = xsocket(lsa->sa.sa_family, SOCK_STREAM, 0); | ||
226 | xconnect(fd, &lsa->sa, lsa->len); | ||
227 | return fd; | ||
228 | } | ||
229 | |||
230 | static char* sockaddr2str(const struct sockaddr *sa, socklen_t salen, int flags) | ||
231 | { | ||
232 | char host[128]; | ||
233 | char serv[16]; | ||
234 | int rc = getnameinfo(sa, salen, | ||
235 | host, sizeof(host), | ||
236 | serv, sizeof(serv), | ||
237 | flags | NI_NUMERICSERV /* do not resolve port# */ | ||
238 | ); | ||
239 | if (rc) return NULL; | ||
240 | return xasprintf("%s:%s", host, serv); | ||
241 | } | ||
242 | |||
243 | char* xmalloc_sockaddr2host(const struct sockaddr *sa, socklen_t salen) | ||
244 | { | ||
245 | return sockaddr2str(sa, salen, 0); | ||
246 | } | ||
247 | |||
248 | char* xmalloc_sockaddr2dotted(const struct sockaddr *sa, socklen_t salen) | ||
249 | { | ||
250 | return sockaddr2str(sa, salen, NI_NUMERICHOST); | ||
251 | } | ||