diff options
author | jjako <jjako> | 2004-01-28 09:27:34 +0000 |
---|---|---|
committer | jjako <jjako> | 2004-01-28 09:27:34 +0000 |
commit | 1ea66348518ad1d438ea14bc7a16244bbb49b9a0 (patch) | |
tree | 7811c242f39999321b4efd8c0fcacbda8bc511f3 /ggsn | |
parent | 3eaf453e06109e6117ce95dfb3c0fd37f5dc0471 (diff) |
Added FreeBSD route capability
Diffstat (limited to 'ggsn')
-rw-r--r-- | ggsn/tun.c | 100 |
1 files changed, 49 insertions, 51 deletions
@@ -421,7 +421,17 @@ int tun_setaddr(struct tun_t *this, close(fd); this->addrs++; - return tun_sifflags(this, IFF_UP | IFF_RUNNING); + + /* On linux the route to the interface is set automatically + on FreeBSD we have to do this manually */ + +#if defined(__FreeBSD__) + tun_sifflags(this, IFF_UP | IFF_RUNNING); /* TODO */ + return tun_addroute(this, addr, addr, netmask); +#else + return tun_sifflags(this, IFF_UP | IFF_RUNNING); +#endif + } int tun_addroute(struct tun_t *this, @@ -430,7 +440,8 @@ int tun_addroute(struct tun_t *this, struct in_addr *mask) { - /* TODO: Learn how to set routing table on sun and FreeBSD */ + + /* TODO: Learn how to set routing table on sun */ #ifdef __linux__ struct rtentry r; @@ -463,67 +474,53 @@ int tun_addroute(struct tun_t *this, #elif defined(__FreeBSD__) -struct my_rt -{ - struct rt_msghdr rt; - struct sockaddr_in dst; - struct sockaddr_in gate; - struct sockaddr_in mask; -} my_rt; +struct { + struct rt_msghdr rt; + struct sockaddr_in dst; + struct sockaddr_in gate; + struct sockaddr_in mask; +} req; - int s; + int fd; struct rt_msghdr *rtm; - struct sockaddr_in *dst, *gate, *mask; - - if((s = socket(AF_ROUTE, SOCK_RAW, 0)) == -1) - { - sys_err(LOG_ERR, __FILE__, __LINE__, errno, - "socket() failed"); - return -1; - } - memset(&my_rt, 0x00, sizeof(my_rt)); + if((fd = socket(AF_ROUTE, SOCK_RAW, 0)) == -1) { + sys_err(LOG_ERR, __FILE__, __LINE__, errno, + "socket() failed"); + return -1; + } - rtm = &my_rt.rt; + memset(&req, 0x00, sizeof(req)); - dst = &my_rt.dst; - gate = &my_rt.gate; - mask = &my_rt.mask; + rtm = &req.rt; + rtm->rtm_msglen = sizeof(req); + rtm->rtm_version = RTM_VERSION; rtm->rtm_type = RTM_ADD; rtm->rtm_flags = RTF_UP | RTF_GATEWAY | RTF_STATIC; /* TODO */ - rtm->rtm_msglen = sizeof(my_rt); - rtm->rtm_version = RTM_VERSION; - rtm->rtm_seq = 1234; /* TODO */ rtm->rtm_addrs = RTA_DST | RTA_GATEWAY | RTA_NETMASK; rtm->rtm_pid = getpid(); + rtm->rtm_seq = 0044; /* TODO */ - dst->sin_family = AF_INET; - dst->sin_len = sizeof(*dst); - dst->sin_addr.s_addr = dst->s_addr; - - mask->sin_family = AF_INET; - mask->sin_len = sizeof(*mask); - mask->sin_addr.s_addr = mask->s_addr; - - gate->sin_family = AF_INET; - gate->sin_len = sizeof(*gate); - gate->sin_addr.s_addr = gateway->s_addr; - - AGAIN: - if(write(s, rtm, rtm->rtm_msglen) < 0) - { - if(errno == EEXIST && rtm->rtm_type == RTM_ADD) - { - rtm->rtm_type = RTM_CHANGE; - goto AGAIN; - } - sys_err(LOG_ERR, __FILE__, __LINE__, errno, - "write() failed"); - return -1; - } - return 0; + req.dst.sin_family = AF_INET; + req.dst.sin_len = sizeof(req.dst); + req.mask.sin_family = AF_INET; + req.mask.sin_len = sizeof(req.mask); + req.gate.sin_family = AF_INET; + req.gate.sin_len = sizeof(req.gate); + + req.dst.sin_addr.s_addr = dst->s_addr; + req.mask.sin_addr.s_addr = mask->s_addr; + req.gate.sin_addr.s_addr = gateway->s_addr; + if(write(fd, rtm, rtm->rtm_msglen) < 0) { + sys_err(LOG_ERR, __FILE__, __LINE__, errno, + "write() failed"); + close(fd); + return -1; + } + close(fd); + #endif return 0; @@ -636,6 +633,7 @@ int tun_new(struct tun_t **tun) snprintf((*tun)->devname, sizeof((*tun)->devname), "tun%d", devnum); (*tun)->devname[sizeof((*tun)->devname)] = 0; + #endif return 0; |