wireless.c 25 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005
  1. /*
  2. * netifd - network interface daemon
  3. * Copyright (C) 2013 Felix Fietkau <nbd@openwrt.org>
  4. *
  5. * This program is free software; you can redistribute it and/or modify
  6. * it under the terms of the GNU General Public License version 2
  7. * as published by the Free Software Foundation
  8. *
  9. * This program is distributed in the hope that it will be useful,
  10. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. * GNU General Public License for more details.
  13. */
  14. #include <signal.h>
  15. #include "netifd.h"
  16. #include "wireless.h"
  17. #include "handler.h"
  18. #include "ubus.h"
  19. #define WIRELESS_SETUP_RETRY 3
  20. struct vlist_tree wireless_devices;
  21. struct avl_tree wireless_drivers;
  22. static struct blob_buf b;
  23. static int drv_fd;
  24. static const struct blobmsg_policy wdev_policy =
  25. { .name = "disabled", .type = BLOBMSG_TYPE_BOOL };
  26. static const struct uci_blob_param_list wdev_param = {
  27. .n_params = 1,
  28. .params = &wdev_policy,
  29. };
  30. enum {
  31. VIF_ATTR_DISABLED,
  32. VIF_ATTR_NETWORK,
  33. VIF_ATTR_ISOLATE,
  34. VIF_ATTR_MODE,
  35. __VIF_ATTR_MAX,
  36. };
  37. static const struct blobmsg_policy vif_policy[__VIF_ATTR_MAX] = {
  38. [VIF_ATTR_DISABLED] = { .name = "disabled", .type = BLOBMSG_TYPE_BOOL },
  39. [VIF_ATTR_NETWORK] = { .name = "network", .type = BLOBMSG_TYPE_ARRAY },
  40. [VIF_ATTR_ISOLATE] = { .name = "isolate", .type = BLOBMSG_TYPE_BOOL },
  41. [VIF_ATTR_MODE] = { .name = "mode", .type = BLOBMSG_TYPE_STRING },
  42. };
  43. static const struct uci_blob_param_list vif_param = {
  44. .n_params = ARRAY_SIZE(vif_policy),
  45. .params = vif_policy,
  46. };
  47. static void
  48. put_container(struct blob_buf *buf, struct blob_attr *attr, const char *name)
  49. {
  50. void *c = blobmsg_open_table(buf, name);
  51. blob_put_raw(buf, blob_data(attr), blob_len(attr));
  52. blobmsg_close_table(buf, c);
  53. }
  54. static void
  55. vif_config_add_bridge(struct blob_buf *buf, struct blob_attr *networks, bool prepare)
  56. {
  57. struct interface *iface;
  58. struct device *dev = NULL;
  59. struct blob_attr *cur;
  60. const char *network;
  61. int rem;
  62. if (!networks)
  63. return;
  64. blobmsg_for_each_attr(cur, networks, rem) {
  65. network = blobmsg_data(cur);
  66. iface = vlist_find(&interfaces, network, iface, node);
  67. if (!iface)
  68. continue;
  69. dev = iface->main_dev.dev;
  70. if (!dev)
  71. return;
  72. if (!dev->type->bridge_capability)
  73. return;
  74. }
  75. if (!dev)
  76. return;
  77. if (dev->hotplug_ops && dev->hotplug_ops->prepare)
  78. dev->hotplug_ops->prepare(dev);
  79. blobmsg_add_string(buf, "bridge", dev->ifname);
  80. if (dev->settings.flags & DEV_OPT_MULTICAST_TO_UNICAST)
  81. blobmsg_add_u8(buf, "multicast_to_unicast",
  82. dev->settings.multicast_to_unicast);
  83. }
  84. static void
  85. prepare_config(struct wireless_device *wdev, struct blob_buf *buf, bool up)
  86. {
  87. struct wireless_interface *vif;
  88. void *l, *i;
  89. blob_buf_init(&b, 0);
  90. put_container(&b, wdev->config, "config");
  91. if (wdev->data)
  92. blobmsg_add_blob(&b, wdev->data);
  93. l = blobmsg_open_table(&b, "interfaces");
  94. vlist_for_each_element(&wdev->interfaces, vif, node) {
  95. i = blobmsg_open_table(&b, vif->name);
  96. vif_config_add_bridge(&b, vif->network, up);
  97. put_container(&b, vif->config, "config");
  98. if (vif->data)
  99. blobmsg_add_blob(&b, vif->data);
  100. blobmsg_close_table(&b, i);
  101. }
  102. blobmsg_close_table(&b, l);
  103. }
  104. static bool
  105. wireless_process_check(struct wireless_process *proc)
  106. {
  107. return check_pid_path(proc->pid, proc->exe);
  108. }
  109. static void
  110. wireless_complete_kill_request(struct wireless_device *wdev)
  111. {
  112. if (!wdev->kill_request)
  113. return;
  114. ubus_complete_deferred_request(ubus_ctx, wdev->kill_request, 0);
  115. free(wdev->kill_request);
  116. wdev->kill_request = NULL;
  117. }
  118. static void
  119. wireless_process_free(struct wireless_device *wdev, struct wireless_process *proc)
  120. {
  121. D(WIRELESS, "Wireless device '%s' free pid %d\n", wdev->name, proc->pid);
  122. list_del(&proc->list);
  123. free(proc);
  124. if (list_empty(&wdev->script_proc))
  125. wireless_complete_kill_request(wdev);
  126. }
  127. static void
  128. wireless_close_script_proc_fd(struct wireless_device *wdev)
  129. {
  130. if (wdev->script_proc_fd.fd < 0)
  131. return;
  132. uloop_fd_delete(&wdev->script_proc_fd);
  133. close(wdev->script_proc_fd.fd);
  134. wdev->script_proc_fd.fd = -1;
  135. }
  136. static void
  137. wireless_process_kill_all(struct wireless_device *wdev, int signal, bool free)
  138. {
  139. struct wireless_process *proc, *tmp;
  140. list_for_each_entry_safe(proc, tmp, &wdev->script_proc, list) {
  141. bool check = wireless_process_check(proc);
  142. if (check) {
  143. D(WIRELESS, "Wireless device '%s' kill pid %d\n", wdev->name, proc->pid);
  144. kill(proc->pid, signal);
  145. }
  146. if (free || !check)
  147. wireless_process_free(wdev, proc);
  148. }
  149. if (free)
  150. wireless_close_script_proc_fd(wdev);
  151. }
  152. static void
  153. wireless_device_free_state(struct wireless_device *wdev)
  154. {
  155. struct wireless_interface *vif;
  156. uloop_timeout_cancel(&wdev->script_check);
  157. uloop_timeout_cancel(&wdev->timeout);
  158. wireless_complete_kill_request(wdev);
  159. free(wdev->data);
  160. wdev->data = NULL;
  161. vlist_for_each_element(&wdev->interfaces, vif, node) {
  162. free(vif->data);
  163. vif->data = NULL;
  164. vif->ifname = NULL;
  165. }
  166. }
  167. static void wireless_interface_handle_link(struct wireless_interface *vif, bool up)
  168. {
  169. struct interface *iface;
  170. struct blob_attr *cur;
  171. const char *network;
  172. int rem;
  173. if (!vif->network || !vif->ifname)
  174. return;
  175. if (up) {
  176. struct device *dev = device_get(vif->ifname, 2);
  177. if (dev) {
  178. dev->wireless_isolate = vif->isolate;
  179. dev->wireless = true;
  180. dev->wireless_ap = vif->ap_mode;
  181. }
  182. }
  183. blobmsg_for_each_attr(cur, vif->network, rem) {
  184. network = blobmsg_data(cur);
  185. iface = vlist_find(&interfaces, network, iface, node);
  186. if (!iface)
  187. continue;
  188. interface_handle_link(iface, vif->ifname, up, true);
  189. }
  190. }
  191. static void
  192. wireless_device_setup_cancel(struct wireless_device *wdev)
  193. {
  194. if (wdev->cancel)
  195. return;
  196. D(WIRELESS, "Cancel wireless device '%s' setup\n", wdev->name);
  197. wdev->cancel = true;
  198. uloop_timeout_set(&wdev->timeout, 10 * 1000);
  199. }
  200. static void
  201. wireless_device_run_handler(struct wireless_device *wdev, bool up)
  202. {
  203. const char *action = up ? "setup" : "teardown";
  204. const char *argv[6];
  205. char *config;
  206. int i = 0;
  207. int fds[2] = { -1, -1 };
  208. D(WIRELESS, "Wireless device '%s' run %s handler\n", wdev->name, action);
  209. if (!up && wdev->prev_config) {
  210. config = blobmsg_format_json(wdev->prev_config, true);
  211. free(wdev->prev_config);
  212. wdev->prev_config = NULL;
  213. } else {
  214. prepare_config(wdev, &b, up);
  215. config = blobmsg_format_json(b.head, true);
  216. }
  217. argv[i++] = wdev->drv->script;
  218. argv[i++] = wdev->drv->name;
  219. argv[i++] = action;
  220. argv[i++] = wdev->name;
  221. argv[i++] = config;
  222. argv[i] = NULL;
  223. if (up && pipe(fds) == 0) {
  224. wdev->script_proc_fd.fd = fds[0];
  225. uloop_fd_add(&wdev->script_proc_fd,
  226. ULOOP_READ | ULOOP_EDGE_TRIGGER);
  227. }
  228. netifd_start_process(argv, NULL, &wdev->script_task);
  229. if (fds[1] >= 0)
  230. close(fds[1]);
  231. free(config);
  232. }
  233. static void
  234. __wireless_device_set_up(struct wireless_device *wdev)
  235. {
  236. if (wdev->disabled)
  237. return;
  238. if (wdev->retry_setup_failed)
  239. return;
  240. if (!wdev->autostart)
  241. return;
  242. if (wdev->state != IFS_DOWN || config_init)
  243. return;
  244. free(wdev->prev_config);
  245. wdev->prev_config = NULL;
  246. wdev->state = IFS_SETUP;
  247. wireless_device_run_handler(wdev, true);
  248. }
  249. static void
  250. wireless_device_free(struct wireless_device *wdev)
  251. {
  252. vlist_flush_all(&wdev->interfaces);
  253. avl_delete(&wireless_devices.avl, &wdev->node.avl);
  254. free(wdev->config);
  255. free(wdev->prev_config);
  256. free(wdev);
  257. }
  258. static void
  259. wdev_handle_config_change(struct wireless_device *wdev)
  260. {
  261. enum interface_config_state state = wdev->config_state;
  262. switch(state) {
  263. case IFC_NORMAL:
  264. case IFC_RELOAD:
  265. __wireless_device_set_up(wdev);
  266. wdev->config_state = IFC_NORMAL;
  267. break;
  268. case IFC_REMOVE:
  269. wireless_device_free(wdev);
  270. break;
  271. }
  272. }
  273. static void
  274. wireless_device_mark_down(struct wireless_device *wdev)
  275. {
  276. struct wireless_interface *vif;
  277. D(WIRELESS, "Wireless device '%s' is now down\n", wdev->name);
  278. vlist_for_each_element(&wdev->interfaces, vif, node)
  279. wireless_interface_handle_link(vif, false);
  280. wireless_process_kill_all(wdev, SIGTERM, true);
  281. wdev->cancel = false;
  282. wdev->state = IFS_DOWN;
  283. wireless_device_free_state(wdev);
  284. wdev_handle_config_change(wdev);
  285. }
  286. static void
  287. wireless_device_setup_timeout(struct uloop_timeout *timeout)
  288. {
  289. struct wireless_device *wdev = container_of(timeout, struct wireless_device, timeout);
  290. netifd_kill_process(&wdev->script_task);
  291. wdev->script_task.cb(&wdev->script_task, -1);
  292. wireless_device_mark_down(wdev);
  293. }
  294. void
  295. wireless_device_set_up(struct wireless_device *wdev)
  296. {
  297. wdev->retry = WIRELESS_SETUP_RETRY;
  298. wdev->autostart = true;
  299. __wireless_device_set_up(wdev);
  300. }
  301. static void
  302. __wireless_device_set_down(struct wireless_device *wdev)
  303. {
  304. if (wdev->state == IFS_TEARDOWN || wdev->state == IFS_DOWN)
  305. return;
  306. if (wdev->script_task.uloop.pending) {
  307. wireless_device_setup_cancel(wdev);
  308. return;
  309. }
  310. wdev->state = IFS_TEARDOWN;
  311. wireless_device_run_handler(wdev, false);
  312. }
  313. static void
  314. wireless_device_mark_up(struct wireless_device *wdev)
  315. {
  316. struct wireless_interface *vif;
  317. if (wdev->cancel) {
  318. wdev->cancel = false;
  319. __wireless_device_set_down(wdev);
  320. return;
  321. }
  322. D(WIRELESS, "Wireless device '%s' is now up\n", wdev->name);
  323. wdev->state = IFS_UP;
  324. vlist_for_each_element(&wdev->interfaces, vif, node)
  325. wireless_interface_handle_link(vif, true);
  326. }
  327. static void
  328. wireless_device_retry_setup(struct wireless_device *wdev)
  329. {
  330. if (wdev->state == IFS_TEARDOWN || wdev->state == IFS_DOWN || wdev->cancel)
  331. return;
  332. if (--wdev->retry < 0)
  333. wdev->retry_setup_failed = true;
  334. __wireless_device_set_down(wdev);
  335. }
  336. static void
  337. wireless_device_script_task_cb(struct netifd_process *proc, int ret)
  338. {
  339. struct wireless_device *wdev = container_of(proc, struct wireless_device, script_task);
  340. switch (wdev->state) {
  341. case IFS_SETUP:
  342. wireless_device_retry_setup(wdev);
  343. break;
  344. case IFS_TEARDOWN:
  345. wireless_device_mark_down(wdev);
  346. break;
  347. default:
  348. break;
  349. }
  350. }
  351. void
  352. wireless_device_set_down(struct wireless_device *wdev)
  353. {
  354. wdev->retry_setup_failed = false;
  355. wdev->autostart = false;
  356. __wireless_device_set_down(wdev);
  357. }
  358. static void
  359. wdev_set_config_state(struct wireless_device *wdev, enum interface_config_state s)
  360. {
  361. if (wdev->config_state != IFC_NORMAL)
  362. return;
  363. wdev->config_state = s;
  364. if (wdev->state == IFS_DOWN)
  365. wdev_handle_config_change(wdev);
  366. else
  367. __wireless_device_set_down(wdev);
  368. }
  369. static void
  370. wdev_prepare_prev_config(struct wireless_device *wdev)
  371. {
  372. if (wdev->prev_config)
  373. return;
  374. prepare_config(wdev, &b, false);
  375. wdev->prev_config = blob_memdup(b.head);
  376. }
  377. static void
  378. wdev_change_config(struct wireless_device *wdev, struct wireless_device *wd_new)
  379. {
  380. struct blob_attr *new_config = wd_new->config;
  381. bool disabled = wd_new->disabled;
  382. free(wd_new);
  383. wdev_prepare_prev_config(wdev);
  384. if (blob_attr_equal(wdev->config, new_config) && wdev->disabled == disabled)
  385. return;
  386. D(WIRELESS, "Update configuration of wireless device '%s'\n", wdev->name);
  387. free(wdev->config);
  388. wdev->config = blob_memdup(new_config);
  389. wdev->disabled = disabled;
  390. wdev->retry_setup_failed = false;
  391. wdev_set_config_state(wdev, IFC_RELOAD);
  392. }
  393. static void
  394. wdev_create(struct wireless_device *wdev)
  395. {
  396. wdev->retry = WIRELESS_SETUP_RETRY;
  397. wdev->config = blob_memdup(wdev->config);
  398. }
  399. static void
  400. wdev_update(struct vlist_tree *tree, struct vlist_node *node_new,
  401. struct vlist_node *node_old)
  402. {
  403. struct wireless_device *wd_old = container_of(node_old, struct wireless_device, node);
  404. struct wireless_device *wd_new = container_of(node_new, struct wireless_device, node);
  405. if (wd_old && wd_new) {
  406. wdev_change_config(wd_old, wd_new);
  407. } else if (wd_old) {
  408. D(WIRELESS, "Delete wireless device '%s'\n", wd_old->name);
  409. wdev_set_config_state(wd_old, IFC_REMOVE);
  410. } else if (wd_new) {
  411. D(WIRELESS, "Create wireless device '%s'\n", wd_new->name);
  412. wdev_create(wd_new);
  413. }
  414. }
  415. static void
  416. wireless_add_handler(const char *script, const char *name, json_object *obj)
  417. {
  418. struct wireless_driver *drv;
  419. char *name_str, *script_str;
  420. json_object *dev_config_obj, *iface_config_obj;
  421. struct uci_blob_param_list *dev_config, *iface_config;
  422. dev_config_obj = json_get_field(obj, "device", json_type_array);
  423. iface_config_obj = json_get_field(obj, "iface", json_type_array);
  424. if (!dev_config_obj || !iface_config_obj)
  425. return;
  426. drv = calloc_a(sizeof(*drv),
  427. &dev_config, sizeof(*dev_config) + sizeof(void *),
  428. &iface_config, sizeof(*iface_config) + sizeof(void *),
  429. &name_str, strlen(name) + 1,
  430. &script_str, strlen(script) + 1);
  431. drv->name = strcpy(name_str, name);
  432. drv->script = strcpy(script_str, script);
  433. dev_config->n_next = 1;
  434. dev_config->next[0] = &wdev_param;
  435. drv->device.config = dev_config;
  436. iface_config->n_next = 1;
  437. iface_config->next[0] = &vif_param;
  438. drv->interface.config = iface_config;
  439. drv->device.buf = netifd_handler_parse_config(drv->device.config, dev_config_obj);
  440. drv->interface.buf = netifd_handler_parse_config(drv->interface.config, iface_config_obj);
  441. drv->node.key = drv->name;
  442. avl_insert(&wireless_drivers, &drv->node);
  443. D(WIRELESS, "Add handler for script %s: %s\n", script, name);
  444. }
  445. void wireless_init(void)
  446. {
  447. vlist_init(&wireless_devices, avl_strcmp, wdev_update);
  448. wireless_devices.keep_old = true;
  449. wireless_devices.no_delete = true;
  450. avl_init(&wireless_drivers, avl_strcmp, false, NULL);
  451. drv_fd = netifd_open_subdir("wireless");
  452. if (drv_fd < 0)
  453. return;
  454. netifd_init_script_handlers(drv_fd, wireless_add_handler);
  455. }
  456. static void
  457. wireless_interface_init_config(struct wireless_interface *vif)
  458. {
  459. struct blob_attr *tb[__VIF_ATTR_MAX];
  460. struct blob_attr *cur;
  461. vif->network = NULL;
  462. blobmsg_parse(vif_policy, __VIF_ATTR_MAX, tb, blob_data(vif->config), blob_len(vif->config));
  463. if ((cur = tb[VIF_ATTR_NETWORK]))
  464. vif->network = cur;
  465. cur = tb[VIF_ATTR_ISOLATE];
  466. if (cur)
  467. vif->isolate = blobmsg_get_bool(cur);
  468. cur = tb[VIF_ATTR_MODE];
  469. if (cur)
  470. vif->ap_mode = !strcmp(blobmsg_get_string(cur), "ap");
  471. }
  472. static void
  473. vif_update(struct vlist_tree *tree, struct vlist_node *node_new,
  474. struct vlist_node *node_old)
  475. {
  476. struct wireless_interface *vif_old = container_of(node_old, struct wireless_interface, node);
  477. struct wireless_interface *vif_new = container_of(node_new, struct wireless_interface, node);
  478. struct wireless_device *wdev;
  479. if (vif_old)
  480. wdev = vif_old->wdev;
  481. else
  482. wdev = vif_new->wdev;
  483. if (vif_old && vif_new) {
  484. free((void *) vif_old->section);
  485. vif_old->section = strdup(vif_new->section);
  486. if (blob_attr_equal(vif_old->config, vif_new->config)) {
  487. free(vif_new);
  488. return;
  489. }
  490. D(WIRELESS, "Update wireless interface %s on device %s\n", vif_new->name, wdev->name);
  491. wireless_interface_handle_link(vif_old, false);
  492. free(vif_old->config);
  493. vif_old->config = blob_memdup(vif_new->config);
  494. vif_old->isolate = vif_new->isolate;
  495. vif_old->ap_mode = vif_new->ap_mode;
  496. wireless_interface_init_config(vif_old);
  497. free(vif_new);
  498. } else if (vif_new) {
  499. D(WIRELESS, "Create new wireless interface %s on device %s\n", vif_new->name, wdev->name);
  500. vif_new->section = strdup(vif_new->section);
  501. vif_new->config = blob_memdup(vif_new->config);
  502. wireless_interface_init_config(vif_new);
  503. } else if (vif_old) {
  504. D(WIRELESS, "Delete wireless interface %s on device %s\n", vif_old->name, wdev->name);
  505. wireless_interface_handle_link(vif_old, false);
  506. free((void *) vif_old->section);
  507. free(vif_old->config);
  508. free(vif_old);
  509. }
  510. wdev_set_config_state(wdev, IFC_RELOAD);
  511. }
  512. static void
  513. wireless_proc_poll_fd(struct uloop_fd *fd, unsigned int events)
  514. {
  515. struct wireless_device *wdev = container_of(fd, struct wireless_device, script_proc_fd);
  516. char buf[128];
  517. while (1) {
  518. int b = read(fd->fd, buf, sizeof(buf));
  519. if (b < 0) {
  520. if (errno == EINTR)
  521. continue;
  522. if (errno == EAGAIN)
  523. return;
  524. goto done;
  525. }
  526. if (!b)
  527. goto done;
  528. }
  529. done:
  530. uloop_timeout_set(&wdev->script_check, 0);
  531. wireless_close_script_proc_fd(wdev);
  532. }
  533. static void
  534. wireless_device_check_script_tasks(struct uloop_timeout *timeout)
  535. {
  536. struct wireless_device *wdev = container_of(timeout, struct wireless_device, script_check);
  537. struct wireless_process *proc, *tmp;
  538. bool restart = false;
  539. list_for_each_entry_safe(proc, tmp, &wdev->script_proc, list) {
  540. if (wireless_process_check(proc))
  541. continue;
  542. D(WIRELESS, "Wireless device '%s' pid %d has terminated\n", wdev->name, proc->pid);
  543. if (proc->required)
  544. restart = true;
  545. wireless_process_free(wdev, proc);
  546. }
  547. if (restart)
  548. wireless_device_retry_setup(wdev);
  549. else
  550. uloop_timeout_set(&wdev->script_check, 1000);
  551. }
  552. void
  553. wireless_device_create(struct wireless_driver *drv, const char *name, struct blob_attr *data)
  554. {
  555. struct wireless_device *wdev;
  556. char *name_buf;
  557. struct blob_attr *disabled;
  558. blobmsg_parse(&wdev_policy, 1, &disabled, blob_data(data), blob_len(data));
  559. wdev = calloc_a(sizeof(*wdev), &name_buf, strlen(name) + 1);
  560. if (disabled && blobmsg_get_bool(disabled))
  561. wdev->disabled = true;
  562. wdev->drv = drv;
  563. wdev->state = IFS_DOWN;
  564. wdev->config_state = IFC_NORMAL;
  565. wdev->name = strcpy(name_buf, name);
  566. wdev->config = data;
  567. wdev->retry_setup_failed = false;
  568. wdev->autostart = true;
  569. INIT_LIST_HEAD(&wdev->script_proc);
  570. vlist_init(&wdev->interfaces, avl_strcmp, vif_update);
  571. wdev->interfaces.keep_old = true;
  572. wdev->timeout.cb = wireless_device_setup_timeout;
  573. wdev->script_task.cb = wireless_device_script_task_cb;
  574. wdev->script_task.dir_fd = drv_fd;
  575. wdev->script_task.log_prefix = wdev->name;
  576. wdev->script_proc_fd.fd = -1;
  577. wdev->script_proc_fd.cb = wireless_proc_poll_fd;
  578. wdev->script_check.cb = wireless_device_check_script_tasks;
  579. vlist_add(&wireless_devices, &wdev->node, wdev->name);
  580. }
  581. void wireless_interface_create(struct wireless_device *wdev, struct blob_attr *data, const char *section)
  582. {
  583. struct wireless_interface *vif;
  584. struct blob_attr *tb[__VIF_ATTR_MAX];
  585. struct blob_attr *cur;
  586. char *name_buf;
  587. char name[8];
  588. blobmsg_parse(vif_policy, __VIF_ATTR_MAX, tb, blob_data(data), blob_len(data));
  589. cur = tb[VIF_ATTR_DISABLED];
  590. if (cur && blobmsg_get_bool(cur))
  591. return;
  592. sprintf(name, "%d", wdev->vif_idx++);
  593. vif = calloc_a(sizeof(*vif),
  594. &name_buf, strlen(name) + 1);
  595. vif->name = strcpy(name_buf, name);
  596. vif->wdev = wdev;
  597. vif->config = data;
  598. vif->section = section;
  599. vif->isolate = false;
  600. vlist_add(&wdev->interfaces, &vif->node, vif->name);
  601. }
  602. static void
  603. wireless_interface_status(struct wireless_interface *iface, struct blob_buf *b)
  604. {
  605. void *i;
  606. i = blobmsg_open_table(b, NULL);
  607. if (iface->section)
  608. blobmsg_add_string(b, "section", iface->section);
  609. if (iface->ifname)
  610. blobmsg_add_string(b, "ifname", iface->ifname);
  611. put_container(b, iface->config, "config");
  612. blobmsg_close_table(b, i);
  613. }
  614. void
  615. wireless_device_status(struct wireless_device *wdev, struct blob_buf *b)
  616. {
  617. struct wireless_interface *iface;
  618. void *c, *i;
  619. c = blobmsg_open_table(b, wdev->name);
  620. blobmsg_add_u8(b, "up", wdev->state == IFS_UP);
  621. blobmsg_add_u8(b, "pending", wdev->state == IFS_SETUP || wdev->state == IFS_TEARDOWN);
  622. blobmsg_add_u8(b, "autostart", wdev->autostart);
  623. blobmsg_add_u8(b, "disabled", wdev->disabled);
  624. blobmsg_add_u8(b, "retry_setup_failed", wdev->retry_setup_failed);
  625. put_container(b, wdev->config, "config");
  626. i = blobmsg_open_array(b, "interfaces");
  627. vlist_for_each_element(&wdev->interfaces, iface, node)
  628. wireless_interface_status(iface, b);
  629. blobmsg_close_array(b, i);
  630. blobmsg_close_table(b, c);
  631. }
  632. void
  633. wireless_device_get_validate(struct wireless_device *wdev, struct blob_buf *b)
  634. {
  635. struct uci_blob_param_list *p;
  636. void *c, *d;
  637. int i;
  638. c = blobmsg_open_table(b, wdev->name);
  639. d = blobmsg_open_table(b, "device");
  640. p = wdev->drv->device.config;
  641. for (i = 0; i < p->n_params; i++)
  642. blobmsg_add_string(b, p->params[i].name, uci_get_validate_string(p, i));
  643. blobmsg_close_table(b, d);
  644. d = blobmsg_open_table(b, "interface");
  645. p = wdev->drv->interface.config;
  646. for (i = 0; i < p->n_params; i++)
  647. blobmsg_add_string(b, p->params[i].name, uci_get_validate_string(p, i));
  648. blobmsg_close_table(b, d);
  649. blobmsg_close_table(b, c);
  650. }
  651. static void
  652. wireless_interface_set_data(struct wireless_interface *vif)
  653. {
  654. enum {
  655. VIF_DATA_IFNAME,
  656. __VIF_DATA_MAX,
  657. };
  658. static const struct blobmsg_policy data_policy[__VIF_DATA_MAX] = {
  659. [VIF_DATA_IFNAME] = { .name = "ifname", .type = BLOBMSG_TYPE_STRING },
  660. };
  661. struct blob_attr *tb[__VIF_DATA_MAX];
  662. struct blob_attr *cur;
  663. blobmsg_parse(data_policy, __VIF_DATA_MAX, tb,
  664. blobmsg_data(vif->data), blobmsg_data_len(vif->data));
  665. if ((cur = tb[VIF_DATA_IFNAME]))
  666. vif->ifname = blobmsg_data(cur);
  667. }
  668. static int
  669. wireless_device_add_process(struct wireless_device *wdev, struct blob_attr *data)
  670. {
  671. enum {
  672. PROC_ATTR_PID,
  673. PROC_ATTR_EXE,
  674. PROC_ATTR_REQUIRED,
  675. __PROC_ATTR_MAX
  676. };
  677. static const struct blobmsg_policy proc_policy[__PROC_ATTR_MAX] = {
  678. [PROC_ATTR_PID] = { .name = "pid", .type = BLOBMSG_TYPE_INT32 },
  679. [PROC_ATTR_EXE] = { .name = "exe", .type = BLOBMSG_TYPE_STRING },
  680. [PROC_ATTR_REQUIRED] = { .name = "required", .type = BLOBMSG_TYPE_BOOL },
  681. };
  682. struct blob_attr *tb[__PROC_ATTR_MAX];
  683. struct wireless_process *proc;
  684. char *name;
  685. int pid;
  686. if (!data)
  687. return UBUS_STATUS_INVALID_ARGUMENT;
  688. blobmsg_parse(proc_policy, __PROC_ATTR_MAX, tb, blobmsg_data(data), blobmsg_data_len(data));
  689. if (!tb[PROC_ATTR_PID] || !tb[PROC_ATTR_EXE])
  690. return UBUS_STATUS_INVALID_ARGUMENT;
  691. pid = blobmsg_get_u32(tb[PROC_ATTR_PID]);
  692. if (pid < 2)
  693. return UBUS_STATUS_INVALID_ARGUMENT;
  694. proc = calloc_a(sizeof(*proc),
  695. &name, strlen(blobmsg_data(tb[PROC_ATTR_EXE])) + 1);
  696. proc->pid = pid;
  697. proc->exe = strcpy(name, blobmsg_data(tb[PROC_ATTR_EXE]));
  698. if (tb[PROC_ATTR_REQUIRED])
  699. proc->required = blobmsg_get_bool(tb[PROC_ATTR_REQUIRED]);
  700. D(WIRELESS, "Wireless device '%s' add pid %d\n", wdev->name, proc->pid);
  701. list_add(&proc->list, &wdev->script_proc);
  702. uloop_timeout_set(&wdev->script_check, 0);
  703. return 0;
  704. }
  705. static int
  706. wireless_device_process_kill_all(struct wireless_device *wdev, struct blob_attr *data,
  707. struct ubus_request_data *req)
  708. {
  709. enum {
  710. KILL_ATTR_SIGNAL,
  711. KILL_ATTR_IMMEDIATE,
  712. __KILL_ATTR_MAX
  713. };
  714. static const struct blobmsg_policy kill_policy[__KILL_ATTR_MAX] = {
  715. [KILL_ATTR_SIGNAL] = { .name = "signal", .type = BLOBMSG_TYPE_INT32 },
  716. [KILL_ATTR_IMMEDIATE] = { .name = "immediate", .type = BLOBMSG_TYPE_BOOL },
  717. };
  718. struct blob_attr *tb[__KILL_ATTR_MAX];
  719. struct blob_attr *cur;
  720. bool immediate = false;
  721. int signal = SIGTERM;
  722. blobmsg_parse(kill_policy, __KILL_ATTR_MAX, tb, blobmsg_data(data), blobmsg_data_len(data));
  723. if ((cur = tb[KILL_ATTR_SIGNAL]))
  724. signal = blobmsg_get_u32(cur);
  725. if ((cur = tb[KILL_ATTR_IMMEDIATE]))
  726. immediate = blobmsg_get_bool(cur);
  727. if (wdev->state != IFS_TEARDOWN || wdev->kill_request)
  728. return UBUS_STATUS_PERMISSION_DENIED;
  729. wireless_process_kill_all(wdev, signal, immediate);
  730. if (list_empty(&wdev->script_proc))
  731. return 0;
  732. wdev->kill_request = calloc(1, sizeof(*wdev->kill_request));
  733. ubus_defer_request(ubus_ctx, req, wdev->kill_request);
  734. return 0;
  735. }
  736. static int
  737. wireless_device_set_retry(struct wireless_device *wdev, struct blob_attr *data)
  738. {
  739. static const struct blobmsg_policy retry_policy = {
  740. .name = "retry", .type = BLOBMSG_TYPE_INT32
  741. };
  742. struct blob_attr *val;
  743. blobmsg_parse(&retry_policy, 1, &val, blobmsg_data(data), blobmsg_data_len(data));
  744. if (!val)
  745. return UBUS_STATUS_INVALID_ARGUMENT;
  746. wdev->retry = blobmsg_get_u32(val);
  747. return 0;
  748. }
  749. enum {
  750. NOTIFY_CMD_UP = 0,
  751. NOTIFY_CMD_SET_DATA = 1,
  752. NOTIFY_CMD_PROCESS_ADD = 2,
  753. NOTIFY_CMD_PROCESS_KILL_ALL = 3,
  754. NOTIFY_CMD_SET_RETRY = 4,
  755. };
  756. int
  757. wireless_device_notify(struct wireless_device *wdev, struct blob_attr *data,
  758. struct ubus_request_data *req)
  759. {
  760. enum {
  761. NOTIFY_ATTR_COMMAND,
  762. NOTIFY_ATTR_VIF,
  763. NOTIFY_ATTR_DATA,
  764. __NOTIFY_MAX,
  765. };
  766. static const struct blobmsg_policy notify_policy[__NOTIFY_MAX] = {
  767. [NOTIFY_ATTR_COMMAND] = { .name = "command", .type = BLOBMSG_TYPE_INT32 },
  768. [NOTIFY_ATTR_VIF] = { .name = "interface", .type = BLOBMSG_TYPE_STRING },
  769. [NOTIFY_ATTR_DATA] = { .name = "data", .type = BLOBMSG_TYPE_TABLE },
  770. };
  771. struct wireless_interface *vif = NULL;
  772. struct blob_attr *tb[__NOTIFY_MAX];
  773. struct blob_attr *cur, **pdata;
  774. blobmsg_parse(notify_policy, __NOTIFY_MAX, tb, blob_data(data), blob_len(data));
  775. if (!tb[NOTIFY_ATTR_COMMAND])
  776. return UBUS_STATUS_INVALID_ARGUMENT;
  777. if ((cur = tb[NOTIFY_ATTR_VIF]) != NULL) {
  778. vif = vlist_find(&wdev->interfaces, blobmsg_data(cur), vif, node);
  779. if (!vif)
  780. return UBUS_STATUS_NOT_FOUND;
  781. }
  782. cur = tb[NOTIFY_ATTR_DATA];
  783. if (!cur)
  784. return UBUS_STATUS_INVALID_ARGUMENT;
  785. switch (blobmsg_get_u32(tb[NOTIFY_ATTR_COMMAND])) {
  786. case NOTIFY_CMD_UP:
  787. if (vif)
  788. return UBUS_STATUS_INVALID_ARGUMENT;
  789. if (wdev->state != IFS_SETUP)
  790. return UBUS_STATUS_PERMISSION_DENIED;
  791. wireless_device_mark_up(wdev);
  792. break;
  793. case NOTIFY_CMD_SET_DATA:
  794. if (vif)
  795. pdata = &vif->data;
  796. else
  797. pdata = &wdev->data;
  798. if (*pdata)
  799. return UBUS_STATUS_INVALID_ARGUMENT;
  800. *pdata = blob_memdup(cur);
  801. if (vif)
  802. wireless_interface_set_data(vif);
  803. break;
  804. case NOTIFY_CMD_PROCESS_ADD:
  805. return wireless_device_add_process(wdev, cur);
  806. case NOTIFY_CMD_PROCESS_KILL_ALL:
  807. return wireless_device_process_kill_all(wdev, cur, req);
  808. case NOTIFY_CMD_SET_RETRY:
  809. return wireless_device_set_retry(wdev, cur);
  810. default:
  811. return UBUS_STATUS_INVALID_ARGUMENT;
  812. }
  813. return 0;
  814. }
  815. void
  816. wireless_start_pending(void)
  817. {
  818. struct wireless_device *wdev;
  819. vlist_for_each_element(&wireless_devices, wdev, node)
  820. __wireless_device_set_up(wdev);
  821. }