aboutsummaryrefslogtreecommitdiff
path: root/server.c
diff options
context:
space:
mode:
authorHenryk Plötz <henryk@ploetzli.ch>2014-10-03 20:04:14 +0200
committerHenryk Plötz <henryk@ploetzli.ch>2014-10-03 20:04:14 +0200
commitc44d8b51ffb5a413f8bbdbd9991bbc573853e397 (patch)
treee7f2e644de620879f610c909c405cbc4e44d6062 /server.c
parent0e5b2871ca6456b01d4bf037a6e68badf1ff1a41 (diff)
downloadtinydnssec-c44d8b51ffb5a413f8bbdbd9991bbc573853e397.tar.gz
tinydnssec-c44d8b51ffb5a413f8bbdbd9991bbc573853e397.tar.bz2
Apply patch djbdns-1.05-test27.diff.bz2
Source was http://www.fefe.de/dns/djbdns-1.05-test27.diff.bz2, SHA1 f0380ec1866f49c0bcf6369a923ac0a4a5095da8
Diffstat (limited to 'server.c')
-rw-r--r--server.c100
1 files changed, 80 insertions, 20 deletions
diff --git a/server.c b/server.c
index e486fe1..d52ce87 100644
--- a/server.c
+++ b/server.c
@@ -4,6 +4,7 @@
#include "buffer.h"
#include "strerr.h"
#include "ip4.h"
+#include "ip6.h"
#include "uint16.h"
#include "ndelay.h"
#include "socket.h"
@@ -11,13 +12,16 @@
#include "qlog.h"
#include "response.h"
#include "dns.h"
+#include "alloc.h"
+#include "iopause.h"
+#include "str.h"
extern char *fatal;
extern char *starting;
extern int respond(char *,char *,char *);
extern void initialize(void);
-static char ip[4];
+static char ip[16];
static uint16 port;
static char buf[513];
@@ -25,6 +29,11 @@ static int len;
static char *q;
+void nomem()
+{
+ strerr_die2x(111,fatal,"out of memory");
+}
+
static int doit(void)
{
unsigned int pos;
@@ -82,35 +91,86 @@ static int doit(void)
int main()
{
char *x;
- int udp53;
+ int *udp53;
+ unsigned int off;
+ unsigned int cnt;
+ iopause_fd *iop;
x = env_get("IP");
if (!x)
strerr_die2x(111,fatal,"$IP not set");
- if (!ip4_scan(x,ip))
- strerr_die3x(111,fatal,"unable to parse IP address ",x);
-
- udp53 = socket_udp();
- if (udp53 == -1)
- strerr_die2sys(111,fatal,"unable to create UDP socket: ");
- if (socket_bind4_reuse(udp53,ip,53) == -1)
- strerr_die2sys(111,fatal,"unable to bind UDP socket: ");
-
+ off=cnt=0;
+ while (x[off]) {
+ unsigned int l;
+ char dummy[16];
+ l=ip6_scan(x+off,dummy);
+ if (!l)
+ strerr_die3x(111,fatal,"unable to parse IP address ",x+off);
+ cnt++;
+ if (!x[off+l]) break;
+ if (x[off+l]=='%')
+ while (x[off+l] && x[off+l]!=',') ++l;
+ if (x[off+l]!=',')
+ strerr_die3x(111,fatal,"unable to parse IP address ",x+off);
+ off+=l+1;
+ }
+ udp53=(int *) alloc(sizeof(int) *cnt);
+ if (!udp53) nomem();
+ iop=(iopause_fd *) alloc(sizeof(*iop) * cnt);
+ if (!iop) nomem();
+
+ off=cnt=0;
+ while (x[off]) {
+ unsigned int l;
+ uint32 ifid=0;
+ l=ip6_scan(x+off,ip);
+ udp53[cnt] = socket_udp6();
+ if (udp53[cnt] == -1)
+ strerr_die2sys(111,fatal,"unable to create UDP socket: ");
+ if (x[off+l]=='%') {
+ char* interface=x+off+l+1;
+ int Len=str_chr(interface,',');
+ if (interface[Len]) {
+ interface[Len]=0;
+ ifid=socket_getifidx(interface);
+ interface[Len]=',';
+ } else
+ ifid=socket_getifidx(interface);
+ l+=Len;
+ }
+ if (socket_bind6_reuse(udp53[cnt],ip,53,ifid) == -1)
+ strerr_die2sys(111,fatal,"unable to bind UDP socket: ");
+ ndelay_off(udp53[cnt]);
+ socket_tryreservein(udp53[cnt],65536);
+ iop[cnt].fd=udp53[cnt];
+ iop[cnt].events=IOPAUSE_READ;
+ cnt++;
+ if (!x[off+l]) break;
+ off+=l+1;
+ }
droproot(fatal);
initialize();
-
- ndelay_off(udp53);
- socket_tryreservein(udp53,65536);
buffer_putsflush(buffer_2,starting);
for (;;) {
- len = socket_recv4(udp53,buf,sizeof buf,ip,&port);
- if (len < 0) continue;
- if (!doit()) continue;
- if (response_len > 512) response_tc();
- socket_send4(udp53,response,response_len,ip,port);
- /* may block for buffer space; if it fails, too bad */
+ struct taia stamp;
+ struct taia deadline;
+ unsigned int i;
+ uint32 ifid;
+ taia_now(&stamp);
+ taia_uint(&deadline,300);
+ taia_add(&deadline,&deadline,&stamp);
+ iopause(iop,cnt,&deadline,&stamp);
+ for (i=0;i<cnt;i++)
+ if (iop[i].revents) {
+ len = socket_recv6(udp53[i],buf,sizeof buf,ip,&port,&ifid);
+ if (len < 0) continue;
+ if (!doit()) continue;
+ if (response_len > 512) response_tc();
+ socket_send6(udp53[i],response,response_len,ip,port,ifid);
+ /* may block for buffer space; if it fails, too bad */
+ }
}
}