175
257
entry = entry->next;
178
if (wpa_s->radius->msgs) {
181
eloop_register_timeout(first - now, 0,
182
radius_client_timer, wpa_s, NULL);
263
eloop_register_timeout(first - now.sec, 0,
264
radius_client_timer, radius, NULL);
265
hostapd_logger(radius->ctx, NULL, HOSTAPD_MODULE_RADIUS,
266
HOSTAPD_LEVEL_DEBUG, "Next RADIUS client "
267
"retransmit in %ld seconds",
268
(long int) (first - now.sec));
185
if (auth_failover && wpa_s->num_auth_servers > 1) {
271
if (auth_failover && conf->num_auth_servers > 1) {
186
272
struct hostapd_radius_server *next, *old;
187
old = wpa_s->auth_server;
188
hostapd_logger(wpa_s, NULL, HOSTAPD_MODULE_RADIUS,
273
old = conf->auth_server;
274
hostapd_logger(radius->ctx, NULL, HOSTAPD_MODULE_RADIUS,
189
275
HOSTAPD_LEVEL_NOTICE,
190
276
"No response from Authentication server "
191
277
"%s:%d - failover",
192
inet_ntoa(old->addr), old->port);
278
hostapd_ip_txt(&old->addr, abuf, sizeof(abuf)),
281
for (entry = radius->msgs; entry; entry = entry->next) {
282
if (entry->msg_type == RADIUS_AUTH)
195
if (next > &(wpa_s->auth_servers
196
[wpa_s->num_auth_servers - 1]))
197
next = wpa_s->auth_servers;
198
wpa_s->auth_server = next;
199
radius_change_server(wpa_s, next, old,
200
wpa_s->radius->auth_serv_sock, 1);
287
if (next > &(conf->auth_servers[conf->num_auth_servers - 1]))
288
next = conf->auth_servers;
289
conf->auth_server = next;
290
radius_change_server(radius, next, old,
291
radius->auth_serv_sock,
292
radius->auth_serv_sock6, 1);
203
if (acct_failover && wpa_s->num_acct_servers > 1) {
295
if (acct_failover && conf->num_acct_servers > 1) {
204
296
struct hostapd_radius_server *next, *old;
205
old = wpa_s->acct_server;
206
hostapd_logger(wpa_s, NULL, HOSTAPD_MODULE_RADIUS,
297
old = conf->acct_server;
298
hostapd_logger(radius->ctx, NULL, HOSTAPD_MODULE_RADIUS,
207
299
HOSTAPD_LEVEL_NOTICE,
208
300
"No response from Accounting server "
209
301
"%s:%d - failover",
210
inet_ntoa(old->addr), old->port);
302
hostapd_ip_txt(&old->addr, abuf, sizeof(abuf)),
305
for (entry = radius->msgs; entry; entry = entry->next) {
306
if (entry->msg_type == RADIUS_ACCT ||
307
entry->msg_type == RADIUS_ACCT_INTERIM)
212
if (next > &wpa_s->acct_servers
213
[wpa_s->num_acct_servers - 1])
214
next = wpa_s->acct_servers;
215
wpa_s->acct_server = next;
216
radius_change_server(wpa_s, next, old,
217
wpa_s->radius->acct_serv_sock, 0);
222
static void radius_client_list_add(struct wpa_supplicant *wpa_s, struct radius_msg *msg,
312
if (next > &conf->acct_servers[conf->num_acct_servers - 1])
313
next = conf->acct_servers;
314
conf->acct_server = next;
315
radius_change_server(radius, next, old,
316
radius->acct_serv_sock,
317
radius->acct_serv_sock6, 0);
322
static void radius_client_update_timeout(struct radius_client_data *radius)
326
struct radius_msg_list *entry;
328
eloop_cancel_timeout(radius_client_timer, radius, NULL);
330
if (radius->msgs == NULL) {
335
for (entry = radius->msgs; entry; entry = entry->next) {
336
if (first == 0 || entry->next_try < first)
337
first = entry->next_try;
343
eloop_register_timeout(first - now.sec, 0, radius_client_timer, radius,
345
hostapd_logger(radius->ctx, NULL, HOSTAPD_MODULE_RADIUS,
346
HOSTAPD_LEVEL_DEBUG, "Next RADIUS client retransmit in"
347
" %ld seconds\n", (long int) (first - now.sec));
351
static void radius_client_list_add(struct radius_client_data *radius,
352
struct radius_msg *msg,
223
353
RadiusType msg_type, u8 *shared_secret,
224
size_t shared_secret_len, u8 *addr)
354
size_t shared_secret_len, const u8 *addr)
226
356
struct radius_msg_list *entry, *prev;
490
void radius_client_flush(struct wpa_supplicant *wpa_s)
669
void radius_client_flush(struct radius_client_data *radius, int only_auth)
492
struct radius_msg_list *entry, *prev;
671
struct radius_msg_list *entry, *prev, *tmp;
497
eloop_cancel_timeout(radius_client_timer, wpa_s, NULL);
677
entry = radius->msgs;
499
entry = wpa_s->radius->msgs;
500
wpa_s->radius->msgs = NULL;
501
wpa_s->radius->num_msgs = 0;
505
radius_client_msg_free(prev);
680
if (!only_auth || entry->msg_type == RADIUS_AUTH) {
682
prev->next = entry->next;
684
radius->msgs = entry->next;
688
radius_client_msg_free(tmp);
696
if (radius->msgs == NULL)
697
eloop_cancel_timeout(radius_client_timer, radius, NULL);
701
void radius_client_update_acct_msgs(struct radius_client_data *radius,
703
size_t shared_secret_len)
705
struct radius_msg_list *entry;
710
for (entry = radius->msgs; entry; entry = entry->next) {
711
if (entry->msg_type == RADIUS_ACCT) {
712
entry->shared_secret = shared_secret;
713
entry->shared_secret_len = shared_secret_len;
714
radius_msg_finish_acct(entry->msg, shared_secret,
511
radius_change_server(struct wpa_supplicant *wpa_s, struct hostapd_radius_server *nserv,
722
radius_change_server(struct radius_client_data *radius,
723
struct hostapd_radius_server *nserv,
512
724
struct hostapd_radius_server *oserv,
725
int sock, int sock6, int auth)
515
727
struct sockaddr_in serv;
729
struct sockaddr_in6 serv6;
730
#endif /* CONFIG_IPV6 */
731
struct sockaddr *addr;
735
struct radius_msg_list *entry;
517
hostapd_logger(wpa_s, NULL, HOSTAPD_MODULE_RADIUS, HOSTAPD_LEVEL_INFO,
737
hostapd_logger(radius->ctx, NULL, HOSTAPD_MODULE_RADIUS,
518
739
"%s server %s:%d",
519
740
auth ? "Authentication" : "Accounting",
520
inet_ntoa(nserv->addr), nserv->port);
741
hostapd_ip_txt(&nserv->addr, abuf, sizeof(abuf)),
522
744
if (!oserv || nserv->shared_secret_len != oserv->shared_secret_len ||
523
745
memcmp(nserv->shared_secret, oserv->shared_secret,
524
746
nserv->shared_secret_len) != 0) {
525
/* Pending RADIUS packets used different shared
526
* secret, so they would need to be modified. Could
527
* update all message authenticators and
528
* User-Passwords, etc. and retry with new server. For
529
* now, just drop all pending packets. */
530
radius_client_flush(wpa_s);
532
/* Reset retry counters for the new server */
533
struct radius_msg_list *entry;
534
entry = wpa_s->radius->msgs;
536
entry->next_try = entry->first_try +
537
RADIUS_CLIENT_FIRST_WAIT;
539
entry->next_wait = RADIUS_CLIENT_FIRST_WAIT * 2;
542
if (wpa_s->radius->msgs) {
543
eloop_cancel_timeout(radius_client_timer, wpa_s, NULL);
544
eloop_register_timeout(RADIUS_CLIENT_FIRST_WAIT, 0,
545
radius_client_timer, wpa_s,
550
memset(&serv, 0, sizeof(serv));
551
serv.sin_family = AF_INET;
552
serv.sin_addr.s_addr = nserv->addr.s_addr;
553
serv.sin_port = htons(nserv->port);
555
if (connect(sock, (struct sockaddr *) &serv, sizeof(serv)) < 0) {
747
/* Pending RADIUS packets used different shared secret, so
748
* they need to be modified. Update accounting message
749
* authenticators here. Authentication messages are removed
750
* since they would require more changes and the new RADIUS
751
* server may not be prepared to receive them anyway due to
752
* missing state information. Client will likely retry
753
* authentication, so this should not be an issue. */
755
radius_client_flush(radius, 1);
757
radius_client_update_acct_msgs(
758
radius, nserv->shared_secret,
759
nserv->shared_secret_len);
763
/* Reset retry counters for the new server */
764
for (entry = radius->msgs; entry; entry = entry->next) {
765
if ((auth && entry->msg_type != RADIUS_AUTH) ||
766
(!auth && entry->msg_type != RADIUS_ACCT))
768
entry->next_try = entry->first_try + RADIUS_CLIENT_FIRST_WAIT;
770
entry->next_wait = RADIUS_CLIENT_FIRST_WAIT * 2;
774
eloop_cancel_timeout(radius_client_timer, radius, NULL);
775
eloop_register_timeout(RADIUS_CLIENT_FIRST_WAIT, 0,
776
radius_client_timer, radius, NULL);
779
switch (nserv->addr.af) {
781
memset(&serv, 0, sizeof(serv));
782
serv.sin_family = AF_INET;
783
serv.sin_addr.s_addr = nserv->addr.u.v4.s_addr;
784
serv.sin_port = htons(nserv->port);
785
addr = (struct sockaddr *) &serv;
786
addrlen = sizeof(serv);
791
memset(&serv6, 0, sizeof(serv6));
792
serv6.sin6_family = AF_INET6;
793
memcpy(&serv6.sin6_addr, &nserv->addr.u.v6,
794
sizeof(struct in6_addr));
795
serv6.sin6_port = htons(nserv->port);
796
addr = (struct sockaddr *) &serv6;
797
addrlen = sizeof(serv6);
800
#endif /* CONFIG_IPV6 */
805
if (connect(sel_sock, addr, addrlen) < 0) {
556
806
perror("connect[radius]");
811
radius->auth_sock = sel_sock;
813
radius->acct_sock = sel_sock;
564
819
static void radius_retry_primary_timer(void *eloop_ctx, void *timeout_ctx)
566
struct wpa_supplicant *wpa_s = eloop_ctx;
821
struct radius_client_data *radius = eloop_ctx;
822
struct hostapd_radius_servers *conf = radius->conf;
567
823
struct hostapd_radius_server *oserv;
569
if (wpa_s->radius->auth_serv_sock >= 0 && wpa_s->auth_servers &&
570
wpa_s->auth_server != wpa_s->auth_servers) {
571
oserv = wpa_s->auth_server;
572
wpa_s->auth_server = wpa_s->auth_servers;
573
radius_change_server(wpa_s, wpa_s->auth_server, oserv,
574
wpa_s->radius->auth_serv_sock, 1);
577
if (wpa_s->radius->acct_serv_sock >= 0 && wpa_s->acct_servers &&
578
wpa_s->acct_server != wpa_s->acct_servers) {
579
oserv = wpa_s->acct_server;
580
wpa_s->acct_server = wpa_s->acct_servers;
581
radius_change_server(wpa_s, wpa_s->acct_server, oserv,
582
wpa_s->radius->acct_serv_sock, 0);
585
if (wpa_s->radius_retry_primary_interval)
586
eloop_register_timeout(wpa_s->
587
radius_retry_primary_interval, 0,
588
radius_retry_primary_timer, wpa_s, NULL);
592
static int radius_client_init_auth(struct wpa_supplicant *wpa_s)
594
wpa_s->radius->auth_serv_sock = socket(PF_INET, SOCK_DGRAM, 0);
595
if (wpa_s->radius->auth_serv_sock < 0) {
596
perror("socket[PF_INET,SOCK_DGRAM]");
600
radius_change_server(wpa_s, wpa_s->auth_server, NULL,
601
wpa_s->radius->auth_serv_sock, 1);
603
if (eloop_register_read_sock(wpa_s->radius->auth_serv_sock,
604
radius_client_receive, wpa_s,
605
(void *) RADIUS_AUTH)) {
606
printf("Could not register read socket for authentication "
615
static int radius_client_init_acct(struct wpa_supplicant *wpa_s)
617
wpa_s->radius->acct_serv_sock = socket(PF_INET, SOCK_DGRAM, 0);
618
if (wpa_s->radius->acct_serv_sock < 0) {
619
perror("socket[PF_INET,SOCK_DGRAM]");
623
radius_change_server(wpa_s, wpa_s->acct_server, NULL,
624
wpa_s->radius->acct_serv_sock, 0);
626
if (eloop_register_read_sock(wpa_s->radius->acct_serv_sock,
627
radius_client_receive, wpa_s,
628
(void *) RADIUS_ACCT)) {
629
printf("Could not register read socket for accounting "
638
int radius_client_init(struct wpa_supplicant *wpa_s)
640
wpa_s->radius = malloc(sizeof(struct radius_client_data));
641
if (wpa_s->radius == NULL)
644
memset(wpa_s->radius, 0, sizeof(struct radius_client_data));
645
wpa_s->radius->auth_serv_sock = wpa_s->radius->acct_serv_sock = -1;
647
if (wpa_s->auth_server && radius_client_init_auth(wpa_s))
650
if (wpa_s->acct_server && radius_client_init_acct(wpa_s))
653
if (wpa_s->radius_retry_primary_interval)
654
eloop_register_timeout(wpa_s->radius_retry_primary_interval, 0,
655
radius_retry_primary_timer, wpa_s,
662
void radius_client_deinit(struct wpa_supplicant *wpa_s)
825
if (radius->auth_sock >= 0 && conf->auth_servers &&
826
conf->auth_server != conf->auth_servers) {
827
oserv = conf->auth_server;
828
conf->auth_server = conf->auth_servers;
829
radius_change_server(radius, conf->auth_server, oserv,
830
radius->auth_serv_sock,
831
radius->auth_serv_sock6, 1);
834
if (radius->acct_sock >= 0 && conf->acct_servers &&
835
conf->acct_server != conf->acct_servers) {
836
oserv = conf->acct_server;
837
conf->acct_server = conf->acct_servers;
838
radius_change_server(radius, conf->acct_server, oserv,
839
radius->acct_serv_sock,
840
radius->acct_serv_sock6, 0);
843
if (conf->retry_primary_interval)
844
eloop_register_timeout(conf->retry_primary_interval, 0,
845
radius_retry_primary_timer, radius,
850
static int radius_client_init_auth(struct radius_client_data *radius)
852
struct hostapd_radius_servers *conf = radius->conf;
855
radius->auth_serv_sock = socket(PF_INET, SOCK_DGRAM, 0);
856
if (radius->auth_serv_sock < 0)
857
perror("socket[PF_INET,SOCK_DGRAM]");
862
radius->auth_serv_sock6 = socket(PF_INET6, SOCK_DGRAM, 0);
863
if (radius->auth_serv_sock6 < 0)
864
perror("socket[PF_INET6,SOCK_DGRAM]");
867
#endif /* CONFIG_IPV6 */
872
radius_change_server(radius, conf->auth_server, NULL,
873
radius->auth_serv_sock, radius->auth_serv_sock6,
876
if (radius->auth_serv_sock >= 0 &&
877
eloop_register_read_sock(radius->auth_serv_sock,
878
radius_client_receive, radius,
879
(void *) RADIUS_AUTH)) {
880
printf("Could not register read socket for authentication "
886
if (radius->auth_serv_sock6 >= 0 &&
887
eloop_register_read_sock(radius->auth_serv_sock6,
888
radius_client_receive, radius,
889
(void *) RADIUS_AUTH)) {
890
printf("Could not register read socket for authentication "
894
#endif /* CONFIG_IPV6 */
900
static int radius_client_init_acct(struct radius_client_data *radius)
902
struct hostapd_radius_servers *conf = radius->conf;
905
radius->acct_serv_sock = socket(PF_INET, SOCK_DGRAM, 0);
906
if (radius->acct_serv_sock < 0)
907
perror("socket[PF_INET,SOCK_DGRAM]");
911
radius_change_server(radius, conf->acct_server, NULL,
912
radius->acct_serv_sock, radius->acct_serv_sock6,
915
if (radius->acct_serv_sock >= 0 &&
916
eloop_register_read_sock(radius->acct_serv_sock,
917
radius_client_receive, radius,
918
(void *) RADIUS_ACCT)) {
919
printf("Could not register read socket for accounting "
925
if (radius->acct_serv_sock6 >= 0 &&
926
eloop_register_read_sock(radius->acct_serv_sock6,
927
radius_client_receive, radius,
928
(void *) RADIUS_ACCT)) {
929
printf("Could not register read socket for accounting "
933
#endif /* CONFIG_IPV6 */
939
struct radius_client_data *
940
radius_client_init(void *ctx, struct hostapd_radius_servers *conf)
942
struct radius_client_data *radius;
944
radius = wpa_zalloc(sizeof(struct radius_client_data));
950
radius->auth_serv_sock = radius->acct_serv_sock =
951
radius->auth_serv_sock6 = radius->acct_serv_sock6 =
952
radius->auth_sock = radius->acct_sock = -1;
954
if (conf->auth_server && radius_client_init_auth(radius)) {
955
radius_client_deinit(radius);
959
if (conf->acct_server && radius_client_init_acct(radius)) {
960
radius_client_deinit(radius);
964
if (conf->retry_primary_interval)
965
eloop_register_timeout(conf->retry_primary_interval, 0,
966
radius_retry_primary_timer, radius,
973
void radius_client_deinit(struct radius_client_data *radius)
667
eloop_cancel_timeout(radius_retry_primary_timer, wpa_s, NULL);
669
radius_client_flush(wpa_s);
670
free(wpa_s->radius->auth_handlers);
671
free(wpa_s->radius->acct_handlers);
673
wpa_s->radius = NULL;
978
eloop_cancel_timeout(radius_retry_primary_timer, radius, NULL);
980
radius_client_flush(radius, 0);
981
free(radius->auth_handlers);
982
free(radius->acct_handlers);
987
void radius_client_flush_auth(struct radius_client_data *radius, u8 *addr)
989
struct radius_msg_list *entry, *prev, *tmp;
992
entry = radius->msgs;
994
if (entry->msg_type == RADIUS_AUTH &&
995
memcmp(entry->addr, addr, ETH_ALEN) == 0) {
996
hostapd_logger(radius->ctx, addr,
997
HOSTAPD_MODULE_RADIUS,
999
"Removing pending RADIUS authentication"
1000
" message for removed client");
1003
prev->next = entry->next;
1005
radius->msgs = entry->next;
1008
entry = entry->next;
1009
radius_client_msg_free(tmp);
1015
entry = entry->next;
1020
static int radius_client_dump_auth_server(char *buf, size_t buflen,
1021
struct hostapd_radius_server *serv,
1022
struct radius_client_data *cli)
1025
struct radius_msg_list *msg;
1029
for (msg = cli->msgs; msg; msg = msg->next) {
1030
if (msg->msg_type == RADIUS_AUTH)
1035
return snprintf(buf, buflen,
1036
"radiusAuthServerIndex=%d\n"
1037
"radiusAuthServerAddress=%s\n"
1038
"radiusAuthClientServerPortNumber=%d\n"
1039
"radiusAuthClientRoundTripTime=%d\n"
1040
"radiusAuthClientAccessRequests=%u\n"
1041
"radiusAuthClientAccessRetransmissions=%u\n"
1042
"radiusAuthClientAccessAccepts=%u\n"
1043
"radiusAuthClientAccessRejects=%u\n"
1044
"radiusAuthClientAccessChallenges=%u\n"
1045
"radiusAuthClientMalformedAccessResponses=%u\n"
1046
"radiusAuthClientBadAuthenticators=%u\n"
1047
"radiusAuthClientPendingRequests=%u\n"
1048
"radiusAuthClientTimeouts=%u\n"
1049
"radiusAuthClientUnknownTypes=%u\n"
1050
"radiusAuthClientPacketsDropped=%u\n",
1052
hostapd_ip_txt(&serv->addr, abuf, sizeof(abuf)),
1054
serv->round_trip_time,
1056
serv->retransmissions,
1057
serv->access_accepts,
1058
serv->access_rejects,
1059
serv->access_challenges,
1060
serv->malformed_responses,
1061
serv->bad_authenticators,
1064
serv->unknown_types,
1065
serv->packets_dropped);
1069
static int radius_client_dump_acct_server(char *buf, size_t buflen,
1070
struct hostapd_radius_server *serv,
1071
struct radius_client_data *cli)
1074
struct radius_msg_list *msg;
1078
for (msg = cli->msgs; msg; msg = msg->next) {
1079
if (msg->msg_type == RADIUS_ACCT ||
1080
msg->msg_type == RADIUS_ACCT_INTERIM)
1085
return snprintf(buf, buflen,
1086
"radiusAccServerIndex=%d\n"
1087
"radiusAccServerAddress=%s\n"
1088
"radiusAccClientServerPortNumber=%d\n"
1089
"radiusAccClientRoundTripTime=%d\n"
1090
"radiusAccClientRequests=%u\n"
1091
"radiusAccClientRetransmissions=%u\n"
1092
"radiusAccClientResponses=%u\n"
1093
"radiusAccClientMalformedResponses=%u\n"
1094
"radiusAccClientBadAuthenticators=%u\n"
1095
"radiusAccClientPendingRequests=%u\n"
1096
"radiusAccClientTimeouts=%u\n"
1097
"radiusAccClientUnknownTypes=%u\n"
1098
"radiusAccClientPacketsDropped=%u\n",
1100
hostapd_ip_txt(&serv->addr, abuf, sizeof(abuf)),
1102
serv->round_trip_time,
1104
serv->retransmissions,
1106
serv->malformed_responses,
1107
serv->bad_authenticators,
1110
serv->unknown_types,
1111
serv->packets_dropped);
1115
int radius_client_get_mib(struct radius_client_data *radius, char *buf,
1118
struct hostapd_radius_servers *conf = radius->conf;
1120
struct hostapd_radius_server *serv;
1123
if (conf->auth_servers) {
1124
for (i = 0; i < conf->num_auth_servers; i++) {
1125
serv = &conf->auth_servers[i];
1126
count += radius_client_dump_auth_server(
1127
buf + count, buflen - count, serv,
1128
serv == conf->auth_server ?
1133
if (conf->acct_servers) {
1134
for (i = 0; i < conf->num_acct_servers; i++) {
1135
serv = &conf->acct_servers[i];
1136
count += radius_client_dump_acct_server(
1137
buf + count, buflen - count, serv,
1138
serv == conf->acct_server ?