Introduction
Introduction Statistics Contact Development Disclaimer Help
Adding IPv6 support. - geomyidae - A small C-based gopherd.
git clone git://bitreich.org/geomyidae/ git://enlrupgkhuxnvlhsf6lc3fziv5h2hhfri…
Log
Files
Refs
Tags
README
LICENSE
---
commit 0989e87037363bc4977b23da4304c51284026a14
parent 2878cc2d95ecac6eef2c33c8cd79a126dc9aa7f0
Author: Christoph Lohmann <[email protected]>
Date: Sat, 13 Apr 2013 21:04:46 +0200
Adding IPv6 support.
Diffstat:
M main.c | 94 +++++++++++++++++++++--------…
1 file changed, 65 insertions(+), 29 deletions(-)
---
diff --git a/main.c b/main.c
@@ -242,6 +242,40 @@ initsignals(void)
signal(SIGPIPE, SIG_IGN);
}
+int
+getlistenfd(struct addrinfo *hints, char *bindip, char *port)
+{
+ struct addrinfo *ai, *rp;
+ int on, listfd;
+
+ listfd = -1;
+
+ if(getaddrinfo(bindip, port, hints, &ai))
+ return -1;
+ if(ai == nil)
+ return -1;
+
+ on = 1;
+ for(rp = ai; rp != nil; rp = rp->ai_next) {
+ listfd = socket(rp->ai_family, rp->ai_socktype,
+ rp->ai_protocol);
+ if(listfd < 0)
+ continue;
+ if(setsockopt(listfd, SOL_SOCKET, SO_REUSEADDR, &on,
+ sizeof(on)) < 0) {
+ break;
+ }
+ if(bind(listfd, rp->ai_addr, rp->ai_addrlen) == 0)
+ break;
+ close(listfd);
+ }
+ if(rp == nil)
+ return -1;
+ freeaddrinfo(ai);
+
+ return listfd;
+}
+
void
usage(void)
{
@@ -256,10 +290,10 @@ usage(void)
int
main(int argc, char *argv[])
{
- struct addrinfo hints, *ai, *rp;
+ struct addrinfo hints;
struct sockaddr_storage clt;
socklen_t cltlen;
- int sock, dofork, on;
+ int sock, dofork, v4, v6;
char *port, *base, clienth[NI_MAXHOST], clientp[NI_MAXSERV];
char *user, *group, *bindip, *ohost, *sport;
struct passwd *us;
@@ -275,8 +309,16 @@ main(int argc, char *argv[])
bindip = nil;
ohost = nil;
sport = port;
+ v4 = 1;
+ v6 = 1;
ARGBEGIN {
+ case '4':
+ v6 = 0;
+ break;
+ case '6':
+ v4 = 0;
+ break;
case 'b':
base = EARGF(usage());
break;
@@ -318,8 +360,9 @@ main(int argc, char *argv[])
free(ohost);
return 1;
}
- } else
+ } else {
ohost = gstrdup(ohost);
+ }
if(group != nil) {
if((gr = getgrnam(group)) == nil) {
@@ -349,36 +392,29 @@ main(int argc, char *argv[])
memset(&hints, 0, sizeof(hints));
hints.ai_flags = AI_PASSIVE;
hints.ai_socktype = SOCK_STREAM;
- hints.ai_protocol = IPPROTO_TCP;
- hints.ai_family = AF_INET;
- if(getaddrinfo(bindip, port, &hints, &ai)) {
- perror("getaddrinfo");
- return 1;
- }
- if(ai == nil) {
- perror("getaddrinfo");
- return 1;
+ if(bindip)
+ hints.ai_flags |= AI_CANONNAME;
+
+ if(v6) {
+ hints.ai_family = PF_INET6;
+ listfd = getlistenfd(&hints, bindip, port);
+ if(!v4 && listfd < 0) {
+ perror("getlistenfd");
+ return 1;
+ }
}
-
- on = 1;
- for(rp = ai; rp != nil; rp = rp->ai_next) {
- listfd = socket(rp->ai_family, rp->ai_socktype,
- rp->ai_protocol);
- if(listfd < 0)
- continue;
- if(setsockopt(listfd, SOL_SOCKET, SO_REUSEADDR, &on,
- sizeof(on)) < 0) {
- break;
+ if(v4) {
+ hints.ai_family = PF_INET;
+ listfd = getlistenfd(&hints, bindip, port);
+ if(listfd < 0) {
+ perror("getlistenfd");
+ return 1;
}
- if(bind(listfd, rp->ai_addr, rp->ai_addrlen) == 0)
- break;
- close(listfd);
}
- if(rp == nil) {
- perror("getaddrinfo");
+ if(listfd < 0) {
+ perror("You did not specify and TCP protocol.");
return 1;
}
- freeaddrinfo(ai);
if(listen(listfd, 255)) {
perror("listen");
@@ -416,7 +452,7 @@ main(int argc, char *argv[])
getnameinfo((struct sockaddr *)&clt, cltlen, clienth,
sizeof(clienth), clientp, sizeof(clientp),
- NI_NUMERICHOST);
+ NI_NUMERICHOST|NI_NUMERICSERV);
switch(fork()) {
case -1:
You are viewing proxied material from bitreich.org. The copyright of proxied material belongs to its original authors. Any comments or complaints in relation to proxied material should be directed to the original authors of the content concerned. Please see the disclaimer for more details.