1 /* 2 * WPA Supplicant / UNIX domain socket -based control interface 3 * Copyright (c) 2004-2020, Jouni Malinen <j@w1.fi> 4 * 5 * This software may be distributed under the terms of the BSD license. 6 * See README for more details. 7 */ 8 9 #include "includes.h" 10 #include <sys/un.h> 11 #include <sys/stat.h> 12 #include <grp.h> 13 #include <stddef.h> 14 #include <unistd.h> 15 #include <fcntl.h> 16 #ifdef __linux__ 17 #include <sys/ioctl.h> 18 #endif /* __linux__ */ 19 #ifdef ANDROID 20 #include <cutils/sockets.h> 21 #endif /* ANDROID */ 22 23 #include "utils/common.h" 24 #include "utils/eloop.h" 25 #include "utils/list.h" 26 #include "common/ctrl_iface_common.h" 27 #include "eapol_supp/eapol_supp_sm.h" 28 #include "config.h" 29 #include "wpa_supplicant_i.h" 30 #include "ctrl_iface.h" 31 32 /* Per-interface ctrl_iface */ 33 34 struct ctrl_iface_priv { 35 struct wpa_supplicant *wpa_s; 36 int sock; 37 struct dl_list ctrl_dst; 38 int android_control_socket; 39 struct dl_list msg_queue; 40 unsigned int throttle_count; 41 }; 42 43 44 struct ctrl_iface_global_priv { 45 struct wpa_global *global; 46 int sock; 47 struct dl_list ctrl_dst; 48 int android_control_socket; 49 struct dl_list msg_queue; 50 unsigned int throttle_count; 51 }; 52 53 struct ctrl_iface_msg { 54 struct dl_list list; 55 struct wpa_supplicant *wpa_s; 56 int level; 57 enum wpa_msg_type type; 58 const char *txt; 59 size_t len; 60 }; 61 62 63 static void wpa_supplicant_ctrl_iface_send(struct wpa_supplicant *wpa_s, 64 const char *ifname, int sock, 65 struct dl_list *ctrl_dst, 66 int level, const char *buf, 67 size_t len, 68 struct ctrl_iface_priv *priv, 69 struct ctrl_iface_global_priv *gp); 70 static int wpas_ctrl_iface_reinit(struct wpa_supplicant *wpa_s, 71 struct ctrl_iface_priv *priv); 72 static int wpas_ctrl_iface_global_reinit(struct wpa_global *global, 73 struct ctrl_iface_global_priv *priv); 74 75 76 static void wpas_ctrl_sock_debug(const char *title, int sock, const char *buf, 77 size_t len) 78 { 79 #ifdef __linux__ 80 socklen_t optlen; 81 int sndbuf, outq; 82 int level = MSG_MSGDUMP; 83 84 if (len >= 5 && os_strncmp(buf, "PONG\n", 5) == 0) 85 level = MSG_EXCESSIVE; 86 87 optlen = sizeof(sndbuf); 88 sndbuf = 0; 89 if (getsockopt(sock, SOL_SOCKET, SO_SNDBUF, &sndbuf, &optlen) < 0) 90 sndbuf = -1; 91 92 if (ioctl(sock, TIOCOUTQ, &outq) < 0) 93 outq = -1; 94 95 wpa_printf(level, 96 "CTRL-DEBUG: %s: sock=%d sndbuf=%d outq=%d send_len=%d", 97 title, sock, sndbuf, outq, (int) len); 98 #endif /* __linux__ */ 99 } 100 101 102 static int wpa_supplicant_ctrl_iface_attach(struct dl_list *ctrl_dst, 103 struct sockaddr_storage *from, 104 socklen_t fromlen, int global) 105 { 106 return ctrl_iface_attach(ctrl_dst, from, fromlen, NULL); 107 } 108 109 110 static int wpa_supplicant_ctrl_iface_detach(struct dl_list *ctrl_dst, 111 struct sockaddr_storage *from, 112 socklen_t fromlen) 113 { 114 return ctrl_iface_detach(ctrl_dst, from, fromlen); 115 } 116 117 118 static int wpa_supplicant_ctrl_iface_level(struct ctrl_iface_priv *priv, 119 struct sockaddr_storage *from, 120 socklen_t fromlen, 121 char *level) 122 { 123 wpa_printf(MSG_DEBUG, "CTRL_IFACE LEVEL %s", level); 124 125 return ctrl_iface_level(&priv->ctrl_dst, from, fromlen, level); 126 } 127 128 129 static void wpa_supplicant_ctrl_iface_receive(int sock, void *eloop_ctx, 130 void *sock_ctx) 131 { 132 struct wpa_supplicant *wpa_s = eloop_ctx; 133 struct ctrl_iface_priv *priv = sock_ctx; 134 char *buf; 135 int res; 136 struct sockaddr_storage from; 137 socklen_t fromlen = sizeof(from); 138 char *reply = NULL, *reply_buf = NULL; 139 size_t reply_len = 0; 140 int new_attached = 0; 141 142 buf = os_malloc(CTRL_IFACE_MAX_LEN + 1); 143 if (!buf) 144 return; 145 res = recvfrom(sock, buf, CTRL_IFACE_MAX_LEN + 1, 0, 146 (struct sockaddr *) &from, &fromlen); 147 if (res < 0) { 148 wpa_printf(MSG_ERROR, "recvfrom(ctrl_iface): %s", 149 strerror(errno)); 150 os_free(buf); 151 return; 152 } 153 if ((size_t) res > CTRL_IFACE_MAX_LEN) { 154 wpa_printf(MSG_ERROR, "recvform(ctrl_iface): input truncated"); 155 os_free(buf); 156 return; 157 } 158 buf[res] = '\0'; 159 160 if (os_strcmp(buf, "ATTACH") == 0) { 161 if (wpa_supplicant_ctrl_iface_attach(&priv->ctrl_dst, &from, 162 fromlen, 0)) 163 reply_len = 1; 164 else { 165 new_attached = 1; 166 reply_len = 2; 167 } 168 } else if (os_strcmp(buf, "DETACH") == 0) { 169 if (wpa_supplicant_ctrl_iface_detach(&priv->ctrl_dst, &from, 170 fromlen)) 171 reply_len = 1; 172 else 173 reply_len = 2; 174 } else if (os_strncmp(buf, "LEVEL ", 6) == 0) { 175 if (wpa_supplicant_ctrl_iface_level(priv, &from, fromlen, 176 buf + 6)) 177 reply_len = 1; 178 else 179 reply_len = 2; 180 } else { 181 sockaddr_print(wpas_ctrl_cmd_debug_level(buf), 182 "Control interface recv command from:", 183 &from, fromlen); 184 reply_buf = wpa_supplicant_ctrl_iface_process(wpa_s, buf, 185 &reply_len); 186 reply = reply_buf; 187 188 /* 189 * There could be some password/key material in the command, so 190 * clear the buffer explicitly now that it is not needed 191 * anymore. 192 */ 193 os_memset(buf, 0, res); 194 } 195 196 if (!reply && reply_len == 1) { 197 reply = "FAIL\n"; 198 reply_len = 5; 199 } else if (!reply && reply_len == 2) { 200 reply = "OK\n"; 201 reply_len = 3; 202 } 203 204 if (reply) { 205 wpas_ctrl_sock_debug("ctrl_sock-sendto", sock, reply, 206 reply_len); 207 if (sendto(sock, reply, reply_len, 0, (struct sockaddr *) &from, 208 fromlen) < 0) { 209 int _errno = errno; 210 wpa_dbg(wpa_s, MSG_DEBUG, 211 "ctrl_iface sendto failed: %d - %s", 212 _errno, strerror(_errno)); 213 if (_errno == ENOBUFS || _errno == EAGAIN) { 214 /* 215 * The socket send buffer could be full. This 216 * may happen if client programs are not 217 * receiving their pending messages. Close and 218 * reopen the socket as a workaround to avoid 219 * getting stuck being unable to send any new 220 * responses. 221 */ 222 sock = wpas_ctrl_iface_reinit(wpa_s, priv); 223 if (sock < 0) { 224 wpa_dbg(wpa_s, MSG_DEBUG, "Failed to reinitialize ctrl_iface socket"); 225 } 226 } 227 if (new_attached) { 228 wpa_dbg(wpa_s, MSG_DEBUG, "Failed to send response to ATTACH - detaching"); 229 new_attached = 0; 230 wpa_supplicant_ctrl_iface_detach( 231 &priv->ctrl_dst, &from, fromlen); 232 } 233 } 234 } 235 os_free(reply_buf); 236 os_free(buf); 237 238 if (new_attached) 239 eapol_sm_notify_ctrl_attached(wpa_s->eapol); 240 } 241 242 243 static char * wpa_supplicant_ctrl_iface_path(struct wpa_supplicant *wpa_s) 244 { 245 char *buf; 246 size_t len; 247 char *pbuf, *dir = NULL; 248 int res; 249 250 if (wpa_s->conf->ctrl_interface == NULL) 251 return NULL; 252 253 pbuf = os_strdup(wpa_s->conf->ctrl_interface); 254 if (pbuf == NULL) 255 return NULL; 256 if (os_strncmp(pbuf, "DIR=", 4) == 0) { 257 char *gid_str; 258 dir = pbuf + 4; 259 gid_str = os_strstr(dir, " GROUP="); 260 if (gid_str) 261 *gid_str = '\0'; 262 } else 263 dir = pbuf; 264 265 len = os_strlen(dir) + os_strlen(wpa_s->ifname) + 2; 266 buf = os_malloc(len); 267 if (buf == NULL) { 268 os_free(pbuf); 269 return NULL; 270 } 271 272 res = os_snprintf(buf, len, "%s/%s", dir, wpa_s->ifname); 273 if (os_snprintf_error(len, res)) { 274 os_free(pbuf); 275 os_free(buf); 276 return NULL; 277 } 278 #ifdef __CYGWIN__ 279 { 280 /* Windows/WinPcap uses interface names that are not suitable 281 * as a file name - convert invalid chars to underscores */ 282 char *pos = buf; 283 while (*pos) { 284 if (*pos == '\\') 285 *pos = '_'; 286 pos++; 287 } 288 } 289 #endif /* __CYGWIN__ */ 290 os_free(pbuf); 291 return buf; 292 } 293 294 295 static int wpas_ctrl_iface_throttle(int sock) 296 { 297 #ifdef __linux__ 298 socklen_t optlen; 299 int sndbuf, outq; 300 301 optlen = sizeof(sndbuf); 302 sndbuf = 0; 303 if (getsockopt(sock, SOL_SOCKET, SO_SNDBUF, &sndbuf, &optlen) < 0 || 304 ioctl(sock, TIOCOUTQ, &outq) < 0 || 305 sndbuf <= 0 || outq < 0) 306 return 0; 307 return outq > sndbuf / 2; 308 #else /* __linux__ */ 309 return 0; 310 #endif /* __linux__ */ 311 } 312 313 314 static void wpas_ctrl_msg_send_pending_global(struct wpa_global *global) 315 { 316 struct ctrl_iface_global_priv *gpriv; 317 struct ctrl_iface_msg *msg; 318 319 gpriv = global->ctrl_iface; 320 while (gpriv && !dl_list_empty(&gpriv->msg_queue) && 321 !wpas_ctrl_iface_throttle(gpriv->sock)) { 322 msg = dl_list_first(&gpriv->msg_queue, struct ctrl_iface_msg, 323 list); 324 if (!msg) 325 break; 326 dl_list_del(&msg->list); 327 wpa_supplicant_ctrl_iface_send( 328 msg->wpa_s, 329 msg->type != WPA_MSG_PER_INTERFACE ? 330 NULL : msg->wpa_s->ifname, 331 gpriv->sock, &gpriv->ctrl_dst, msg->level, 332 msg->txt, msg->len, NULL, gpriv); 333 os_free(msg); 334 } 335 } 336 337 338 static void wpas_ctrl_msg_send_pending_iface(struct wpa_supplicant *wpa_s) 339 { 340 struct ctrl_iface_priv *priv; 341 struct ctrl_iface_msg *msg; 342 343 priv = wpa_s->ctrl_iface; 344 while (priv && !dl_list_empty(&priv->msg_queue) && 345 !wpas_ctrl_iface_throttle(priv->sock)) { 346 msg = dl_list_first(&priv->msg_queue, struct ctrl_iface_msg, 347 list); 348 if (!msg) 349 break; 350 dl_list_del(&msg->list); 351 wpa_supplicant_ctrl_iface_send(wpa_s, NULL, priv->sock, 352 &priv->ctrl_dst, msg->level, 353 msg->txt, msg->len, priv, NULL); 354 os_free(msg); 355 } 356 } 357 358 359 static void wpas_ctrl_msg_queue_timeout(void *eloop_ctx, void *timeout_ctx) 360 { 361 struct wpa_supplicant *wpa_s = eloop_ctx; 362 struct ctrl_iface_priv *priv; 363 struct ctrl_iface_global_priv *gpriv; 364 int sock = -1, gsock = -1; 365 366 wpas_ctrl_msg_send_pending_global(wpa_s->global); 367 wpas_ctrl_msg_send_pending_iface(wpa_s); 368 369 priv = wpa_s->ctrl_iface; 370 if (priv && !dl_list_empty(&priv->msg_queue)) 371 sock = priv->sock; 372 373 gpriv = wpa_s->global->ctrl_iface; 374 if (gpriv && !dl_list_empty(&gpriv->msg_queue)) 375 gsock = gpriv->sock; 376 377 if (sock > -1 || gsock > -1) { 378 /* Continue pending message transmission from a timeout */ 379 wpa_printf(MSG_MSGDUMP, 380 "CTRL: Had to throttle pending event message transmission for (sock %d gsock %d)", 381 sock, gsock); 382 eloop_register_timeout(0, 20000, wpas_ctrl_msg_queue_timeout, 383 wpa_s, NULL); 384 } 385 } 386 387 388 static void wpas_ctrl_msg_queue(struct dl_list *queue, 389 struct wpa_supplicant *wpa_s, int level, 390 enum wpa_msg_type type, 391 const char *txt, size_t len) 392 { 393 struct ctrl_iface_msg *msg; 394 395 msg = os_zalloc(sizeof(*msg) + len); 396 if (!msg) 397 return; 398 399 msg->wpa_s = wpa_s; 400 msg->level = level; 401 msg->type = type; 402 os_memcpy(msg + 1, txt, len); 403 msg->txt = (const char *) (msg + 1); 404 msg->len = len; 405 dl_list_add_tail(queue, &msg->list); 406 eloop_cancel_timeout(wpas_ctrl_msg_queue_timeout, wpa_s, NULL); 407 eloop_register_timeout(0, 0, wpas_ctrl_msg_queue_timeout, wpa_s, NULL); 408 } 409 410 411 static void wpas_ctrl_msg_queue_limit(unsigned int throttle_count, 412 struct dl_list *queue) 413 { 414 struct ctrl_iface_msg *msg; 415 416 if (throttle_count < 2000) 417 return; 418 419 msg = dl_list_first(queue, struct ctrl_iface_msg, list); 420 if (msg) { 421 wpa_printf(MSG_DEBUG, "CTRL: Dropped oldest pending message"); 422 dl_list_del(&msg->list); 423 os_free(msg); 424 } 425 } 426 427 428 static void wpa_supplicant_ctrl_iface_msg_cb(void *ctx, int level, 429 enum wpa_msg_type type, 430 const char *txt, size_t len) 431 { 432 struct wpa_supplicant *wpa_s = ctx; 433 struct ctrl_iface_priv *priv; 434 struct ctrl_iface_global_priv *gpriv; 435 436 if (wpa_s == NULL) 437 return; 438 439 gpriv = wpa_s->global->ctrl_iface; 440 441 if (type != WPA_MSG_NO_GLOBAL && gpriv && 442 !dl_list_empty(&gpriv->ctrl_dst)) { 443 if (!dl_list_empty(&gpriv->msg_queue) || 444 wpas_ctrl_iface_throttle(gpriv->sock)) { 445 if (gpriv->throttle_count == 0) { 446 wpa_printf(MSG_MSGDUMP, 447 "CTRL: Had to throttle global event message for sock %d", 448 gpriv->sock); 449 } 450 gpriv->throttle_count++; 451 wpas_ctrl_msg_queue_limit(gpriv->throttle_count, 452 &gpriv->msg_queue); 453 wpas_ctrl_msg_queue(&gpriv->msg_queue, wpa_s, level, 454 type, txt, len); 455 } else { 456 if (gpriv->throttle_count) { 457 wpa_printf(MSG_MSGDUMP, 458 "CTRL: Had to throttle %u global event message(s) for sock %d", 459 gpriv->throttle_count, gpriv->sock); 460 } 461 gpriv->throttle_count = 0; 462 wpa_supplicant_ctrl_iface_send( 463 wpa_s, 464 type != WPA_MSG_PER_INTERFACE ? 465 NULL : wpa_s->ifname, 466 gpriv->sock, &gpriv->ctrl_dst, level, 467 txt, len, NULL, gpriv); 468 } 469 } 470 471 priv = wpa_s->ctrl_iface; 472 473 if (type != WPA_MSG_ONLY_GLOBAL && priv) { 474 if (!dl_list_empty(&priv->msg_queue) || 475 wpas_ctrl_iface_throttle(priv->sock)) { 476 if (priv->throttle_count == 0) { 477 wpa_printf(MSG_MSGDUMP, 478 "CTRL: Had to throttle event message for sock %d", 479 priv->sock); 480 } 481 priv->throttle_count++; 482 wpas_ctrl_msg_queue_limit(priv->throttle_count, 483 &priv->msg_queue); 484 wpas_ctrl_msg_queue(&priv->msg_queue, wpa_s, level, 485 type, txt, len); 486 } else { 487 if (priv->throttle_count) { 488 wpa_printf(MSG_MSGDUMP, 489 "CTRL: Had to throttle %u event message(s) for sock %d", 490 priv->throttle_count, priv->sock); 491 } 492 priv->throttle_count = 0; 493 wpa_supplicant_ctrl_iface_send(wpa_s, NULL, priv->sock, 494 &priv->ctrl_dst, level, 495 txt, len, priv, NULL); 496 } 497 } 498 } 499 500 501 static int wpas_ctrl_iface_open_sock(struct wpa_supplicant *wpa_s, 502 struct ctrl_iface_priv *priv) 503 { 504 struct sockaddr_un addr; 505 char *fname = NULL; 506 gid_t gid = 0; 507 int gid_set = 0; 508 char *buf, *dir = NULL, *gid_str = NULL; 509 struct group *grp; 510 char *endp; 511 int flags; 512 513 buf = os_strdup(wpa_s->conf->ctrl_interface); 514 if (buf == NULL) 515 goto fail; 516 #ifdef ANDROID 517 os_snprintf(addr.sun_path, sizeof(addr.sun_path), "wpa_%s", 518 wpa_s->conf->ctrl_interface); 519 priv->sock = android_get_control_socket(addr.sun_path); 520 if (priv->sock >= 0) { 521 priv->android_control_socket = 1; 522 goto havesock; 523 } 524 #endif /* ANDROID */ 525 if (os_strncmp(buf, "DIR=", 4) == 0) { 526 dir = buf + 4; 527 gid_str = os_strstr(dir, " GROUP="); 528 if (gid_str) { 529 *gid_str = '\0'; 530 gid_str += 7; 531 } 532 } else { 533 dir = buf; 534 gid_str = wpa_s->conf->ctrl_interface_group; 535 } 536 537 if (mkdir(dir, S_IRWXU | S_IRWXG) < 0) { 538 if (errno == EEXIST) { 539 wpa_printf(MSG_DEBUG, "Using existing control " 540 "interface directory."); 541 } else { 542 wpa_printf(MSG_ERROR, "mkdir[ctrl_interface=%s]: %s", 543 dir, strerror(errno)); 544 goto fail; 545 } 546 } 547 548 #ifdef ANDROID 549 /* 550 * wpa_supplicant is started from /init.*.rc on Android and that seems 551 * to be using umask 0077 which would leave the control interface 552 * directory without group access. This breaks things since Wi-Fi 553 * framework assumes that this directory can be accessed by other 554 * applications in the wifi group. Fix this by adding group access even 555 * if umask value would prevent this. 556 */ 557 if (chmod(dir, S_IRWXU | S_IRWXG) < 0) { 558 wpa_printf(MSG_ERROR, "CTRL: Could not chmod directory: %s", 559 strerror(errno)); 560 /* Try to continue anyway */ 561 } 562 #endif /* ANDROID */ 563 564 if (gid_str) { 565 grp = getgrnam(gid_str); 566 if (grp) { 567 gid = grp->gr_gid; 568 gid_set = 1; 569 wpa_printf(MSG_DEBUG, "ctrl_interface_group=%d" 570 " (from group name '%s')", 571 (int) gid, gid_str); 572 } else { 573 /* Group name not found - try to parse this as gid */ 574 gid = strtol(gid_str, &endp, 10); 575 if (*gid_str == '\0' || *endp != '\0') { 576 wpa_printf(MSG_ERROR, "CTRL: Invalid group " 577 "'%s'", gid_str); 578 goto fail; 579 } 580 gid_set = 1; 581 wpa_printf(MSG_DEBUG, "ctrl_interface_group=%d", 582 (int) gid); 583 } 584 } 585 586 if (gid_set && lchown(dir, -1, gid) < 0) { 587 wpa_printf(MSG_ERROR, "lchown[ctrl_interface=%s,gid=%d]: %s", 588 dir, (int) gid, strerror(errno)); 589 goto fail; 590 } 591 592 /* Make sure the group can enter and read the directory */ 593 if (gid_set && 594 chmod(dir, S_IRUSR | S_IWUSR | S_IXUSR | S_IRGRP | S_IXGRP) < 0) { 595 wpa_printf(MSG_ERROR, "CTRL: chmod[ctrl_interface]: %s", 596 strerror(errno)); 597 goto fail; 598 } 599 600 if (os_strlen(dir) + 1 + os_strlen(wpa_s->ifname) >= 601 sizeof(addr.sun_path)) { 602 wpa_printf(MSG_ERROR, "ctrl_iface path limit exceeded"); 603 goto fail; 604 } 605 606 priv->sock = socket(PF_UNIX, SOCK_DGRAM, 0); 607 if (priv->sock < 0) { 608 wpa_printf(MSG_ERROR, "socket(PF_UNIX): %s", strerror(errno)); 609 goto fail; 610 } 611 612 os_memset(&addr, 0, sizeof(addr)); 613 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__) 614 addr.sun_len = sizeof(addr); 615 #endif /* __FreeBSD__ */ 616 addr.sun_family = AF_UNIX; 617 fname = wpa_supplicant_ctrl_iface_path(wpa_s); 618 if (fname == NULL) 619 goto fail; 620 os_strlcpy(addr.sun_path, fname, sizeof(addr.sun_path)); 621 if (bind(priv->sock, (struct sockaddr *) &addr, sizeof(addr)) < 0) { 622 wpa_printf(MSG_DEBUG, "ctrl_iface bind(PF_UNIX) failed: %s", 623 strerror(errno)); 624 if (connect(priv->sock, (struct sockaddr *) &addr, 625 sizeof(addr)) < 0) { 626 wpa_printf(MSG_DEBUG, "ctrl_iface exists, but does not" 627 " allow connections - assuming it was left" 628 "over from forced program termination"); 629 if (unlink(fname) < 0) { 630 wpa_printf(MSG_ERROR, 631 "Could not unlink existing ctrl_iface socket '%s': %s", 632 fname, strerror(errno)); 633 goto fail; 634 } 635 if (bind(priv->sock, (struct sockaddr *) &addr, 636 sizeof(addr)) < 0) { 637 wpa_printf(MSG_ERROR, "supp-ctrl-iface-init: bind(PF_UNIX): %s", 638 strerror(errno)); 639 goto fail; 640 } 641 wpa_printf(MSG_DEBUG, "Successfully replaced leftover " 642 "ctrl_iface socket '%s'", fname); 643 } else { 644 wpa_printf(MSG_INFO, "ctrl_iface exists and seems to " 645 "be in use - cannot override it"); 646 wpa_printf(MSG_INFO, "Delete '%s' manually if it is " 647 "not used anymore", fname); 648 os_free(fname); 649 fname = NULL; 650 goto fail; 651 } 652 } 653 654 if (gid_set && lchown(fname, -1, gid) < 0) { 655 wpa_printf(MSG_ERROR, "lchown[ctrl_interface=%s,gid=%d]: %s", 656 fname, (int) gid, strerror(errno)); 657 goto fail; 658 } 659 660 if (chmod(fname, S_IRWXU | S_IRWXG) < 0) { 661 wpa_printf(MSG_ERROR, "chmod[ctrl_interface=%s]: %s", 662 fname, strerror(errno)); 663 goto fail; 664 } 665 os_free(fname); 666 667 #ifdef ANDROID 668 havesock: 669 #endif /* ANDROID */ 670 671 /* 672 * Make socket non-blocking so that we don't hang forever if 673 * target dies unexpectedly. 674 */ 675 flags = fcntl(priv->sock, F_GETFL); 676 if (flags >= 0) { 677 flags |= O_NONBLOCK; 678 if (fcntl(priv->sock, F_SETFL, flags) < 0) { 679 wpa_printf(MSG_INFO, "fcntl(ctrl, O_NONBLOCK): %s", 680 strerror(errno)); 681 /* Not fatal, continue on.*/ 682 } 683 } 684 685 eloop_register_read_sock(priv->sock, wpa_supplicant_ctrl_iface_receive, 686 wpa_s, priv); 687 wpa_msg_register_cb(wpa_supplicant_ctrl_iface_msg_cb); 688 689 os_free(buf); 690 return 0; 691 692 fail: 693 if (priv->sock >= 0) { 694 close(priv->sock); 695 priv->sock = -1; 696 } 697 if (fname) { 698 unlink(fname); 699 os_free(fname); 700 } 701 os_free(buf); 702 return -1; 703 } 704 705 706 struct ctrl_iface_priv * 707 wpa_supplicant_ctrl_iface_init(struct wpa_supplicant *wpa_s) 708 { 709 struct ctrl_iface_priv *priv; 710 711 priv = os_zalloc(sizeof(*priv)); 712 if (priv == NULL) 713 return NULL; 714 dl_list_init(&priv->ctrl_dst); 715 dl_list_init(&priv->msg_queue); 716 priv->wpa_s = wpa_s; 717 priv->sock = -1; 718 719 if (wpa_s->conf->ctrl_interface == NULL) 720 return priv; 721 722 #ifdef ANDROID 723 if (wpa_s->global->params.ctrl_interface) { 724 int same = 0; 725 726 if (wpa_s->global->params.ctrl_interface[0] == '/') { 727 if (os_strcmp(wpa_s->global->params.ctrl_interface, 728 wpa_s->conf->ctrl_interface) == 0) 729 same = 1; 730 } else if (os_strncmp(wpa_s->global->params.ctrl_interface, 731 "@android:", 9) == 0 || 732 os_strncmp(wpa_s->global->params.ctrl_interface, 733 "@abstract:", 10) == 0) { 734 char *pos; 735 736 /* 737 * Currently, Android uses @android:wpa_* as the naming 738 * convention for the global ctrl interface. This logic 739 * needs to be revisited if the above naming convention 740 * is modified. 741 */ 742 pos = os_strchr(wpa_s->global->params.ctrl_interface, 743 '_'); 744 if (pos && 745 os_strcmp(pos + 1, 746 wpa_s->conf->ctrl_interface) == 0) 747 same = 1; 748 } 749 750 if (same) { 751 /* 752 * The invalid configuration combination might be 753 * possible to hit in an Android OTA upgrade case, so 754 * instead of refusing to start the wpa_supplicant 755 * process, do not open the per-interface ctrl_iface 756 * and continue with the global control interface that 757 * was set from the command line since the Wi-Fi 758 * framework will use it for operations. 759 */ 760 wpa_printf(MSG_ERROR, 761 "global ctrl interface %s matches ctrl interface %s - do not open per-interface ctrl interface", 762 wpa_s->global->params.ctrl_interface, 763 wpa_s->conf->ctrl_interface); 764 return priv; 765 } 766 } 767 #endif /* ANDROID */ 768 769 if (wpas_ctrl_iface_open_sock(wpa_s, priv) < 0) { 770 os_free(priv); 771 return NULL; 772 } 773 774 return priv; 775 } 776 777 778 static int wpas_ctrl_iface_reinit(struct wpa_supplicant *wpa_s, 779 struct ctrl_iface_priv *priv) 780 { 781 int res; 782 783 if (priv->sock <= 0) 784 return -1; 785 786 /* 787 * On Android, the control socket being used may be the socket 788 * that is created when wpa_supplicant is started as a /init.*.rc 789 * service. Such a socket is maintained as a key-value pair in 790 * Android's environment. Closing this control socket would leave us 791 * in a bad state with an invalid socket descriptor. 792 */ 793 if (priv->android_control_socket) 794 return priv->sock; 795 796 eloop_unregister_read_sock(priv->sock); 797 close(priv->sock); 798 priv->sock = -1; 799 res = wpas_ctrl_iface_open_sock(wpa_s, priv); 800 if (res < 0) 801 return -1; 802 return priv->sock; 803 } 804 805 806 static void 807 wpas_global_ctrl_iface_flush_queued_msg(struct wpa_global *global, 808 struct wpa_supplicant *wpa_s) 809 { 810 struct ctrl_iface_global_priv *gpriv; 811 struct ctrl_iface_msg *msg, *prev_msg; 812 unsigned int count = 0; 813 814 if (!global || !global->ctrl_iface) 815 return; 816 817 gpriv = global->ctrl_iface; 818 dl_list_for_each_safe(msg, prev_msg, &gpriv->msg_queue, 819 struct ctrl_iface_msg, list) { 820 if (msg->wpa_s == wpa_s) { 821 count++; 822 dl_list_del(&msg->list); 823 os_free(msg); 824 } 825 } 826 827 if (count) { 828 wpa_printf(MSG_DEBUG, 829 "CTRL: Dropped %u pending message(s) for interface that is being removed", 830 count); 831 } 832 } 833 834 835 void wpa_supplicant_ctrl_iface_deinit(struct wpa_supplicant *wpa_s, 836 struct ctrl_iface_priv *priv) 837 { 838 struct wpa_ctrl_dst *dst, *prev; 839 struct ctrl_iface_msg *msg, *prev_msg; 840 struct ctrl_iface_global_priv *gpriv; 841 842 if (!priv) { 843 /* Control interface has not yet been initialized, so there is 844 * nothing to deinitialize here. However, there might be a 845 * pending message for this interface, so get rid of any such 846 * entry before completing interface removal. */ 847 wpas_global_ctrl_iface_flush_queued_msg(wpa_s->global, wpa_s); 848 eloop_cancel_timeout(wpas_ctrl_msg_queue_timeout, wpa_s, NULL); 849 return; 850 } 851 852 if (priv->sock > -1) { 853 char *fname; 854 char *buf, *dir = NULL; 855 eloop_unregister_read_sock(priv->sock); 856 if (!dl_list_empty(&priv->ctrl_dst)) { 857 /* 858 * Wait before closing the control socket if 859 * there are any attached monitors in order to allow 860 * them to receive any pending messages. 861 */ 862 wpa_printf(MSG_DEBUG, "CTRL_IFACE wait for attached " 863 "monitors to receive messages"); 864 os_sleep(0, 100000); 865 } 866 close(priv->sock); 867 priv->sock = -1; 868 fname = wpa_supplicant_ctrl_iface_path(priv->wpa_s); 869 if (fname) { 870 unlink(fname); 871 os_free(fname); 872 } 873 874 if (priv->wpa_s->conf->ctrl_interface == NULL) 875 goto free_dst; 876 buf = os_strdup(priv->wpa_s->conf->ctrl_interface); 877 if (buf == NULL) 878 goto free_dst; 879 if (os_strncmp(buf, "DIR=", 4) == 0) { 880 char *gid_str; 881 dir = buf + 4; 882 gid_str = os_strstr(dir, " GROUP="); 883 if (gid_str) 884 *gid_str = '\0'; 885 } else 886 dir = buf; 887 888 if (rmdir(dir) < 0) { 889 if (errno == ENOTEMPTY) { 890 wpa_printf(MSG_DEBUG, "Control interface " 891 "directory not empty - leaving it " 892 "behind"); 893 } else { 894 wpa_printf(MSG_ERROR, 895 "rmdir[ctrl_interface=%s]: %s", 896 dir, strerror(errno)); 897 } 898 } 899 os_free(buf); 900 } 901 902 free_dst: 903 dl_list_for_each_safe(dst, prev, &priv->ctrl_dst, struct wpa_ctrl_dst, 904 list) { 905 dl_list_del(&dst->list); 906 os_free(dst); 907 } 908 dl_list_for_each_safe(msg, prev_msg, &priv->msg_queue, 909 struct ctrl_iface_msg, list) { 910 dl_list_del(&msg->list); 911 os_free(msg); 912 } 913 gpriv = priv->wpa_s->global->ctrl_iface; 914 if (gpriv) { 915 dl_list_for_each_safe(msg, prev_msg, &gpriv->msg_queue, 916 struct ctrl_iface_msg, list) { 917 if (msg->wpa_s == priv->wpa_s) { 918 dl_list_del(&msg->list); 919 os_free(msg); 920 } 921 } 922 } 923 wpas_global_ctrl_iface_flush_queued_msg(wpa_s->global, wpa_s); 924 eloop_cancel_timeout(wpas_ctrl_msg_queue_timeout, priv->wpa_s, NULL); 925 os_free(priv); 926 } 927 928 929 /** 930 * wpa_supplicant_ctrl_iface_send - Send a control interface packet to monitors 931 * @ifname: Interface name for global control socket or %NULL 932 * @sock: Local socket fd 933 * @ctrl_dst: List of attached listeners 934 * @level: Priority level of the message 935 * @buf: Message data 936 * @len: Message length 937 * 938 * Send a packet to all monitor programs attached to the control interface. 939 */ 940 static void wpa_supplicant_ctrl_iface_send(struct wpa_supplicant *wpa_s, 941 const char *ifname, int sock, 942 struct dl_list *ctrl_dst, 943 int level, const char *buf, 944 size_t len, 945 struct ctrl_iface_priv *priv, 946 struct ctrl_iface_global_priv *gp) 947 { 948 struct wpa_ctrl_dst *dst, *next; 949 char levelstr[10]; 950 int idx, res; 951 struct msghdr msg; 952 struct iovec io[5]; 953 954 if (sock < 0 || dl_list_empty(ctrl_dst)) 955 return; 956 957 res = os_snprintf(levelstr, sizeof(levelstr), "<%d>", level); 958 if (os_snprintf_error(sizeof(levelstr), res)) 959 return; 960 idx = 0; 961 if (ifname) { 962 io[idx].iov_base = "IFNAME="; 963 io[idx].iov_len = 7; 964 idx++; 965 io[idx].iov_base = (char *) ifname; 966 io[idx].iov_len = os_strlen(ifname); 967 idx++; 968 io[idx].iov_base = " "; 969 io[idx].iov_len = 1; 970 idx++; 971 } 972 io[idx].iov_base = levelstr; 973 io[idx].iov_len = os_strlen(levelstr); 974 idx++; 975 io[idx].iov_base = (char *) buf; 976 io[idx].iov_len = len; 977 idx++; 978 os_memset(&msg, 0, sizeof(msg)); 979 msg.msg_iov = io; 980 msg.msg_iovlen = idx; 981 982 dl_list_for_each_safe(dst, next, ctrl_dst, struct wpa_ctrl_dst, list) { 983 int _errno; 984 char txt[200]; 985 986 if (level < dst->debug_level) 987 continue; 988 989 msg.msg_name = (void *) &dst->addr; 990 msg.msg_namelen = dst->addrlen; 991 wpas_ctrl_sock_debug("ctrl_sock-sendmsg", sock, buf, len); 992 if (sendmsg(sock, &msg, MSG_DONTWAIT) >= 0) { 993 sockaddr_print(MSG_MSGDUMP, 994 "CTRL_IFACE monitor sent successfully to", 995 &dst->addr, dst->addrlen); 996 dst->errors = 0; 997 continue; 998 } 999 1000 _errno = errno; 1001 os_snprintf(txt, sizeof(txt), "CTRL_IFACE monitor: %d (%s) for", 1002 _errno, strerror(_errno)); 1003 sockaddr_print(MSG_DEBUG, txt, &dst->addr, dst->addrlen); 1004 dst->errors++; 1005 1006 if (dst->errors > 10 || _errno == ENOENT || _errno == EPERM) { 1007 sockaddr_print(MSG_INFO, "CTRL_IFACE: Detach monitor that cannot receive messages:", 1008 &dst->addr, dst->addrlen); 1009 wpa_supplicant_ctrl_iface_detach(ctrl_dst, &dst->addr, 1010 dst->addrlen); 1011 } 1012 1013 if (_errno == ENOBUFS || _errno == EAGAIN) { 1014 /* 1015 * The socket send buffer could be full. This may happen 1016 * if client programs are not receiving their pending 1017 * messages. Close and reopen the socket as a workaround 1018 * to avoid getting stuck being unable to send any new 1019 * responses. 1020 */ 1021 if (priv) 1022 sock = wpas_ctrl_iface_reinit(wpa_s, priv); 1023 else if (gp) 1024 sock = wpas_ctrl_iface_global_reinit( 1025 wpa_s->global, gp); 1026 else 1027 break; 1028 if (sock < 0) { 1029 wpa_dbg(wpa_s, MSG_DEBUG, 1030 "Failed to reinitialize ctrl_iface socket"); 1031 break; 1032 } 1033 } 1034 } 1035 } 1036 1037 1038 void wpa_supplicant_ctrl_iface_wait(struct ctrl_iface_priv *priv) 1039 { 1040 char buf[256]; 1041 int res; 1042 struct sockaddr_storage from; 1043 socklen_t fromlen = sizeof(from); 1044 1045 if (priv->sock == -1) 1046 return; 1047 1048 for (;;) { 1049 wpa_printf(MSG_DEBUG, "CTRL_IFACE - %s - wait for monitor to " 1050 "attach", priv->wpa_s->ifname); 1051 eloop_wait_for_read_sock(priv->sock); 1052 1053 res = recvfrom(priv->sock, buf, sizeof(buf) - 1, 0, 1054 (struct sockaddr *) &from, &fromlen); 1055 if (res < 0) { 1056 wpa_printf(MSG_ERROR, "recvfrom(ctrl_iface): %s", 1057 strerror(errno)); 1058 continue; 1059 } 1060 buf[res] = '\0'; 1061 1062 if (os_strcmp(buf, "ATTACH") == 0) { 1063 /* handle ATTACH signal of first monitor interface */ 1064 if (!wpa_supplicant_ctrl_iface_attach(&priv->ctrl_dst, 1065 &from, fromlen, 1066 0)) { 1067 if (sendto(priv->sock, "OK\n", 3, 0, 1068 (struct sockaddr *) &from, fromlen) < 1069 0) { 1070 wpa_printf(MSG_DEBUG, "ctrl_iface sendto failed: %s", 1071 strerror(errno)); 1072 } 1073 /* OK to continue */ 1074 return; 1075 } else { 1076 if (sendto(priv->sock, "FAIL\n", 5, 0, 1077 (struct sockaddr *) &from, fromlen) < 1078 0) { 1079 wpa_printf(MSG_DEBUG, "ctrl_iface sendto failed: %s", 1080 strerror(errno)); 1081 } 1082 } 1083 } else { 1084 /* return FAIL for all other signals */ 1085 if (sendto(priv->sock, "FAIL\n", 5, 0, 1086 (struct sockaddr *) &from, fromlen) < 0) { 1087 wpa_printf(MSG_DEBUG, 1088 "ctrl_iface sendto failed: %s", 1089 strerror(errno)); 1090 } 1091 } 1092 } 1093 } 1094 1095 1096 /* Global ctrl_iface */ 1097 1098 static void wpa_supplicant_global_ctrl_iface_receive(int sock, void *eloop_ctx, 1099 void *sock_ctx) 1100 { 1101 struct wpa_global *global = eloop_ctx; 1102 struct ctrl_iface_global_priv *priv = sock_ctx; 1103 char *buf; 1104 int res; 1105 struct sockaddr_storage from; 1106 socklen_t fromlen = sizeof(from); 1107 char *reply = NULL, *reply_buf = NULL; 1108 size_t reply_len; 1109 1110 buf = os_malloc(CTRL_IFACE_MAX_LEN + 1); 1111 if (!buf) 1112 return; 1113 res = recvfrom(sock, buf, CTRL_IFACE_MAX_LEN + 1, 0, 1114 (struct sockaddr *) &from, &fromlen); 1115 if (res < 0) { 1116 wpa_printf(MSG_ERROR, "recvfrom(ctrl_iface): %s", 1117 strerror(errno)); 1118 os_free(buf); 1119 return; 1120 } 1121 if ((size_t) res > CTRL_IFACE_MAX_LEN) { 1122 wpa_printf(MSG_ERROR, "recvform(ctrl_iface): input truncated"); 1123 os_free(buf); 1124 return; 1125 } 1126 buf[res] = '\0'; 1127 1128 if (os_strcmp(buf, "ATTACH") == 0) { 1129 if (wpa_supplicant_ctrl_iface_attach(&priv->ctrl_dst, &from, 1130 fromlen, 1)) 1131 reply_len = 1; 1132 else 1133 reply_len = 2; 1134 } else if (os_strcmp(buf, "DETACH") == 0) { 1135 if (wpa_supplicant_ctrl_iface_detach(&priv->ctrl_dst, &from, 1136 fromlen)) 1137 reply_len = 1; 1138 else 1139 reply_len = 2; 1140 } else { 1141 reply_buf = wpa_supplicant_global_ctrl_iface_process( 1142 global, buf, &reply_len); 1143 reply = reply_buf; 1144 1145 /* 1146 * There could be some password/key material in the command, so 1147 * clear the buffer explicitly now that it is not needed 1148 * anymore. 1149 */ 1150 os_memset(buf, 0, res); 1151 } 1152 1153 if (!reply && reply_len == 1) { 1154 reply = "FAIL\n"; 1155 reply_len = 5; 1156 } else if (!reply && reply_len == 2) { 1157 reply = "OK\n"; 1158 reply_len = 3; 1159 } 1160 1161 if (reply) { 1162 wpas_ctrl_sock_debug("global_ctrl_sock-sendto", 1163 sock, reply, reply_len); 1164 if (sendto(sock, reply, reply_len, 0, (struct sockaddr *) &from, 1165 fromlen) < 0) { 1166 wpa_printf(MSG_DEBUG, "ctrl_iface sendto failed: %s", 1167 strerror(errno)); 1168 } 1169 } 1170 os_free(reply_buf); 1171 os_free(buf); 1172 } 1173 1174 1175 static int wpas_global_ctrl_iface_open_sock(struct wpa_global *global, 1176 struct ctrl_iface_global_priv *priv) 1177 { 1178 struct sockaddr_un addr; 1179 const char *ctrl = global->params.ctrl_interface; 1180 int flags; 1181 1182 wpa_printf(MSG_DEBUG, "Global control interface '%s'", ctrl); 1183 1184 #ifdef ANDROID 1185 if (os_strncmp(ctrl, "@android:", 9) == 0) { 1186 priv->sock = android_get_control_socket(ctrl + 9); 1187 if (priv->sock < 0) { 1188 wpa_printf(MSG_ERROR, "Failed to open Android control " 1189 "socket '%s'", ctrl + 9); 1190 goto fail; 1191 } 1192 wpa_printf(MSG_DEBUG, "Using Android control socket '%s'", 1193 ctrl + 9); 1194 priv->android_control_socket = 1; 1195 goto havesock; 1196 } 1197 1198 if (os_strncmp(ctrl, "@abstract:", 10) != 0) { 1199 /* 1200 * Backwards compatibility - try to open an Android control 1201 * socket and if that fails, assume this was a UNIX domain 1202 * socket instead. 1203 */ 1204 priv->sock = android_get_control_socket(ctrl); 1205 if (priv->sock >= 0) { 1206 wpa_printf(MSG_DEBUG, 1207 "Using Android control socket '%s'", 1208 ctrl); 1209 priv->android_control_socket = 1; 1210 goto havesock; 1211 } 1212 } 1213 #endif /* ANDROID */ 1214 1215 priv->sock = socket(PF_UNIX, SOCK_DGRAM, 0); 1216 if (priv->sock < 0) { 1217 wpa_printf(MSG_ERROR, "socket(PF_UNIX): %s", strerror(errno)); 1218 goto fail; 1219 } 1220 1221 os_memset(&addr, 0, sizeof(addr)); 1222 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__) 1223 addr.sun_len = sizeof(addr); 1224 #endif /* __FreeBSD__ */ 1225 addr.sun_family = AF_UNIX; 1226 1227 if (os_strncmp(ctrl, "@abstract:", 10) == 0) { 1228 addr.sun_path[0] = '\0'; 1229 os_strlcpy(addr.sun_path + 1, ctrl + 10, 1230 sizeof(addr.sun_path) - 1); 1231 if (bind(priv->sock, (struct sockaddr *) &addr, sizeof(addr)) < 1232 0) { 1233 wpa_printf(MSG_ERROR, "supp-global-ctrl-iface-init: " 1234 "bind(PF_UNIX;%s) failed: %s", 1235 ctrl, strerror(errno)); 1236 goto fail; 1237 } 1238 wpa_printf(MSG_DEBUG, "Using Abstract control socket '%s'", 1239 ctrl + 10); 1240 goto havesock; 1241 } 1242 1243 os_strlcpy(addr.sun_path, ctrl, sizeof(addr.sun_path)); 1244 if (bind(priv->sock, (struct sockaddr *) &addr, sizeof(addr)) < 0) { 1245 wpa_printf(MSG_INFO, "supp-global-ctrl-iface-init(%s) (will try fixup): bind(PF_UNIX): %s", 1246 ctrl, strerror(errno)); 1247 if (connect(priv->sock, (struct sockaddr *) &addr, 1248 sizeof(addr)) < 0) { 1249 wpa_printf(MSG_DEBUG, "ctrl_iface exists, but does not" 1250 " allow connections - assuming it was left" 1251 "over from forced program termination"); 1252 if (unlink(ctrl) < 0) { 1253 wpa_printf(MSG_ERROR, 1254 "Could not unlink existing ctrl_iface socket '%s': %s", 1255 ctrl, strerror(errno)); 1256 goto fail; 1257 } 1258 if (bind(priv->sock, (struct sockaddr *) &addr, 1259 sizeof(addr)) < 0) { 1260 wpa_printf(MSG_ERROR, "supp-glb-iface-init: bind(PF_UNIX;%s): %s", 1261 ctrl, strerror(errno)); 1262 goto fail; 1263 } 1264 wpa_printf(MSG_DEBUG, "Successfully replaced leftover " 1265 "ctrl_iface socket '%s'", 1266 ctrl); 1267 } else { 1268 wpa_printf(MSG_INFO, "ctrl_iface exists and seems to " 1269 "be in use - cannot override it"); 1270 wpa_printf(MSG_INFO, "Delete '%s' manually if it is " 1271 "not used anymore", 1272 ctrl); 1273 goto fail; 1274 } 1275 } 1276 1277 wpa_printf(MSG_DEBUG, "Using UNIX control socket '%s'", ctrl); 1278 1279 if (global->params.ctrl_interface_group) { 1280 char *gid_str = global->params.ctrl_interface_group; 1281 gid_t gid = 0; 1282 struct group *grp; 1283 char *endp; 1284 1285 grp = getgrnam(gid_str); 1286 if (grp) { 1287 gid = grp->gr_gid; 1288 wpa_printf(MSG_DEBUG, "ctrl_interface_group=%d" 1289 " (from group name '%s')", 1290 (int) gid, gid_str); 1291 } else { 1292 /* Group name not found - try to parse this as gid */ 1293 gid = strtol(gid_str, &endp, 10); 1294 if (*gid_str == '\0' || *endp != '\0') { 1295 wpa_printf(MSG_ERROR, "CTRL: Invalid group " 1296 "'%s'", gid_str); 1297 goto fail; 1298 } 1299 wpa_printf(MSG_DEBUG, "ctrl_interface_group=%d", 1300 (int) gid); 1301 } 1302 if (lchown(ctrl, -1, gid) < 0) { 1303 wpa_printf(MSG_ERROR, 1304 "lchown[global_ctrl_interface=%s,gid=%d]: %s", 1305 ctrl, (int) gid, strerror(errno)); 1306 goto fail; 1307 } 1308 1309 if (chmod(ctrl, S_IRWXU | S_IRWXG) < 0) { 1310 wpa_printf(MSG_ERROR, 1311 "chmod[global_ctrl_interface=%s]: %s", 1312 ctrl, strerror(errno)); 1313 goto fail; 1314 } 1315 } else { 1316 if (chmod(ctrl, S_IRWXU) < 0) { 1317 wpa_printf(MSG_DEBUG, 1318 "chmod[global_ctrl_interface=%s](S_IRWXU): %s", 1319 ctrl, strerror(errno)); 1320 /* continue anyway since group change was not required 1321 */ 1322 } 1323 } 1324 1325 havesock: 1326 1327 /* 1328 * Make socket non-blocking so that we don't hang forever if 1329 * target dies unexpectedly. 1330 */ 1331 flags = fcntl(priv->sock, F_GETFL); 1332 if (flags >= 0) { 1333 flags |= O_NONBLOCK; 1334 if (fcntl(priv->sock, F_SETFL, flags) < 0) { 1335 wpa_printf(MSG_INFO, "fcntl(ctrl, O_NONBLOCK): %s", 1336 strerror(errno)); 1337 /* Not fatal, continue on.*/ 1338 } 1339 } 1340 1341 eloop_register_read_sock(priv->sock, 1342 wpa_supplicant_global_ctrl_iface_receive, 1343 global, priv); 1344 1345 return 0; 1346 1347 fail: 1348 if (priv->sock >= 0) { 1349 close(priv->sock); 1350 priv->sock = -1; 1351 } 1352 return -1; 1353 } 1354 1355 1356 struct ctrl_iface_global_priv * 1357 wpa_supplicant_global_ctrl_iface_init(struct wpa_global *global) 1358 { 1359 struct ctrl_iface_global_priv *priv; 1360 1361 priv = os_zalloc(sizeof(*priv)); 1362 if (priv == NULL) 1363 return NULL; 1364 dl_list_init(&priv->ctrl_dst); 1365 dl_list_init(&priv->msg_queue); 1366 priv->global = global; 1367 priv->sock = -1; 1368 1369 if (global->params.ctrl_interface == NULL) 1370 return priv; 1371 1372 if (wpas_global_ctrl_iface_open_sock(global, priv) < 0) { 1373 os_free(priv); 1374 return NULL; 1375 } 1376 1377 wpa_msg_register_cb(wpa_supplicant_ctrl_iface_msg_cb); 1378 1379 return priv; 1380 } 1381 1382 1383 static int wpas_ctrl_iface_global_reinit(struct wpa_global *global, 1384 struct ctrl_iface_global_priv *priv) 1385 { 1386 int res; 1387 1388 if (priv->sock <= 0) 1389 return -1; 1390 1391 /* 1392 * On Android, the control socket being used may be the socket 1393 * that is created when wpa_supplicant is started as a /init.*.rc 1394 * service. Such a socket is maintained as a key-value pair in 1395 * Android's environment. Closing this control socket would leave us 1396 * in a bad state with an invalid socket descriptor. 1397 */ 1398 if (priv->android_control_socket) 1399 return priv->sock; 1400 1401 eloop_unregister_read_sock(priv->sock); 1402 close(priv->sock); 1403 priv->sock = -1; 1404 res = wpas_global_ctrl_iface_open_sock(global, priv); 1405 if (res < 0) 1406 return -1; 1407 return priv->sock; 1408 } 1409 1410 1411 void 1412 wpa_supplicant_global_ctrl_iface_deinit(struct ctrl_iface_global_priv *priv) 1413 { 1414 struct wpa_ctrl_dst *dst, *prev; 1415 struct ctrl_iface_msg *msg, *prev_msg; 1416 1417 if (priv->sock >= 0) { 1418 eloop_unregister_read_sock(priv->sock); 1419 close(priv->sock); 1420 } 1421 if (priv->global->params.ctrl_interface) 1422 unlink(priv->global->params.ctrl_interface); 1423 dl_list_for_each_safe(dst, prev, &priv->ctrl_dst, struct wpa_ctrl_dst, 1424 list) { 1425 dl_list_del(&dst->list); 1426 os_free(dst); 1427 } 1428 dl_list_for_each_safe(msg, prev_msg, &priv->msg_queue, 1429 struct ctrl_iface_msg, list) { 1430 dl_list_del(&msg->list); 1431 os_free(msg); 1432 } 1433 os_free(priv); 1434 } 1435