5623bea21b0ea37caae06bd4dbfd8f8b9ddb24a8
[freeradius.git] / src / main / listen.c
1 /*
2  * listen.c     Handle socket stuff
3  *
4  * Version:     $Id$
5  *
6  *   This program is free software; you can redistribute it and/or modify
7  *   it under the terms of the GNU General Public License as published by
8  *   the Free Software Foundation; either version 2 of the License, or
9  *   (at your option) any later version.
10  *
11  *   This program is distributed in the hope that it will be useful,
12  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
13  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  *   GNU General Public License for more details.
15  *
16  *   You should have received a copy of the GNU General Public License
17  *   along with this program; if not, write to the Free Software
18  *   Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19  *
20  * Copyright 2005,2006  The FreeRADIUS server project
21  * Copyright 2005  Alan DeKok <aland@ox.org>
22  */
23
24 #include <freeradius-devel/ident.h>
25 RCSID("$Id$")
26
27 #include <freeradius-devel/radiusd.h>
28 #include <freeradius-devel/modules.h>
29 #include <freeradius-devel/rad_assert.h>
30 #include <freeradius-devel/vqp.h>
31 #include <freeradius-devel/dhcp.h>
32
33 #include <freeradius-devel/vmps.h>
34 #include <freeradius-devel/detail.h>
35
36 #ifdef WITH_UDPFROMTO
37 #include <freeradius-devel/udpfromto.h>
38 #endif
39
40 #ifdef HAVE_SYS_RESOURCE_H
41 #include <sys/resource.h>
42 #endif
43
44 #ifdef HAVE_NET_IF_H
45 #include <net/if.h>
46 #endif
47
48 #ifdef HAVE_FCNTL_H
49 #include <fcntl.h>
50 #endif
51
52
53 /*
54  *      We'll use this below.
55  */
56 typedef int (*rad_listen_parse_t)(CONF_SECTION *, rad_listen_t *);
57 typedef void (*rad_listen_free_t)(rad_listen_t *);
58
59 typedef struct rad_listen_master_t {
60         rad_listen_parse_t      parse;
61         rad_listen_free_t       free;
62         rad_listen_recv_t       recv;
63         rad_listen_send_t       send;
64         rad_listen_print_t      print;
65         rad_listen_encode_t     encode;
66         rad_listen_decode_t     decode;
67 } rad_listen_master_t;
68
69 typedef struct listen_socket_t {
70         /*
71          *      For normal sockets.
72          */
73         fr_ipaddr_t     ipaddr;
74         int             port;
75 #ifdef SO_BINDTODEVICE
76         const char              *interface;
77 #endif
78         RADCLIENT_LIST  *clients;
79 } listen_socket_t;
80
81 static rad_listen_t *listen_alloc(RAD_LISTEN_TYPE type);
82
83 /*
84  *      Find a per-socket client.
85  */
86 RADCLIENT *client_listener_find(const rad_listen_t *listener,
87                                 const fr_ipaddr_t *ipaddr, int src_port)
88 {
89 #ifdef WITH_DYNAMIC_CLIENTS
90         int rcode;
91         listen_socket_t *sock;
92         REQUEST *request;
93         RADCLIENT *created;
94 #endif
95         time_t now;
96         RADCLIENT *client;
97         RADCLIENT_LIST *clients;
98
99         rad_assert(listener != NULL);
100         rad_assert(ipaddr != NULL);
101
102         clients = ((listen_socket_t *)listener->data)->clients;
103
104         /*
105          *      This HAS to have been initialized previously.
106          */
107         rad_assert(clients != NULL);
108
109         client = client_find(clients, ipaddr);
110         if (!client) {
111                 static time_t last_printed = 0;
112                 char name[256], buffer[128];
113                                         
114 #ifdef WITH_DYNAMIC_CLIENTS
115         unknown:                /* used only for dynamic clients */
116 #endif
117
118                 /*
119                  *      DoS attack quenching, but only in debug mode.
120                  *      If they're running in debug mode, show them
121                  *      every packet.
122                  */
123                 if (debug_flag == 0) {
124                         now = time(NULL);
125                         if (last_printed == now) return NULL;
126                         
127                         last_printed = now;
128                 }
129
130                 listener->print(listener, name, sizeof(name));
131
132                 radlog(L_ERR, "Ignoring request to %s from unknown client %s port %d",
133                        name, inet_ntop(ipaddr->af, &ipaddr->ipaddr,
134                                        buffer, sizeof(buffer)),
135                        src_port);
136                 return NULL;
137         }
138
139 #ifndef WITH_DYNAMIC_CLIENTS
140         return client;          /* return the found client. */
141 #else
142
143         /*
144          *      No server defined, and it's not dynamic.  Return it.
145          */
146         if (!client->client_server && !client->dynamic) return client;
147
148         now = time(NULL);
149         
150         /*
151          *      It's a dynamically generated client, check it.
152          */
153         if (client->dynamic && (src_port != 0)) {
154                 /*
155                  *      Lives forever.  Return it.
156                  */
157                 if (client->lifetime == 0) return client;
158                 
159                 /*
160                  *      Rate-limit the deletion of known clients.
161                  *      This makes them last a little longer, but
162                  *      prevents the server from melting down if (say)
163                  *      10k clients all expire at once.
164                  */
165                 if (now == client->last_new_client) return client;
166
167                 /*
168                  *      It's not dead yet.  Return it.
169                  */
170                 if ((client->created + client->lifetime) > now) return client;
171                 
172                 /*
173                  *      This really puts them onto a queue for later
174                  *      deletion.
175                  */
176                 client_delete(clients, client);
177
178                 /*
179                  *      Go find the enclosing network again.
180                  */
181                 client = client_find(clients, ipaddr);
182
183                 /*
184                  *      WTF?
185                  */
186                 if (!client) goto unknown;
187                 if (!client->client_server) goto unknown;
188
189                 /*
190                  *      At this point, 'client' is the enclosing
191                  *      network that configures where dynamic clients
192                  *      can be defined.
193                  */
194                 rad_assert(client->dynamic == 0);
195         } else {
196                 /*
197                  *      The IP is unknown, so we've found an enclosing
198                  *      network.  Enable DoS protection.  We only
199                  *      allow one new client per second.  Known
200                  *      clients aren't subject to this restriction.
201                  */
202                 if (now == client->last_new_client) goto unknown;
203         }
204
205         client->last_new_client = now;
206
207         request = request_alloc();
208         if (!request) goto unknown;
209
210         request->listener = listener;
211         request->client = client;
212         request->packet = rad_alloc(0);
213         if (!request->packet) {
214                 request_free(&request);
215                 goto unknown;
216         }
217         request->reply = rad_alloc(0);
218         if (!request->reply) {
219                 request_free(&request);
220                 goto unknown;
221         }
222         request->packet->timestamp = request->timestamp;
223         request->number = 0;
224         request->priority = listener->type;
225         request->server = client->client_server;
226         request->root = &mainconfig;
227
228         /*
229          *      Run a fake request through the given virtual server.
230          *      Look for FreeRADIUS-Client-IP-Address
231          *               FreeRADIUS-Client-Secret
232          *              ...
233          *
234          *      and create the RADCLIENT structure from that.
235          */
236
237         sock = listener->data;
238         request->packet->sockfd = listener->fd;
239         request->packet->src_ipaddr = *ipaddr;
240         request->packet->src_port = 0; /* who cares... */
241         request->packet->dst_ipaddr = sock->ipaddr;
242         request->packet->dst_port = sock->port;
243
244         request->reply->sockfd = request->packet->sockfd;
245         request->reply->dst_ipaddr = request->packet->src_ipaddr;
246         request->reply->src_ipaddr = request->packet->dst_ipaddr;
247         request->reply->dst_port = request->packet->src_port;
248         request->reply->src_port = request->packet->dst_port;
249         request->reply->id = request->packet->id;
250         request->reply->code = 0; /* UNKNOWN code */
251
252         
253         DEBUG("server %s {", request->server);
254
255         rcode = module_authorize(0, request);
256
257         DEBUG("} # server %s", request->server);
258
259         if (rcode != RLM_MODULE_OK) {
260                 request_free(&request);
261                 goto unknown;
262         }
263
264         /*
265          *      If the client was updated by rlm_dynamic_clients,
266          *      don't create the client from attribute-value pairs.
267          */
268         if (request->client == client) {
269                 created = client_create(clients, request);
270         } else {
271                 created = request->client;
272
273                 /*
274                  *      This frees the client if it isn't valid.
275                  */
276                 if (!client_validate(clients, client, created)) goto unknown;
277         }
278         request_free(&request);
279
280         if (!created) goto unknown;
281
282         return created;
283 #endif
284 }
285
286 static int listen_bind(rad_listen_t *this);
287
288
289 /*
290  *      Process and reply to a server-status request.
291  *      Like rad_authenticate and rad_accounting this should
292  *      live in it's own file but it's so small we don't bother.
293  */
294 static int rad_status_server(REQUEST *request)
295 {
296         int rcode = RLM_MODULE_OK;
297         DICT_VALUE *dval;
298
299         switch (request->listener->type) {
300 #ifdef WITH_STATS
301         case RAD_LISTEN_NONE:
302 #endif
303         case RAD_LISTEN_AUTH:
304                 dval = dict_valbyname(PW_AUTZ_TYPE, "Status-Server");
305                 if (dval) {
306                         rcode = module_authorize(dval->value, request);
307                 } else {
308                         rcode = RLM_MODULE_OK;
309                 }
310
311                 switch (rcode) {
312                 case RLM_MODULE_OK:
313                 case RLM_MODULE_UPDATED:
314                         request->reply->code = PW_AUTHENTICATION_ACK;
315                         break;
316
317                 case RLM_MODULE_FAIL:
318                 case RLM_MODULE_HANDLED:
319                         request->reply->code = 0; /* don't reply */
320                         break;
321
322                 default:
323                 case RLM_MODULE_REJECT:
324                         request->reply->code = PW_AUTHENTICATION_REJECT;
325                         break;
326                 }
327                 break;
328
329 #ifdef WITH_ACCOUNTING
330         case RAD_LISTEN_ACCT:
331                 dval = dict_valbyname(PW_ACCT_TYPE, "Status-Server");
332                 if (dval) {
333                         rcode = module_accounting(dval->value, request);
334                 } else {
335                         rcode = RLM_MODULE_OK;
336                 }
337
338                 switch (rcode) {
339                 case RLM_MODULE_OK:
340                 case RLM_MODULE_UPDATED:
341                         request->reply->code = PW_ACCOUNTING_RESPONSE;
342                         break;
343
344                 default:
345                         request->reply->code = 0; /* don't reply */
346                         break;
347                 }
348                 break;
349 #endif
350
351 #ifdef WITH_COA
352                 /*
353                  *      This is a vendor extension.  Suggested by Glen
354                  *      Zorn in IETF 72, and rejected by the rest of
355                  *      the WG.  We like it, so it goes in here.
356                  */
357         case RAD_LISTEN_COA:
358                 dval = dict_valbyname(PW_RECV_COA_TYPE, "Status-Server");
359                 if (dval) {
360                         rcode = module_recv_coa(dval->value, request);
361                 } else {
362                         rcode = RLM_MODULE_OK;
363                 }
364
365                 switch (rcode) {
366                 case RLM_MODULE_OK:
367                 case RLM_MODULE_UPDATED:
368                         request->reply->code = PW_COA_ACK;
369                         break;
370
371                 default:
372                         request->reply->code = 0; /* don't reply */
373                         break;
374                 }
375                 break;
376 #endif
377
378         default:
379                 return 0;
380         }
381
382 #ifdef WITH_STATS
383         /*
384          *      Full statistics are available only on a statistics
385          *      socket.
386          */
387         if (request->listener->type == RAD_LISTEN_NONE) {
388                 request_stats_reply(request);
389         }
390 #endif
391
392         return 0;
393 }
394
395
396 static int socket_print(rad_listen_t *this, char *buffer, size_t bufsize)
397 {
398         size_t len;
399         listen_socket_t *sock = this->data;
400         const char *name;
401
402         switch (this->type) {
403 #ifdef WITH_STATS
404         case RAD_LISTEN_NONE:   /* what a hack... */
405                 name = "status";
406                 break;
407 #endif
408
409         case RAD_LISTEN_AUTH:
410                 name = "authentication";
411                 break;
412
413 #ifdef WITH_ACCOUNTING
414         case RAD_LISTEN_ACCT:
415                 name = "accounting";
416                 break;
417 #endif
418
419 #ifdef WITH_PROXY
420         case RAD_LISTEN_PROXY:
421                 name = "proxy";
422                 break;
423 #endif
424
425 #ifdef WITH_VMPS
426         case RAD_LISTEN_VQP:
427                 name = "vmps";
428                 break;
429 #endif
430
431 #ifdef WITH_DHCP
432         case RAD_LISTEN_DHCP:
433                 name = "dhcp";
434                 break;
435 #endif
436
437 #ifdef WITH_COA
438         case RAD_LISTEN_COA:
439                 name = "coa";
440                 break;
441 #endif
442
443         default:
444                 name = "??";
445                 break;
446         }
447
448 #define FORWARD len = strlen(buffer); if (len >= (bufsize + 1)) return 0;buffer += len;bufsize -= len
449 #define ADDSTRING(_x) strlcpy(buffer, _x, bufsize);FORWARD
450
451         ADDSTRING(name);
452
453 #ifdef SO_BINDTODEVICE
454         if (sock->interface) {
455                 ADDSTRING(" interface ");
456                 ADDSTRING(sock->interface);
457         }
458 #endif
459
460         ADDSTRING(" address ");
461         
462         if ((sock->ipaddr.af == AF_INET) &&
463             (sock->ipaddr.ipaddr.ip4addr.s_addr == htonl(INADDR_ANY))) {
464                 strlcpy(buffer, "*", bufsize);
465         } else {
466                 ip_ntoh(&sock->ipaddr, buffer, bufsize);
467         }
468         FORWARD;
469
470         ADDSTRING(" port ");
471         snprintf(buffer, bufsize, "%d", sock->port);
472         FORWARD;
473
474         if (this->server) {
475                 ADDSTRING(" as server ");
476                 ADDSTRING(this->server);
477         }
478
479 #undef ADDSTRING
480 #undef FORWARD
481
482         return 1;
483 }
484
485
486 /*
487  *      Parse an authentication or accounting socket.
488  */
489 static int common_socket_parse(CONF_SECTION *cs, rad_listen_t *this)
490 {
491         int             rcode;
492         int             listen_port;
493         fr_ipaddr_t     ipaddr;
494         listen_socket_t *sock = this->data;
495         char            *section_name = NULL;
496         CONF_SECTION    *client_cs, *parentcs;
497
498         /*
499          *      Try IPv4 first
500          */
501         ipaddr.ipaddr.ip4addr.s_addr = htonl(INADDR_NONE);
502         rcode = cf_item_parse(cs, "ipaddr", PW_TYPE_IPADDR,
503                               &ipaddr.ipaddr.ip4addr, NULL);
504         if (rcode < 0) return -1;
505
506         if (rcode == 0) { /* successfully parsed IPv4 */
507                 ipaddr.af = AF_INET;
508
509         } else {        /* maybe IPv6? */
510                 rcode = cf_item_parse(cs, "ipv6addr", PW_TYPE_IPV6ADDR,
511                                       &ipaddr.ipaddr.ip6addr, NULL);
512                 if (rcode < 0) return -1;
513
514                 if (rcode == 1) {
515                         cf_log_err(cf_sectiontoitem(cs),
516                                    "No address specified in listen section");
517                         return -1;
518                 }
519                 ipaddr.af = AF_INET6;
520         }
521
522         rcode = cf_item_parse(cs, "port", PW_TYPE_INTEGER,
523                               &listen_port, "0");
524         if (rcode < 0) return -1;
525
526         if ((listen_port < 0) || (listen_port > 65535)) {
527                         cf_log_err(cf_sectiontoitem(cs),
528                                    "Invalid value for \"port\"");
529                         return -1;
530         }
531
532         sock->ipaddr = ipaddr;
533         sock->port = listen_port;
534
535         /*
536          *      If we can bind to interfaces, do so,
537          *      else don't.
538          */
539         if (cf_pair_find(cs, "interface")) {
540 #ifndef SO_BINDTODEVICE
541                 cf_log_err(cf_sectiontoitem(cs),
542                            "System does not support binding to interfaces.  Delete this line from the configuration file.");
543                 return -1;
544 #else
545                 const char *value;
546                 CONF_PAIR *cp = cf_pair_find(cs, "interface");
547
548                 rad_assert(cp != NULL);
549                 value = cf_pair_value(cp);
550                 if (!value) {
551                         cf_log_err(cf_sectiontoitem(cs),
552                                    "No interface name given");
553                         return -1;
554                 }
555                 sock->interface = value;
556 #endif
557         }
558
559         /*
560          *      And bind it to the port.
561          */
562         if (listen_bind(this) < 0) {
563                 char buffer[128];
564                 cf_log_err(cf_sectiontoitem(cs),
565                            "Error binding to port for %s port %d",
566                            ip_ntoh(&sock->ipaddr, buffer, sizeof(buffer)),
567                            sock->port);
568                 return -1;
569         }
570
571 #ifdef WITH_PROXY
572         /*
573          *      Proxy sockets don't have clients.
574          */
575         if (this->type == RAD_LISTEN_PROXY) return 0;
576 #endif
577         
578         /*
579          *      The more specific configurations are preferred to more
580          *      generic ones.
581          */
582         client_cs = NULL;
583         parentcs = cf_top_section(cs);
584         rcode = cf_item_parse(cs, "clients", PW_TYPE_STRING_PTR,
585                               &section_name, NULL);
586         if (rcode < 0) return -1; /* bad string */
587         if (rcode == 0) {
588                 /*
589                  *      Explicit list given: use it.
590                  */
591                 client_cs = cf_section_sub_find_name2(parentcs,
592                                                       "clients",
593                                                       section_name);
594                 if (!client_cs) {
595                         client_cs = cf_section_find(section_name);
596                 }
597                 if (!client_cs) {
598                         cf_log_err(cf_sectiontoitem(cs),
599                                    "Failed to find clients %s {...}",
600                                    section_name);
601                         free(section_name);
602                         return -1;
603                 }
604                 free(section_name);
605         } /* else there was no "clients = " entry. */
606
607         if (!client_cs) {
608                 CONF_SECTION *server_cs;
609
610                 server_cs = cf_section_sub_find_name2(parentcs,
611                                                       "server",
612                                                       this->server);
613                 /*
614                  *      Found a "server foo" section.  If there are clients
615                  *      in it, use them.
616                  */
617                 if (server_cs &&
618                     (cf_section_sub_find(server_cs, "client") != NULL)) {
619                         client_cs = server_cs;
620                 }
621         }
622
623         /*
624          *      Still nothing.  Look for global clients.
625          */
626         if (!client_cs) client_cs = parentcs;
627
628         sock->clients = clients_parse_section(client_cs);
629         if (!sock->clients) {
630                 cf_log_err(cf_sectiontoitem(cs),
631                            "Failed to load clients for this listen section");
632                 return -1;
633         }
634
635         return 0;
636 }
637
638 /*
639  *      Send an authentication response packet
640  */
641 static int auth_socket_send(rad_listen_t *listener, REQUEST *request)
642 {
643         rad_assert(request->listener == listener);
644         rad_assert(listener->send == auth_socket_send);
645
646         return rad_send(request->reply, request->packet,
647                         request->client->secret);
648 }
649
650
651 #ifdef WITH_ACCOUNTING
652 /*
653  *      Send an accounting response packet (or not)
654  */
655 static int acct_socket_send(rad_listen_t *listener, REQUEST *request)
656 {
657         rad_assert(request->listener == listener);
658         rad_assert(listener->send == acct_socket_send);
659
660         /*
661          *      Accounting reject's are silently dropped.
662          *
663          *      We do it here to avoid polluting the rest of the
664          *      code with this knowledge
665          */
666         if (request->reply->code == 0) return 0;
667
668         return rad_send(request->reply, request->packet,
669                         request->client->secret);
670 }
671 #endif
672
673 #ifdef WITH_PROXY
674 /*
675  *      Send a packet to a home server.
676  *
677  *      FIXME: have different code for proxy auth & acct!
678  */
679 static int proxy_socket_send(rad_listen_t *listener, REQUEST *request)
680 {
681         listen_socket_t *sock = listener->data;
682
683         rad_assert(request->proxy_listener == listener);
684         rad_assert(listener->send == proxy_socket_send);
685
686         request->proxy->src_ipaddr = sock->ipaddr;
687         request->proxy->src_port = sock->port;
688
689         return rad_send(request->proxy, request->packet,
690                         request->home_server->secret);
691 }
692 #endif
693
694 #ifdef WITH_STATS
695 /*
696  *      Check if an incoming request is "ok"
697  *
698  *      It takes packets, not requests.  It sees if the packet looks
699  *      OK.  If so, it does a number of sanity checks on it.
700   */
701 static int stats_socket_recv(rad_listen_t *listener,
702                             RAD_REQUEST_FUNP *pfun, REQUEST **prequest)
703 {
704         ssize_t         rcode;
705         int             code, src_port;
706         RADIUS_PACKET   *packet;
707         RADCLIENT       *client;
708         fr_ipaddr_t     src_ipaddr;
709
710         rcode = rad_recv_header(listener->fd, &src_ipaddr, &src_port, &code);
711         if (rcode < 0) return 0;
712
713         RAD_STATS_TYPE_INC(listener, total_requests);
714
715         if (rcode < 20) {       /* AUTH_HDR_LEN */
716                 RAD_STATS_TYPE_INC(listener, total_malformed_requests);
717                 return 0;
718         }
719
720         if ((client = client_listener_find(listener,
721                                            &src_ipaddr, src_port)) == NULL) {
722                 rad_recv_discard(listener->fd);
723                 RAD_STATS_TYPE_INC(listener, total_invalid_requests);
724                 return 0;
725         }
726
727         /*
728          *      We only understand Status-Server on this socket.
729          */
730         if (code != PW_STATUS_SERVER) {
731                 DEBUG("Ignoring packet code %d sent to Status-Server port",
732                       code);
733                 rad_recv_discard(listener->fd);
734                 RAD_STATS_TYPE_INC(listener, total_unknown_types);
735                 RAD_STATS_CLIENT_INC(listener, client, total_unknown_types);
736                 return 0;
737         }
738
739         /*
740          *      Now that we've sanity checked everything, receive the
741          *      packet.
742          */
743         packet = rad_recv(listener->fd, 1); /* require message authenticator */
744         if (!packet) {
745                 RAD_STATS_TYPE_INC(listener, total_malformed_requests);
746                 DEBUG("%s", fr_strerror());
747                 return 0;
748         }
749
750         if (!received_request(listener, packet, prequest, client)) {
751                 RAD_STATS_TYPE_INC(listener, total_packets_dropped);
752                 RAD_STATS_CLIENT_INC(listener, client, total_packets_dropped);
753                 rad_free(&packet);
754                 return 0;
755         }
756
757         *pfun = rad_status_server;
758         return 1;
759 }
760 #endif
761
762
763 /*
764  *      Check if an incoming request is "ok"
765  *
766  *      It takes packets, not requests.  It sees if the packet looks
767  *      OK.  If so, it does a number of sanity checks on it.
768   */
769 static int auth_socket_recv(rad_listen_t *listener,
770                             RAD_REQUEST_FUNP *pfun, REQUEST **prequest)
771 {
772         ssize_t         rcode;
773         int             code, src_port;
774         RADIUS_PACKET   *packet;
775         RAD_REQUEST_FUNP fun = NULL;
776         RADCLIENT       *client;
777         fr_ipaddr_t     src_ipaddr;
778
779         rcode = rad_recv_header(listener->fd, &src_ipaddr, &src_port, &code);
780         if (rcode < 0) return 0;
781
782         RAD_STATS_TYPE_INC(listener, total_requests);
783
784         if (rcode < 20) {       /* AUTH_HDR_LEN */
785                 RAD_STATS_TYPE_INC(listener, total_malformed_requests);
786                 return 0;
787         }
788
789         if ((client = client_listener_find(listener,
790                                            &src_ipaddr, src_port)) == NULL) {
791                 rad_recv_discard(listener->fd);
792                 RAD_STATS_TYPE_INC(listener, total_invalid_requests);
793                 return 0;
794         }
795
796         /*
797          *      Some sanity checks, based on the packet code.
798          */
799         switch(code) {
800         case PW_AUTHENTICATION_REQUEST:
801                 RAD_STATS_CLIENT_INC(listener, client, total_requests);
802                 fun = rad_authenticate;
803                 break;
804
805         case PW_STATUS_SERVER:
806                 if (!mainconfig.status_server) {
807                         rad_recv_discard(listener->fd);
808                         RAD_STATS_TYPE_INC(listener, total_packets_dropped);
809                         RAD_STATS_CLIENT_INC(listener, client, total_packets_dropped);
810                         DEBUG("WARNING: Ignoring Status-Server request due to security configuration");
811                         return 0;
812                 }
813                 fun = rad_status_server;
814                 break;
815
816         default:
817                 rad_recv_discard(listener->fd);
818                 RAD_STATS_INC(radius_auth_stats.total_unknown_types);
819                 RAD_STATS_CLIENT_INC(listener, client, total_unknown_types);
820
821                 DEBUG("Invalid packet code %d sent to authentication port from client %s port %d : IGNORED",
822                       code, client->shortname, src_port);
823                 return 0;
824                 break;
825         } /* switch over packet types */
826
827         /*
828          *      Now that we've sanity checked everything, receive the
829          *      packet.
830          */
831         packet = rad_recv(listener->fd, client->message_authenticator);
832         if (!packet) {
833                 RAD_STATS_TYPE_INC(listener, total_malformed_requests);
834                 DEBUG("%s", fr_strerror());
835                 return 0;
836         }
837
838         if (!received_request(listener, packet, prequest, client)) {
839                 RAD_STATS_TYPE_INC(listener, total_packets_dropped);
840                 RAD_STATS_CLIENT_INC(listener, client, total_packets_dropped);
841                 rad_free(&packet);
842                 return 0;
843         }
844
845         *pfun = fun;
846         return 1;
847 }
848
849
850 #ifdef WITH_ACCOUNTING
851 /*
852  *      Receive packets from an accounting socket
853  */
854 static int acct_socket_recv(rad_listen_t *listener,
855                             RAD_REQUEST_FUNP *pfun, REQUEST **prequest)
856 {
857         ssize_t         rcode;
858         int             code, src_port;
859         RADIUS_PACKET   *packet;
860         RAD_REQUEST_FUNP fun = NULL;
861         RADCLIENT       *client;
862         fr_ipaddr_t     src_ipaddr;
863
864         rcode = rad_recv_header(listener->fd, &src_ipaddr, &src_port, &code);
865         if (rcode < 0) return 0;
866
867         RAD_STATS_TYPE_INC(listener, total_requests);
868
869         if (rcode < 20) {       /* AUTH_HDR_LEN */
870                 RAD_STATS_TYPE_INC(listener, total_malformed_requests);
871                 return 0;
872         }
873
874         if ((client = client_listener_find(listener,
875                                            &src_ipaddr, src_port)) == NULL) {
876                 rad_recv_discard(listener->fd);
877                 RAD_STATS_TYPE_INC(listener, total_invalid_requests);
878                 return 0;
879         }
880
881         /*
882          *      Some sanity checks, based on the packet code.
883          */
884         switch(code) {
885         case PW_ACCOUNTING_REQUEST:
886                 RAD_STATS_CLIENT_INC(listener, client, total_requests);
887                 fun = rad_accounting;
888                 break;
889
890         case PW_STATUS_SERVER:
891                 if (!mainconfig.status_server) {
892                         rad_recv_discard(listener->fd);
893                         RAD_STATS_TYPE_INC(listener, total_packets_dropped);
894                         RAD_STATS_CLIENT_INC(listener, client, total_unknown_types);
895
896                         DEBUG("WARNING: Ignoring Status-Server request due to security configuration");
897                         return 0;
898                 }
899                 fun = rad_status_server;
900                 break;
901
902         default:
903                 rad_recv_discard(listener->fd);
904                 RAD_STATS_TYPE_INC(listener, total_unknown_types);
905                 RAD_STATS_CLIENT_INC(listener, client, total_unknown_types);
906
907                 DEBUG("Invalid packet code %d sent to a accounting port from client %s port %d : IGNORED",
908                       code, client->shortname, src_port);
909                 return 0;
910         } /* switch over packet types */
911
912         /*
913          *      Now that we've sanity checked everything, receive the
914          *      packet.
915          */
916         packet = rad_recv(listener->fd, 0);
917         if (!packet) {
918                 RAD_STATS_TYPE_INC(listener, total_malformed_requests);
919                 radlog(L_ERR, "%s", fr_strerror());
920                 return 0;
921         }
922
923         /*
924          *      There can be no duplicate accounting packets.
925          */
926         if (!received_request(listener, packet, prequest, client)) {
927                 RAD_STATS_TYPE_INC(listener, total_packets_dropped);
928                 RAD_STATS_CLIENT_INC(listener, client, total_packets_dropped);
929                 rad_free(&packet);
930                 return 0;
931         }
932
933         *pfun = fun;
934         return 1;
935 }
936 #endif
937
938
939 #ifdef WITH_COA
940 /*
941  *      For now, all CoA requests are *only* originated, and not
942  *      proxied.  So all of the necessary work is done in the
943  *      post-proxy section, which is automatically handled by event.c.
944  *      As a result, we don't have to do anything here.
945  */
946 static int rad_coa_reply(REQUEST *request)
947 {
948         VALUE_PAIR *s1, *s2;
949
950         /*
951          *      Inform the user about RFC requirements.
952          */
953         s1 = pairfind(request->proxy->vps, PW_STATE);
954         if (s1) {
955                 s2 = pairfind(request->proxy_reply->vps, PW_STATE);
956
957                 if (!s2) {
958                         DEBUG("WARNING: Client was sent State in CoA, and did not respond with State.");
959
960                 } else if ((s1->length != s2->length) ||
961                            (memcmp(s1->vp_octets, s2->vp_octets,
962                                    s1->length) != 0)) {
963                         DEBUG("WARNING: Client was sent State in CoA, and did not respond with the same State.");
964                 }
965         }
966
967         return RLM_MODULE_OK;
968 }
969
970 /*
971  *      Receive a CoA packet.
972  */
973 static int rad_coa_recv(REQUEST *request)
974 {
975         int rcode = RLM_MODULE_OK;
976         int ack, nak;
977         VALUE_PAIR *vp;
978
979         /*
980          *      Get the correct response
981          */
982         switch (request->packet->code) {
983         case PW_COA_REQUEST:
984                 ack = PW_COA_ACK;
985                 nak = PW_COA_NAK;
986                 break;
987
988         case PW_DISCONNECT_REQUEST:
989                 ack = PW_DISCONNECT_ACK;
990                 nak = PW_DISCONNECT_NAK;
991                 break;
992
993         default:                /* shouldn't happen */
994                 return RLM_MODULE_FAIL;
995         }
996
997 #ifdef WITH_PROXY
998 #define WAS_PROXIED (request->proxy)
999 #else
1000 #define WAS_PROXIED (0)
1001 #endif
1002
1003         if (!WAS_PROXIED) {
1004                 /*
1005                  *      RFC 5176 Section 3.3.  If we have a CoA-Request
1006                  *      with Service-Type = Authorize-Only, it MUST
1007                  *      have a State attribute in it.
1008                  */
1009                 vp = pairfind(request->packet->vps, PW_SERVICE_TYPE);
1010                 if (request->packet->code == PW_COA_REQUEST) {
1011                         if (vp && (vp->vp_integer == 17)) {
1012                                 vp = pairfind(request->packet->vps, PW_STATE);
1013                                 if (!vp || (vp->length == 0)) {
1014                                         RDEBUG("ERROR: CoA-Request with Service-Type = Authorize-Only MUST contain a State attribute");
1015                                         request->reply->code = PW_COA_NAK;
1016                                         return RLM_MODULE_FAIL;
1017                                 }
1018                         }
1019                 } else if (vp) {
1020                         /*
1021                          *      RFC 5176, Section 3.2.
1022                          */
1023                         RDEBUG("ERROR: Disconnect-Request MUST NOT contain a Service-Type attribute");
1024                         request->reply->code = PW_DISCONNECT_NAK;
1025                         return RLM_MODULE_FAIL;
1026                 }
1027
1028                 rcode = module_recv_coa(0, request);
1029                 switch (rcode) {
1030                 case RLM_MODULE_FAIL:
1031                 case RLM_MODULE_INVALID:
1032                 case RLM_MODULE_REJECT:
1033                 case RLM_MODULE_USERLOCK:
1034                 default:
1035                         request->reply->code = nak;
1036                         break;
1037                         
1038                 case RLM_MODULE_HANDLED:
1039                         return rcode;
1040                         
1041                 case RLM_MODULE_NOOP:
1042                 case RLM_MODULE_NOTFOUND:
1043                 case RLM_MODULE_OK:
1044                 case RLM_MODULE_UPDATED:
1045                         request->reply->code = ack;
1046                         break;
1047                 }
1048         } else {
1049                 /*
1050                  *      Start the reply code with the proxy reply
1051                  *      code.
1052                  */
1053                 request->reply->code = request->proxy_reply->code;
1054         }
1055
1056         /*
1057          *      Copy State from the request to the reply.
1058          *      See RFC 5176 Section 3.3.
1059          */
1060         vp = paircopy2(request->packet->vps, PW_STATE);
1061         if (vp) pairadd(&request->reply->vps, vp);
1062
1063         /*
1064          *      We may want to over-ride the reply.
1065          */
1066         rcode = module_send_coa(0, request);
1067         switch (rcode) {
1068                 /*
1069                  *      We need to send CoA-NAK back if Service-Type
1070                  *      is Authorize-Only.  Rely on the user's policy
1071                  *      to do that.  We're not a real NAS, so this
1072                  *      restriction doesn't (ahem) apply to us.
1073                  */
1074                 case RLM_MODULE_FAIL:
1075                 case RLM_MODULE_INVALID:
1076                 case RLM_MODULE_REJECT:
1077                 case RLM_MODULE_USERLOCK:
1078                 default:
1079                         request->reply->code = nak;
1080                         break;
1081                         
1082                 case RLM_MODULE_HANDLED:
1083                         return rcode;
1084                         
1085                 case RLM_MODULE_NOOP:
1086                 case RLM_MODULE_NOTFOUND:
1087                 case RLM_MODULE_OK:
1088                 case RLM_MODULE_UPDATED:
1089                         request->reply->code = ack;
1090                         break;
1091
1092         }
1093
1094         return RLM_MODULE_OK;
1095 }
1096
1097
1098 /*
1099  *      Check if an incoming request is "ok"
1100  *
1101  *      It takes packets, not requests.  It sees if the packet looks
1102  *      OK.  If so, it does a number of sanity checks on it.
1103   */
1104 static int coa_socket_recv(rad_listen_t *listener,
1105                             RAD_REQUEST_FUNP *pfun, REQUEST **prequest)
1106 {
1107         ssize_t         rcode;
1108         int             code, src_port;
1109         RADIUS_PACKET   *packet;
1110         RAD_REQUEST_FUNP fun = NULL;
1111         char            buffer[128];
1112         RADCLIENT       *client;
1113         fr_ipaddr_t     src_ipaddr;
1114
1115         rcode = rad_recv_header(listener->fd, &src_ipaddr, &src_port, &code);
1116         if (rcode < 0) return 0;
1117
1118         RAD_STATS_TYPE_INC(listener, total_requests);
1119
1120         if (rcode < 20) {       /* AUTH_HDR_LEN */
1121                 RAD_STATS_TYPE_INC(listener, total_malformed_requests);
1122                 return 0;
1123         }
1124
1125         if ((client = client_listener_find(listener,
1126                                            &src_ipaddr, src_port)) == NULL) {
1127                 rad_recv_discard(listener->fd);
1128                 RAD_STATS_TYPE_INC(listener, total_invalid_requests);
1129
1130                 if (debug_flag > 0) {
1131                         char name[1024];
1132
1133                         listener->print(listener, name, sizeof(name));
1134
1135                         /*
1136                          *      This is debugging rather than logging, so that
1137                          *      DoS attacks don't affect us.
1138                          */
1139                         DEBUG("Ignoring request to %s from unknown client %s port %d",
1140                               name,
1141                               inet_ntop(src_ipaddr.af, &src_ipaddr.ipaddr,
1142                                         buffer, sizeof(buffer)), src_port);
1143                 }
1144
1145                 return 0;
1146         }
1147
1148         /*
1149          *      Some sanity checks, based on the packet code.
1150          */
1151         switch(code) {
1152         case PW_COA_REQUEST:
1153         case PW_DISCONNECT_REQUEST:
1154                 fun = rad_coa_recv;
1155                 break;
1156
1157         default:
1158                 rad_recv_discard(listener->fd);
1159                 DEBUG("Invalid packet code %d sent to coa port from client %s port %d : IGNORED",
1160                       code, client->shortname, src_port);
1161                 return 0;
1162                 break;
1163         } /* switch over packet types */
1164
1165         /*
1166          *      Now that we've sanity checked everything, receive the
1167          *      packet.
1168          */
1169         packet = rad_recv(listener->fd, client->message_authenticator);
1170         if (!packet) {
1171                 RAD_STATS_TYPE_INC(listener, total_malformed_requests);
1172                 DEBUG("%s", fr_strerror());
1173                 return 0;
1174         }
1175
1176         if (!received_request(listener, packet, prequest, client)) {
1177                 rad_free(&packet);
1178                 return 0;
1179         }
1180
1181         *pfun = fun;
1182         return 1;
1183 }
1184 #endif
1185
1186 #ifdef WITH_PROXY
1187 /*
1188  *      Recieve packets from a proxy socket.
1189  */
1190 static int proxy_socket_recv(rad_listen_t *listener,
1191                               RAD_REQUEST_FUNP *pfun, REQUEST **prequest)
1192 {
1193         REQUEST         *request;
1194         RADIUS_PACKET   *packet;
1195         RAD_REQUEST_FUNP fun = NULL;
1196         char            buffer[128];
1197
1198         packet = rad_recv(listener->fd, 0);
1199         if (!packet) {
1200                 radlog(L_ERR, "%s", fr_strerror());
1201                 return 0;
1202         }
1203
1204         /*
1205          *      FIXME: Client MIB updates?
1206          */
1207         switch(packet->code) {
1208         case PW_AUTHENTICATION_ACK:
1209         case PW_ACCESS_CHALLENGE:
1210         case PW_AUTHENTICATION_REJECT:
1211                 fun = rad_authenticate;
1212                 break;
1213
1214 #ifdef WITH_ACCOUNTING
1215         case PW_ACCOUNTING_RESPONSE:
1216                 fun = rad_accounting;
1217                 break;
1218 #endif
1219
1220 #ifdef WITH_COA
1221         case PW_DISCONNECT_ACK:
1222         case PW_DISCONNECT_NAK:
1223         case PW_COA_ACK:
1224         case PW_COA_NAK:
1225                 fun = rad_coa_reply;
1226                 break;
1227 #endif
1228
1229         default:
1230                 /*
1231                  *      FIXME: Update MIB for packet types?
1232                  */
1233                 radlog(L_ERR, "Invalid packet code %d sent to a proxy port "
1234                        "from home server %s port %d - ID %d : IGNORED",
1235                        packet->code,
1236                        ip_ntoh(&packet->src_ipaddr, buffer, sizeof(buffer)),
1237                        packet->src_port, packet->id);
1238                 rad_free(&packet);
1239                 return 0;
1240         }
1241
1242         request = received_proxy_response(packet);
1243         if (!request) {
1244                 rad_free(&packet);
1245                 return 0;
1246         }
1247
1248 #ifdef WITH_COA
1249         /*
1250          *      Distinguish proxied CoA requests from ones we
1251          *      originate.
1252          */
1253         if ((fun == rad_coa_reply) &&
1254             (request->packet->code == request->proxy->code)) {
1255                 fun = rad_coa_recv;
1256         }
1257 #endif
1258
1259         rad_assert(fun != NULL);
1260         *pfun = fun;
1261         *prequest = request;
1262
1263         return 1;
1264 }
1265 #endif
1266
1267
1268 static int client_socket_encode(UNUSED rad_listen_t *listener, REQUEST *request)
1269 {
1270         if (!request->reply->code) return 0;
1271
1272         rad_encode(request->reply, request->packet,
1273                    request->client->secret);
1274         rad_sign(request->reply, request->packet,
1275                  request->client->secret);
1276
1277         return 0;
1278 }
1279
1280
1281 static int client_socket_decode(UNUSED rad_listen_t *listener, REQUEST *request)
1282 {
1283         if (rad_verify(request->packet, NULL,
1284                        request->client->secret) < 0) {
1285                 return -1;
1286         }
1287
1288         return rad_decode(request->packet, NULL,
1289                           request->client->secret);
1290 }
1291
1292 #ifdef WITH_PROXY
1293 static int proxy_socket_encode(UNUSED rad_listen_t *listener, REQUEST *request)
1294 {
1295         rad_encode(request->proxy, NULL, request->home_server->secret);
1296         rad_sign(request->proxy, NULL, request->home_server->secret);
1297
1298         return 0;
1299 }
1300
1301
1302 static int proxy_socket_decode(UNUSED rad_listen_t *listener, REQUEST *request)
1303 {
1304         /*
1305          *      rad_verify is run in event.c, received_proxy_response()
1306          */
1307
1308         return rad_decode(request->proxy_reply, request->proxy,
1309                            request->home_server->secret);
1310 }
1311 #endif
1312
1313 #include "dhcpd.c"
1314
1315 #include "command.c"
1316
1317 static const rad_listen_master_t master_listen[RAD_LISTEN_MAX] = {
1318 #ifdef WITH_STATS
1319         { common_socket_parse, NULL,
1320           stats_socket_recv, auth_socket_send,
1321           socket_print, client_socket_encode, client_socket_decode },
1322 #else
1323         /*
1324          *      This always gets defined.
1325          */
1326         { NULL, NULL, NULL, NULL, NULL, NULL, NULL},    /* RAD_LISTEN_NONE */
1327 #endif
1328
1329 #ifdef WITH_PROXY
1330         /* proxying */
1331         { common_socket_parse, NULL,
1332           proxy_socket_recv, proxy_socket_send,
1333           socket_print, proxy_socket_encode, proxy_socket_decode },
1334 #endif
1335
1336         /* authentication */
1337         { common_socket_parse, NULL,
1338           auth_socket_recv, auth_socket_send,
1339           socket_print, client_socket_encode, client_socket_decode },
1340
1341 #ifdef WITH_ACCOUNTING
1342         /* accounting */
1343         { common_socket_parse, NULL,
1344           acct_socket_recv, acct_socket_send,
1345           socket_print, client_socket_encode, client_socket_decode},
1346 #endif
1347
1348 #ifdef WITH_DETAIL
1349         /* detail */
1350         { detail_parse, detail_free,
1351           detail_recv, detail_send,
1352           detail_print, detail_encode, detail_decode },
1353 #endif
1354
1355 #ifdef WITH_VMPS
1356         /* vlan query protocol */
1357         { common_socket_parse, NULL,
1358           vqp_socket_recv, vqp_socket_send,
1359           socket_print, vqp_socket_encode, vqp_socket_decode },
1360 #endif
1361
1362 #ifdef WITH_DHCP
1363         /* dhcp query protocol */
1364         { dhcp_socket_parse, NULL,
1365           dhcp_socket_recv, dhcp_socket_send,
1366           socket_print, dhcp_socket_encode, dhcp_socket_decode },
1367 #endif
1368
1369 #ifdef WITH_COMMAND_SOCKET
1370         /* TCP command socket */
1371         { command_socket_parse, NULL,
1372           command_domain_accept, command_domain_send,
1373           command_socket_print, command_socket_encode, command_socket_decode },
1374 #endif
1375
1376 #ifdef WITH_COA
1377         /* Change of Authorization */
1378         { common_socket_parse, NULL,
1379           coa_socket_recv, auth_socket_send, /* CoA packets are same as auth */
1380           socket_print, client_socket_encode, client_socket_decode },
1381 #endif
1382
1383 };
1384
1385
1386
1387 /*
1388  *      Binds a listener to a socket.
1389  */
1390 static int listen_bind(rad_listen_t *this)
1391 {
1392         int rcode;
1393         struct sockaddr_storage salocal;
1394         socklen_t       salen;
1395         listen_socket_t *sock = this->data;
1396
1397         /*
1398          *      If the port is zero, then it means the appropriate
1399          *      thing from /etc/services.
1400          */
1401         if (sock->port == 0) {
1402                 struct servent  *svp;
1403
1404                 switch (this->type) {
1405                 case RAD_LISTEN_AUTH:
1406                         svp = getservbyname ("radius", "udp");
1407                         if (svp != NULL) {
1408                                 sock->port = ntohs(svp->s_port);
1409                         } else {
1410                                 sock->port = PW_AUTH_UDP_PORT;
1411                         }
1412                         break;
1413
1414 #ifdef WITH_ACCOUNTING
1415                 case RAD_LISTEN_ACCT:
1416                         svp = getservbyname ("radacct", "udp");
1417                         if (svp != NULL) {
1418                                 sock->port = ntohs(svp->s_port);
1419                         } else {
1420                                 sock->port = PW_ACCT_UDP_PORT;
1421                         }
1422                         break;
1423 #endif
1424
1425 #ifdef WITH_PROXY
1426                 case RAD_LISTEN_PROXY:
1427                         sock->port = 0;
1428                         break;
1429 #endif
1430
1431 #ifdef WITH_VMPS
1432                 case RAD_LISTEN_VQP:
1433                         sock->port = 1589;
1434                         break;
1435 #endif
1436
1437 #ifdef WITH_COA
1438                 case RAD_LISTEN_COA:
1439                         sock->port = PW_COA_UDP_PORT;
1440                         break;
1441 #endif
1442
1443                 default:
1444                         radlog(L_ERR, "ERROR: Non-fatal internal sanity check failed in bind.");
1445                         return -1;
1446                 }
1447         }
1448
1449         /*
1450          *      Copy fr_socket() here, as we may need to bind to a device.
1451          */
1452         this->fd = socket(sock->ipaddr.af, SOCK_DGRAM, 0);
1453         if (this->fd < 0) {
1454                 radlog(L_ERR, "Failed opening socket: %s", strerror(errno));
1455                 return -1;
1456         }
1457                 
1458 #ifdef SO_BINDTODEVICE
1459         /*
1460          *      Bind to a device BEFORE touching IP addresses.
1461          */
1462         if (sock->interface) {
1463                 struct ifreq ifreq;
1464                 strcpy(ifreq.ifr_name, sock->interface);
1465
1466                 fr_suid_up();
1467                 rcode = setsockopt(this->fd, SOL_SOCKET, SO_BINDTODEVICE,
1468                                    (char *)&ifreq, sizeof(ifreq));
1469                 fr_suid_down();
1470                 if (rcode < 0) {
1471                         close(this->fd);
1472                         radlog(L_ERR, "Failed binding to interface %s: %s",
1473                                sock->interface, strerror(errno));
1474                         return -1;
1475                 } /* else it worked. */
1476         }
1477 #endif
1478
1479 #ifdef WITH_UDPFROMTO
1480         /*
1481          *      Initialize udpfromto for all sockets.
1482          */
1483         if (udpfromto_init(this->fd) != 0) {
1484                 close(this->fd);
1485                 return -1;
1486         }
1487 #endif
1488         
1489         /*
1490          *      Set up sockaddr stuff.
1491          */
1492         if (!fr_ipaddr2sockaddr(&sock->ipaddr, sock->port, &salocal, &salen)) {
1493                 close(this->fd);
1494                 return -1;
1495         }
1496                 
1497 #ifdef HAVE_STRUCT_SOCKADDR_IN6
1498         if (sock->ipaddr.af == AF_INET6) {
1499                 /*
1500                  *      Listening on '::' does NOT get you IPv4 to
1501                  *      IPv6 mapping.  You've got to listen on an IPv4
1502                  *      address, too.  This makes the rest of the server
1503                  *      design a little simpler.
1504                  */
1505 #ifdef IPV6_V6ONLY
1506                 
1507                 if (IN6_IS_ADDR_UNSPECIFIED(&sock->ipaddr.ipaddr.ip6addr)) {
1508                         int on = 1;
1509                         
1510                         setsockopt(this->fd, IPPROTO_IPV6, IPV6_V6ONLY,
1511                                    (char *)&on, sizeof(on));
1512                 }
1513 #endif /* IPV6_V6ONLY */
1514         }
1515 #endif /* HAVE_STRUCT_SOCKADDR_IN6 */
1516
1517         /*
1518          *      May be binding to priviledged ports.
1519          */
1520         fr_suid_up();
1521         rcode = bind(this->fd, (struct sockaddr *) &salocal, salen);
1522         fr_suid_down();
1523         if (rcode < 0) {
1524                 close(this->fd);
1525                 radlog(L_ERR, "Failed binding to socket: %s\n",
1526                        strerror(errno));
1527                 return -1;
1528         }
1529         
1530         /*
1531          *      FreeBSD jail issues.  We bind to 0.0.0.0, but the
1532          *      kernel instead binds us to a 1.2.3.4.  If this
1533          *      happens, notice, and remember our real IP.
1534          */
1535         {
1536                 struct sockaddr_storage src;
1537                 socklen_t               sizeof_src = sizeof(src);
1538
1539                 memset(&src, 0, sizeof_src);
1540                 if (getsockname(this->fd, (struct sockaddr *) &src,
1541                                 &sizeof_src) < 0) {
1542                         radlog(L_ERR, "Failed getting socket name: %s",
1543                                strerror(errno));
1544                         return -1;
1545                 }
1546
1547                 if (!fr_sockaddr2ipaddr(&src, sizeof_src,
1548                                         &sock->ipaddr, &sock->port)) {
1549                         radlog(L_ERR, "Socket has unsupported address family");
1550                         return -1;
1551                 }
1552         }
1553
1554 #ifdef O_NONBLOCK
1555         {
1556                 int flags;
1557                 
1558                 if ((flags = fcntl(this->fd, F_GETFL, NULL)) < 0)  {
1559                         radlog(L_ERR, "Failure getting socket flags: %s)\n",
1560                                strerror(errno));
1561                         return -1;
1562                 }
1563                 
1564                 flags |= O_NONBLOCK;
1565                 if( fcntl(this->fd, F_SETFL, flags) < 0) {
1566                         radlog(L_ERR, "Failure setting socket flags: %s)\n",
1567                                strerror(errno));
1568                         return -1;
1569                 }
1570         }
1571 #endif
1572
1573         return 0;
1574 }
1575
1576
1577 /*
1578  *      Allocate & initialize a new listener.
1579  */
1580 static rad_listen_t *listen_alloc(RAD_LISTEN_TYPE type)
1581 {
1582         rad_listen_t *this;
1583
1584         this = rad_malloc(sizeof(*this));
1585         memset(this, 0, sizeof(*this));
1586
1587         this->type = type;
1588         this->recv = master_listen[this->type].recv;
1589         this->send = master_listen[this->type].send;
1590         this->print = master_listen[this->type].print;
1591         this->encode = master_listen[this->type].encode;
1592         this->decode = master_listen[this->type].decode;
1593
1594         switch (type) {
1595 #ifdef WITH_STATS
1596         case RAD_LISTEN_NONE:
1597 #endif
1598         case RAD_LISTEN_AUTH:
1599 #ifdef WITH_ACCOUNTING
1600         case RAD_LISTEN_ACCT:
1601 #endif
1602 #ifdef WITH_PROXY
1603         case RAD_LISTEN_PROXY:
1604 #endif
1605 #ifdef WITH_VMPS
1606         case RAD_LISTEN_VQP:
1607 #endif
1608 #ifdef WITH_DHCP
1609         case RAD_LISTEN_DHCP:
1610 #endif
1611 #ifdef WITH_COA
1612         case RAD_LISTEN_COA:
1613 #endif
1614                 this->data = rad_malloc(sizeof(listen_socket_t));
1615                 memset(this->data, 0, sizeof(listen_socket_t));
1616                 break;
1617
1618 #ifdef WITH_DETAIL
1619         case RAD_LISTEN_DETAIL:
1620                 this->data = NULL;
1621                 break;
1622 #endif
1623
1624 #ifdef WITH_COMMAND_SOCKET
1625         case RAD_LISTEN_COMMAND:
1626                 this->data = rad_malloc(sizeof(fr_command_socket_t));
1627                 memset(this->data, 0, sizeof(fr_command_socket_t));
1628                 break;
1629 #endif
1630
1631         default:
1632                 rad_assert("Unsupported option!" == NULL);
1633                 break;
1634         }
1635
1636         return this;
1637 }
1638
1639
1640 #ifdef WITH_PROXY
1641 /*
1642  *      Externally visible function for creating a new proxy LISTENER.
1643  *
1644  *      For now, don't take ipaddr or port.
1645  *
1646  *      Not thread-safe, but all calls to it are protected by the
1647  *      proxy mutex in request_list.c
1648  */
1649 rad_listen_t *proxy_new_listener()
1650 {
1651         int last_proxy_port, port;
1652         rad_listen_t *this, *tmp, **last;
1653         listen_socket_t *sock, *old;
1654
1655         this = listen_alloc(RAD_LISTEN_PROXY);
1656
1657         /*
1658          *      Find an existing proxy socket to copy.
1659          *
1660          *      FIXME: Make it per-realm, or per-home server!
1661          */
1662         last_proxy_port = 0;
1663         old = NULL;
1664         last = &mainconfig.listen;
1665         for (tmp = mainconfig.listen; tmp != NULL; tmp = tmp->next) {
1666                 if (tmp->type == RAD_LISTEN_PROXY) {
1667                         sock = tmp->data;
1668                         if (sock->port > last_proxy_port) {
1669                                 last_proxy_port = sock->port + 1;
1670                         }
1671                         if (!old) old = sock;
1672                 }
1673
1674                 last = &(tmp->next);
1675         }
1676
1677         if (!old) {
1678                 listen_free(&this);
1679                 return NULL;    /* This is a serious error. */
1680         }
1681
1682         /*
1683          *      FIXME: find a new IP address to listen on?
1684          *
1685          *      This could likely be done in the "home server"
1686          *      configuration, to have per-home-server source IP's.
1687          */
1688         sock = this->data;
1689         memcpy(&sock->ipaddr, &old->ipaddr, sizeof(sock->ipaddr));
1690
1691         /*
1692          *      Keep going until we find an unused port.
1693          */
1694         for (port = last_proxy_port; port < 64000; port++) {
1695                 sock->port = port;
1696                 if (listen_bind(this) == 0) {
1697                         /*
1698                          *      Add the new listener to the list of
1699                          *      listeners.
1700                          */
1701                         *last = this;
1702                         return this;
1703                 }
1704         }
1705
1706         listen_free(&this);
1707         return NULL;
1708 }
1709 #endif
1710
1711 static const FR_NAME_NUMBER listen_compare[] = {
1712 #ifdef WITH_STATS
1713         { "status",     RAD_LISTEN_NONE },
1714 #endif
1715         { "auth",       RAD_LISTEN_AUTH },
1716 #ifdef WITH_ACCOUNTING
1717         { "acct",       RAD_LISTEN_ACCT },
1718 #endif
1719 #ifdef WITH_DETAIL
1720         { "detail",     RAD_LISTEN_DETAIL },
1721 #endif
1722 #ifdef WITH_PROXY
1723         { "proxy",      RAD_LISTEN_PROXY },
1724 #endif
1725 #ifdef WITH_VMPS
1726         { "vmps",       RAD_LISTEN_VQP },
1727 #endif
1728 #ifdef WITH_DHCP
1729         { "dhcp",       RAD_LISTEN_DHCP },
1730 #endif
1731 #ifdef WITH_COMMAND_SOCKET
1732         { "control",    RAD_LISTEN_COMMAND },
1733 #endif
1734 #ifdef WITH_COA
1735         { "coa",        RAD_LISTEN_COA },
1736 #endif
1737         { NULL, 0 },
1738 };
1739
1740
1741 static rad_listen_t *listen_parse(CONF_SECTION *cs, const char *server)
1742 {
1743         int             type, rcode;
1744         char            *listen_type;
1745         rad_listen_t    *this;
1746
1747         listen_type = NULL;
1748         
1749         cf_log_info(cs, "listen {");
1750
1751         rcode = cf_item_parse(cs, "type", PW_TYPE_STRING_PTR,
1752                               &listen_type, "");
1753         if (rcode < 0) return NULL;
1754         if (rcode == 1) {
1755                 free(listen_type);
1756                 cf_log_err(cf_sectiontoitem(cs),
1757                            "No type specified in listen section");
1758                 return NULL;
1759         }
1760
1761         type = fr_str2int(listen_compare, listen_type, -1);
1762         if (type < 0) {
1763                 cf_log_err(cf_sectiontoitem(cs),
1764                            "Invalid type \"%s\" in listen section.",
1765                            listen_type);
1766                 free(listen_type);
1767                 return NULL;
1768         }
1769         free(listen_type);
1770         
1771         /*
1772          *      Allow listen sections in the default config to
1773          *      refer to a server.
1774          */
1775         if (!server) {
1776                 rcode = cf_item_parse(cs, "virtual_server", PW_TYPE_STRING_PTR,
1777                                       &server, NULL);
1778                 if (rcode == 1) { /* compatiblity with 2.0-pre */
1779                         rcode = cf_item_parse(cs, "server", PW_TYPE_STRING_PTR,
1780                                               &server, NULL);
1781                 }
1782                 if (rcode < 0) return NULL;
1783         }
1784
1785         /*
1786          *      Set up cross-type data.
1787          */
1788         this = listen_alloc(type);
1789         this->server = server;
1790         this->fd = -1;
1791
1792         /*
1793          *      Call per-type parser.
1794          */
1795         if (master_listen[type].parse(cs, this) < 0) {
1796                 listen_free(&this);
1797                 return NULL;
1798         }
1799
1800         cf_log_info(cs, "}");
1801
1802         return this;
1803 }
1804
1805 /*
1806  *      Generate a list of listeners.  Takes an input list of
1807  *      listeners, too, so we don't close sockets with waiting packets.
1808  */
1809 int listen_init(CONF_SECTION *config, rad_listen_t **head)
1810 {
1811         int             override = FALSE;
1812         int             rcode;
1813         CONF_SECTION    *cs = NULL;
1814         rad_listen_t    **last;
1815         rad_listen_t    *this;
1816         fr_ipaddr_t     server_ipaddr;
1817         int             auth_port = 0;
1818 #ifdef WITH_PROXY
1819         int             defined_proxy = 0;
1820 #endif
1821
1822         /*
1823          *      We shouldn't be called with a pre-existing list.
1824          */
1825         rad_assert(head && (*head == NULL));
1826
1827         last = head;
1828         server_ipaddr.af = AF_UNSPEC;
1829
1830         /*
1831          *      If the port is specified on the command-line,
1832          *      it over-rides the configuration file.
1833          *
1834          *      FIXME: If argv[0] == "vmpsd", then don't listen on auth/acct!
1835          */
1836         if (mainconfig.port >= 0) auth_port = mainconfig.port;
1837
1838         /*
1839          *      If the IP address was configured on the command-line,
1840          *      use that as the "bind_address"
1841          */
1842         if (mainconfig.myip.af != AF_UNSPEC) {
1843                 memcpy(&server_ipaddr, &mainconfig.myip,
1844                        sizeof(server_ipaddr));
1845                 override = TRUE;
1846                 goto bind_it;
1847         }
1848
1849         /*
1850          *      Else look for bind_address and/or listen sections.
1851          */
1852         server_ipaddr.ipaddr.ip4addr.s_addr = htonl(INADDR_NONE);
1853         rcode = cf_item_parse(config, "bind_address",
1854                               PW_TYPE_IPADDR,
1855                               &server_ipaddr.ipaddr.ip4addr, NULL);
1856         if (rcode < 0) return -1; /* error parsing it */
1857
1858         if (rcode == 0) { /* successfully parsed IPv4 */
1859                 listen_socket_t *sock;
1860                 server_ipaddr.af = AF_INET;
1861
1862                 radlog(L_INFO, "WARNING: The directive 'bind_adress' is deprecated, and will be removed in future versions of FreeRADIUS. Please edit the configuration files to use the directive 'listen'.");
1863
1864         bind_it:
1865 #ifdef WITH_VMPS
1866                 if (strcmp(progname, "vmpsd") == 0) {
1867                         this = listen_alloc(RAD_LISTEN_VQP);
1868                         if (!auth_port) auth_port = 1589;
1869                 } else
1870 #endif
1871                         this = listen_alloc(RAD_LISTEN_AUTH);
1872
1873                 sock = this->data;
1874
1875                 sock->ipaddr = server_ipaddr;
1876                 sock->port = auth_port;
1877
1878                 sock->clients = clients_parse_section(config);
1879                 if (!sock->clients) {
1880                         cf_log_err(cf_sectiontoitem(config),
1881                                    "Failed to find any clients for this listen section");
1882                         listen_free(&this);
1883                         return -1;
1884                 }
1885
1886                 if (listen_bind(this) < 0) {
1887                         listen_free(head);
1888                         radlog(L_ERR, "There appears to be another RADIUS server running on the authentication port %d", sock->port);
1889                         listen_free(&this);
1890                         return -1;
1891                 }
1892                 auth_port = sock->port; /* may have been updated in listen_bind */
1893                 if (override) {
1894                         cs = cf_section_sub_find_name2(config, "server",
1895                                                        mainconfig.name);
1896                         if (cs) this->server = mainconfig.name;
1897                 }
1898
1899                 *last = this;
1900                 last = &(this->next);
1901
1902 #ifdef WITH_VMPS
1903                 /*
1904                  *      No acct for vmpsd
1905                  */
1906                 if (strcmp(progname, "vmpsd") == 0) goto do_proxy;
1907 #endif
1908
1909 #ifdef WITH_ACCOUNTING
1910                 /*
1911                  *      Open Accounting Socket.
1912                  *
1913                  *      If we haven't already gotten acct_port from
1914                  *      /etc/services, then make it auth_port + 1.
1915                  */
1916                 this = listen_alloc(RAD_LISTEN_ACCT);
1917                 sock = this->data;
1918
1919                 /*
1920                  *      Create the accounting socket.
1921                  *
1922                  *      The accounting port is always the
1923                  *      authentication port + 1
1924                  */
1925                 sock->ipaddr = server_ipaddr;
1926                 sock->port = auth_port + 1;
1927
1928                 sock->clients = clients_parse_section(config);
1929                 if (!sock->clients) {
1930                         cf_log_err(cf_sectiontoitem(config),
1931                                    "Failed to find any clients for this listen section");
1932                         return -1;
1933                 }
1934
1935                 if (listen_bind(this) < 0) {
1936                         listen_free(&this);
1937                         listen_free(head);
1938                         radlog(L_ERR, "There appears to be another RADIUS server running on the accounting port %d", sock->port);
1939                         return -1;
1940                 }
1941
1942                 if (override) {
1943                         cs = cf_section_sub_find_name2(config, "server",
1944                                                        mainconfig.name);
1945                         if (cs) this->server = mainconfig.name;
1946                 }
1947
1948                 *last = this;
1949                 last = &(this->next);
1950 #endif
1951         } else if (mainconfig.port > 0) { /* no bind address, but a port */
1952                 radlog(L_ERR, "The command-line says \"-p %d\", but there is no associated IP address to use",
1953                        mainconfig.port);
1954                 return -1;
1955         }
1956
1957         /*
1958          *      They specified an IP on the command-line, ignore
1959          *      all listen sections except the one in '-n'.
1960          */
1961         if (mainconfig.myip.af != AF_UNSPEC) {
1962                 CONF_SECTION *subcs;
1963                 const char *name2 = cf_section_name2(cs);
1964
1965                 cs = cf_section_sub_find_name2(config, "server",
1966                                                mainconfig.name);
1967                 if (!cs) goto do_proxy;
1968
1969                 /*
1970                  *      Should really abstract this code...
1971                  */
1972                 for (subcs = cf_subsection_find_next(cs, NULL, "listen");
1973                      subcs != NULL;
1974                      subcs = cf_subsection_find_next(cs, subcs, "listen")) {
1975                         this = listen_parse(subcs, name2);
1976                         if (!this) {
1977                                 listen_free(head);
1978                                 return -1;
1979                         }
1980
1981 #ifdef WITH_PROXY
1982                         if (this->type == RAD_LISTEN_PROXY) defined_proxy = 1;
1983 #endif
1984                         
1985                         *last = this;
1986                         last = &(this->next);
1987                 } /* loop over "listen" directives in server <foo> */
1988
1989                 goto do_proxy;
1990         }
1991
1992         /*
1993          *      Walk through the "listen" sections, if they exist.
1994          */
1995         for (cs = cf_subsection_find_next(config, NULL, "listen");
1996              cs != NULL;
1997              cs = cf_subsection_find_next(config, cs, "listen")) {
1998                 this = listen_parse(cs, NULL);
1999                 if (!this) {
2000                         listen_free(head);
2001                         return -1;
2002                 }
2003
2004 #ifdef WITH_PROXY
2005                 if (this->type == RAD_LISTEN_PROXY) defined_proxy = 1;
2006 #endif
2007
2008                 *last = this;
2009                 last = &(this->next);
2010         }
2011
2012         /*
2013          *      Check virtual servers for "listen" sections, too.
2014          *
2015          *      FIXME: Move to virtual server init?
2016          */
2017         for (cs = cf_subsection_find_next(config, NULL, "server");
2018              cs != NULL;
2019              cs = cf_subsection_find_next(config, cs, "server")) {
2020                 CONF_SECTION *subcs;
2021                 const char *name2 = cf_section_name2(cs);
2022                 
2023                 for (subcs = cf_subsection_find_next(cs, NULL, "listen");
2024                      subcs != NULL;
2025                      subcs = cf_subsection_find_next(cs, subcs, "listen")) {
2026                         this = listen_parse(subcs, name2);
2027                         if (!this) {
2028                                 listen_free(head);
2029                                 return -1;
2030                         }
2031                         
2032 #ifdef WITH_PROXY
2033                         if (this->type == RAD_LISTEN_PROXY) {
2034                                 radlog(L_ERR, "Error: listen type \"proxy\" Cannot appear in a virtual server section");
2035                                 listen_free(head);
2036                                 return -1;
2037                         }
2038 #endif
2039
2040                         *last = this;
2041                         last = &(this->next);
2042                 } /* loop over "listen" directives in virtual servers */
2043         } /* loop over virtual servers */
2044
2045         /*
2046          *      If we're proxying requests, open the proxy FD.
2047          *      Otherwise, don't do anything.
2048          */
2049  do_proxy:
2050 #ifdef WITH_PROXY
2051         if (mainconfig.proxy_requests == TRUE) {
2052                 int             port = -1;
2053                 listen_socket_t *sock = NULL;
2054
2055                 /*
2056                  *      No sockets to receive packets, therefore
2057                  *      proxying is pointless.
2058                  */
2059                 if (!*head) return -1;
2060
2061                 if (defined_proxy) goto done;
2062
2063                 /*
2064                  *      Find the first authentication port,
2065                  *      and use it
2066                  */
2067                 for (this = *head; this != NULL; this = this->next) {
2068                         if (this->type == RAD_LISTEN_AUTH) {
2069                                 sock = this->data;
2070                                 if (server_ipaddr.af == AF_UNSPEC) {
2071                                         server_ipaddr = sock->ipaddr;
2072                                 }
2073                                 port = sock->port + 2; /* skip acct port */
2074                                 break;
2075                         }
2076 #ifdef WITH_VMPS
2077                         if (this->type == RAD_LISTEN_VQP) {
2078                                 sock = this->data;
2079                                 if (server_ipaddr.af == AF_UNSPEC) {
2080                                         server_ipaddr = sock->ipaddr;
2081                                 }
2082                                 port = sock->port + 1;
2083                                 break;
2084                         }
2085 #endif
2086                 }
2087
2088                 if (port < 0) port = 1024 + (fr_rand() & 0x1ff);
2089
2090                 /*
2091                  *      Address is still unspecified, use IPv4.
2092                  */
2093                 if (server_ipaddr.af == AF_UNSPEC) {
2094                         server_ipaddr.af = AF_INET;
2095                         server_ipaddr.ipaddr.ip4addr.s_addr = htonl(INADDR_ANY);
2096                 }
2097
2098                 this = listen_alloc(RAD_LISTEN_PROXY);
2099                 sock = this->data;
2100
2101                 /*
2102                  *      Create the first proxy socket.
2103                  */
2104                 sock->ipaddr = server_ipaddr;
2105
2106                 /*
2107                  *      Try to find a proxy port (value doesn't matter)
2108                  */
2109                 for (sock->port = port;
2110                      sock->port < 64000;
2111                      sock->port++) {
2112                         if (listen_bind(this) == 0) {
2113                                 *last = this;
2114                                 last = &(this->next); /* just in case */
2115                                 break;
2116                         }
2117                 }
2118
2119                 if (sock->port >= 64000) {
2120                         listen_free(head);
2121                         listen_free(&this);
2122                         radlog(L_ERR, "Failed to open socket for proxying");
2123                         return -1;
2124                 }
2125         }
2126
2127  done:                  /* used only in proxy code. */
2128 #endif
2129
2130         return 0;
2131 }
2132
2133 /*
2134  *      Free a linked list of listeners;
2135  */
2136 void listen_free(rad_listen_t **head)
2137 {
2138         rad_listen_t *this;
2139
2140         if (!head || !*head) return;
2141
2142         this = *head;
2143         while (this) {
2144                 rad_listen_t *next = this->next;
2145
2146                 /*
2147                  *      Other code may have eaten the FD.
2148                  */
2149                 if (this->fd >= 0) close(this->fd);
2150
2151                 if (master_listen[this->type].free) {
2152                         master_listen[this->type].free(this);
2153                 }
2154                 free(this->data);
2155                 free(this);
2156
2157                 this = next;
2158         }
2159
2160         *head = NULL;
2161 }
2162
2163 #ifdef WITH_STATS
2164 RADCLIENT_LIST *listener_find_client_list(const fr_ipaddr_t *ipaddr,
2165                                           int port)
2166 {
2167         rad_listen_t *this;
2168
2169         for (this = mainconfig.listen; this != NULL; this = this->next) {
2170                 listen_socket_t *sock;
2171
2172                 if ((this->type != RAD_LISTEN_AUTH) &&
2173                     (this->type != RAD_LISTEN_ACCT)) continue;
2174                 
2175                 sock = this->data;
2176
2177                 if ((sock->port == port) &&
2178                     (fr_ipaddr_cmp(ipaddr, &sock->ipaddr) == 0)) {
2179                         return sock->clients;
2180                 }
2181         }
2182
2183         return NULL;
2184 }
2185 #endif
2186
2187 rad_listen_t *listener_find_byipaddr(const fr_ipaddr_t *ipaddr, int port)
2188 {
2189         rad_listen_t *this;
2190
2191         for (this = mainconfig.listen; this != NULL; this = this->next) {
2192                 listen_socket_t *sock;
2193
2194                 /*
2195                  *      FIXME: For TCP, ignore the *secondary*
2196                  *      listeners associated with the main socket.
2197                  */
2198                 if ((this->type != RAD_LISTEN_AUTH) &&
2199                     (this->type != RAD_LISTEN_ACCT)) continue;
2200                 
2201                 sock = this->data;
2202
2203                 if ((sock->port == port) &&
2204                     (fr_ipaddr_cmp(ipaddr, &sock->ipaddr) == 0)) {
2205                         return this;
2206                 }
2207
2208                 if ((sock->port == port) &&
2209                     ((sock->ipaddr.af == AF_INET) &&
2210                      (sock->ipaddr.ipaddr.ip4addr.s_addr == INADDR_ANY))) {
2211                         return this;
2212                 }
2213
2214 #ifdef HAVE_STRUCT_SOCKADDR_IN6
2215                 if ((sock->port == port) &&
2216                     (sock->ipaddr.af == AF_INET6) &&
2217                     (IN6_IS_ADDR_UNSPECIFIED(&sock->ipaddr.ipaddr.ip6addr))) {
2218                         return this;
2219                 }
2220 #endif
2221         }
2222
2223         return NULL;
2224 }