wlp-lc.c 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559
  1. /*
  2. * WiMedia Logical Link Control Protocol (WLP)
  3. *
  4. * Copyright (C) 2005-2006 Intel Corporation
  5. * Reinette Chatre <reinette.chatre@intel.com>
  6. *
  7. * This program is free software; you can redistribute it and/or
  8. * modify it under the terms of the GNU General Public License version
  9. * 2 as published by the Free Software Foundation.
  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 Street, Fifth Floor, Boston, MA
  19. * 02110-1301, USA.
  20. *
  21. *
  22. * FIXME: docs
  23. */
  24. #include <linux/wlp.h>
  25. #include "wlp-internal.h"
  26. static
  27. void wlp_neighbor_init(struct wlp_neighbor_e *neighbor)
  28. {
  29. INIT_LIST_HEAD(&neighbor->wssid);
  30. }
  31. /**
  32. * Create area for device information storage
  33. *
  34. * wlp->mutex must be held
  35. */
  36. int __wlp_alloc_device_info(struct wlp *wlp)
  37. {
  38. struct device *dev = &wlp->rc->uwb_dev.dev;
  39. BUG_ON(wlp->dev_info != NULL);
  40. wlp->dev_info = kzalloc(sizeof(struct wlp_device_info), GFP_KERNEL);
  41. if (wlp->dev_info == NULL) {
  42. dev_err(dev, "WLP: Unable to allocate memory for "
  43. "device information.\n");
  44. return -ENOMEM;
  45. }
  46. return 0;
  47. }
  48. /**
  49. * Fill in device information using function provided by driver
  50. *
  51. * wlp->mutex must be held
  52. */
  53. static
  54. void __wlp_fill_device_info(struct wlp *wlp)
  55. {
  56. wlp->fill_device_info(wlp, wlp->dev_info);
  57. }
  58. /**
  59. * Setup device information
  60. *
  61. * Allocate area for device information and populate it.
  62. *
  63. * wlp->mutex must be held
  64. */
  65. int __wlp_setup_device_info(struct wlp *wlp)
  66. {
  67. int result;
  68. struct device *dev = &wlp->rc->uwb_dev.dev;
  69. result = __wlp_alloc_device_info(wlp);
  70. if (result < 0) {
  71. dev_err(dev, "WLP: Unable to allocate area for "
  72. "device information.\n");
  73. return result;
  74. }
  75. __wlp_fill_device_info(wlp);
  76. return 0;
  77. }
  78. /**
  79. * Remove information about neighbor stored temporarily
  80. *
  81. * Information learned during discovey should only be stored when the
  82. * device enrolls in the neighbor's WSS. We do need to store this
  83. * information temporarily in order to present it to the user.
  84. *
  85. * We are only interested in keeping neighbor WSS information if that
  86. * neighbor is accepting enrollment.
  87. *
  88. * should be called with wlp->nbmutex held
  89. */
  90. void wlp_remove_neighbor_tmp_info(struct wlp_neighbor_e *neighbor)
  91. {
  92. struct wlp_wssid_e *wssid_e, *next;
  93. u8 keep;
  94. if (!list_empty(&neighbor->wssid)) {
  95. list_for_each_entry_safe(wssid_e, next, &neighbor->wssid,
  96. node) {
  97. if (wssid_e->info != NULL) {
  98. keep = wssid_e->info->accept_enroll;
  99. kfree(wssid_e->info);
  100. wssid_e->info = NULL;
  101. if (!keep) {
  102. list_del(&wssid_e->node);
  103. kfree(wssid_e);
  104. }
  105. }
  106. }
  107. }
  108. if (neighbor->info != NULL) {
  109. kfree(neighbor->info);
  110. neighbor->info = NULL;
  111. }
  112. }
  113. /*
  114. * Populate WLP neighborhood cache with neighbor information
  115. *
  116. * A new neighbor is found. If it is discoverable then we add it to the
  117. * neighborhood cache.
  118. *
  119. */
  120. static
  121. int wlp_add_neighbor(struct wlp *wlp, struct uwb_dev *dev)
  122. {
  123. int result = 0;
  124. int discoverable;
  125. struct wlp_neighbor_e *neighbor;
  126. /*
  127. * FIXME:
  128. * Use contents of WLP IE found in beacon cache to determine if
  129. * neighbor is discoverable.
  130. * The device does not support WLP IE yet so this still needs to be
  131. * done. Until then we assume all devices are discoverable.
  132. */
  133. discoverable = 1; /* will be changed when FIXME disappears */
  134. if (discoverable) {
  135. /* Add neighbor to cache for discovery */
  136. neighbor = kzalloc(sizeof(*neighbor), GFP_KERNEL);
  137. if (neighbor == NULL) {
  138. dev_err(&dev->dev, "Unable to create memory for "
  139. "new neighbor. \n");
  140. result = -ENOMEM;
  141. goto error_no_mem;
  142. }
  143. wlp_neighbor_init(neighbor);
  144. uwb_dev_get(dev);
  145. neighbor->uwb_dev = dev;
  146. list_add(&neighbor->node, &wlp->neighbors);
  147. }
  148. error_no_mem:
  149. return result;
  150. }
  151. /**
  152. * Remove one neighbor from cache
  153. */
  154. static
  155. void __wlp_neighbor_release(struct wlp_neighbor_e *neighbor)
  156. {
  157. struct wlp_wssid_e *wssid_e, *next_wssid_e;
  158. list_for_each_entry_safe(wssid_e, next_wssid_e,
  159. &neighbor->wssid, node) {
  160. list_del(&wssid_e->node);
  161. kfree(wssid_e);
  162. }
  163. uwb_dev_put(neighbor->uwb_dev);
  164. list_del(&neighbor->node);
  165. kfree(neighbor);
  166. }
  167. /**
  168. * Clear entire neighborhood cache.
  169. */
  170. static
  171. void __wlp_neighbors_release(struct wlp *wlp)
  172. {
  173. struct wlp_neighbor_e *neighbor, *next;
  174. if (list_empty(&wlp->neighbors))
  175. return;
  176. list_for_each_entry_safe(neighbor, next, &wlp->neighbors, node) {
  177. __wlp_neighbor_release(neighbor);
  178. }
  179. }
  180. static
  181. void wlp_neighbors_release(struct wlp *wlp)
  182. {
  183. mutex_lock(&wlp->nbmutex);
  184. __wlp_neighbors_release(wlp);
  185. mutex_unlock(&wlp->nbmutex);
  186. }
  187. /**
  188. * Send D1 message to neighbor, receive D2 message
  189. *
  190. * @neighbor: neighbor to which D1 message will be sent
  191. * @wss: if not NULL, it is an enrollment request for this WSS
  192. * @wssid: if wss not NULL, this is the wssid of the WSS in which we
  193. * want to enroll
  194. *
  195. * A D1/D2 exchange is done for one of two reasons: discovery or
  196. * enrollment. If done for discovery the D1 message is sent to the neighbor
  197. * and the contents of the D2 response is stored in a temporary cache.
  198. * If done for enrollment the @wss and @wssid are provided also. In this
  199. * case the D1 message is sent to the neighbor, the D2 response is parsed
  200. * for enrollment of the WSS with wssid.
  201. *
  202. * &wss->mutex is held
  203. */
  204. static
  205. int wlp_d1d2_exchange(struct wlp *wlp, struct wlp_neighbor_e *neighbor,
  206. struct wlp_wss *wss, struct wlp_uuid *wssid)
  207. {
  208. int result;
  209. struct device *dev = &wlp->rc->uwb_dev.dev;
  210. DECLARE_COMPLETION_ONSTACK(completion);
  211. struct wlp_session session;
  212. struct sk_buff *skb;
  213. struct wlp_frame_assoc *resp;
  214. struct uwb_dev_addr *dev_addr = &neighbor->uwb_dev->dev_addr;
  215. mutex_lock(&wlp->mutex);
  216. if (!wlp_uuid_is_set(&wlp->uuid)) {
  217. dev_err(dev, "WLP: UUID is not set. Set via sysfs to "
  218. "proceed.\n");
  219. result = -ENXIO;
  220. goto out;
  221. }
  222. /* Send D1 association frame */
  223. result = wlp_send_assoc_frame(wlp, wss, dev_addr, WLP_ASSOC_D1);
  224. if (result < 0) {
  225. dev_err(dev, "Unable to send D1 frame to neighbor "
  226. "%02x:%02x (%d)\n", dev_addr->data[1],
  227. dev_addr->data[0], result);
  228. goto out;
  229. }
  230. /* Create session, wait for response */
  231. session.exp_message = WLP_ASSOC_D2;
  232. session.cb = wlp_session_cb;
  233. session.cb_priv = &completion;
  234. session.neighbor_addr = *dev_addr;
  235. BUG_ON(wlp->session != NULL);
  236. wlp->session = &session;
  237. /* Wait for D2/F0 frame */
  238. result = wait_for_completion_interruptible_timeout(&completion,
  239. WLP_PER_MSG_TIMEOUT * HZ);
  240. if (result == 0) {
  241. result = -ETIMEDOUT;
  242. dev_err(dev, "Timeout while sending D1 to neighbor "
  243. "%02x:%02x.\n", dev_addr->data[1],
  244. dev_addr->data[0]);
  245. goto error_session;
  246. }
  247. if (result < 0) {
  248. dev_err(dev, "Unable to discover/enroll neighbor %02x:%02x.\n",
  249. dev_addr->data[1], dev_addr->data[0]);
  250. goto error_session;
  251. }
  252. /* Parse message in session->data: it will be either D2 or F0 */
  253. skb = session.data;
  254. resp = (void *) skb->data;
  255. if (resp->type == WLP_ASSOC_F0) {
  256. result = wlp_parse_f0(wlp, skb);
  257. if (result < 0)
  258. dev_err(dev, "WLP: Unable to parse F0 from neighbor "
  259. "%02x:%02x.\n", dev_addr->data[1],
  260. dev_addr->data[0]);
  261. result = -EINVAL;
  262. goto error_resp_parse;
  263. }
  264. if (wss == NULL) {
  265. /* Discovery */
  266. result = wlp_parse_d2_frame_to_cache(wlp, skb, neighbor);
  267. if (result < 0) {
  268. dev_err(dev, "WLP: Unable to parse D2 message from "
  269. "neighbor %02x:%02x for discovery.\n",
  270. dev_addr->data[1], dev_addr->data[0]);
  271. goto error_resp_parse;
  272. }
  273. } else {
  274. /* Enrollment */
  275. result = wlp_parse_d2_frame_to_enroll(wss, skb, neighbor,
  276. wssid);
  277. if (result < 0) {
  278. dev_err(dev, "WLP: Unable to parse D2 message from "
  279. "neighbor %02x:%02x for enrollment.\n",
  280. dev_addr->data[1], dev_addr->data[0]);
  281. goto error_resp_parse;
  282. }
  283. }
  284. error_resp_parse:
  285. kfree_skb(skb);
  286. error_session:
  287. wlp->session = NULL;
  288. out:
  289. mutex_unlock(&wlp->mutex);
  290. return result;
  291. }
  292. /**
  293. * Enroll into WSS of provided WSSID by using neighbor as registrar
  294. *
  295. * &wss->mutex is held
  296. */
  297. int wlp_enroll_neighbor(struct wlp *wlp, struct wlp_neighbor_e *neighbor,
  298. struct wlp_wss *wss, struct wlp_uuid *wssid)
  299. {
  300. int result = 0;
  301. struct device *dev = &wlp->rc->uwb_dev.dev;
  302. char buf[WLP_WSS_UUID_STRSIZE];
  303. struct uwb_dev_addr *dev_addr = &neighbor->uwb_dev->dev_addr;
  304. wlp_wss_uuid_print(buf, sizeof(buf), wssid);
  305. result = wlp_d1d2_exchange(wlp, neighbor, wss, wssid);
  306. if (result < 0) {
  307. dev_err(dev, "WLP: D1/D2 message exchange for enrollment "
  308. "failed. result = %d \n", result);
  309. goto out;
  310. }
  311. if (wss->state != WLP_WSS_STATE_PART_ENROLLED) {
  312. dev_err(dev, "WLP: Unable to enroll into WSS %s using "
  313. "neighbor %02x:%02x. \n", buf,
  314. dev_addr->data[1], dev_addr->data[0]);
  315. result = -EINVAL;
  316. goto out;
  317. }
  318. if (wss->secure_status == WLP_WSS_SECURE) {
  319. dev_err(dev, "FIXME: need to complete secure enrollment.\n");
  320. result = -EINVAL;
  321. goto error;
  322. } else {
  323. wss->state = WLP_WSS_STATE_ENROLLED;
  324. dev_dbg(dev, "WLP: Success Enrollment into unsecure WSS "
  325. "%s using neighbor %02x:%02x. \n",
  326. buf, dev_addr->data[1], dev_addr->data[0]);
  327. }
  328. out:
  329. return result;
  330. error:
  331. wlp_wss_reset(wss);
  332. return result;
  333. }
  334. /**
  335. * Discover WSS information of neighbor's active WSS
  336. */
  337. static
  338. int wlp_discover_neighbor(struct wlp *wlp,
  339. struct wlp_neighbor_e *neighbor)
  340. {
  341. return wlp_d1d2_exchange(wlp, neighbor, NULL, NULL);
  342. }
  343. /**
  344. * Each neighbor in the neighborhood cache is discoverable. Discover it.
  345. *
  346. * Discovery is done through sending of D1 association frame and parsing
  347. * the D2 association frame response. Only wssid from D2 will be included
  348. * in neighbor cache, rest is just displayed to user and forgotten.
  349. *
  350. * The discovery is not done in parallel. This is simple and enables us to
  351. * maintain only one association context.
  352. *
  353. * The discovery of one neighbor does not affect the other, but if the
  354. * discovery of a neighbor fails it is removed from the neighborhood cache.
  355. */
  356. static
  357. int wlp_discover_all_neighbors(struct wlp *wlp)
  358. {
  359. int result = 0;
  360. struct device *dev = &wlp->rc->uwb_dev.dev;
  361. struct wlp_neighbor_e *neighbor, *next;
  362. list_for_each_entry_safe(neighbor, next, &wlp->neighbors, node) {
  363. result = wlp_discover_neighbor(wlp, neighbor);
  364. if (result < 0) {
  365. dev_err(dev, "WLP: Unable to discover neighbor "
  366. "%02x:%02x, removing from neighborhood. \n",
  367. neighbor->uwb_dev->dev_addr.data[1],
  368. neighbor->uwb_dev->dev_addr.data[0]);
  369. __wlp_neighbor_release(neighbor);
  370. }
  371. }
  372. return result;
  373. }
  374. static int wlp_add_neighbor_helper(struct device *dev, void *priv)
  375. {
  376. struct wlp *wlp = priv;
  377. struct uwb_dev *uwb_dev = to_uwb_dev(dev);
  378. return wlp_add_neighbor(wlp, uwb_dev);
  379. }
  380. /**
  381. * Discover WLP neighborhood
  382. *
  383. * Will send D1 association frame to all devices in beacon group that have
  384. * discoverable bit set in WLP IE. D2 frames will be received, information
  385. * displayed to user in @buf. Partial information (from D2 association
  386. * frame) will be cached to assist with future association
  387. * requests.
  388. *
  389. * The discovery of the WLP neighborhood is triggered by the user. This
  390. * should occur infrequently and we thus free current cache and re-allocate
  391. * memory if needed.
  392. *
  393. * If one neighbor fails during initial discovery (determining if it is a
  394. * neighbor or not), we fail all - note that interaction with neighbor has
  395. * not occured at this point so if a failure occurs we know something went wrong
  396. * locally. We thus undo everything.
  397. */
  398. ssize_t wlp_discover(struct wlp *wlp)
  399. {
  400. int result = 0;
  401. struct device *dev = &wlp->rc->uwb_dev.dev;
  402. mutex_lock(&wlp->nbmutex);
  403. /* Clear current neighborhood cache. */
  404. __wlp_neighbors_release(wlp);
  405. /* Determine which devices in neighborhood. Repopulate cache. */
  406. result = uwb_dev_for_each(wlp->rc, wlp_add_neighbor_helper, wlp);
  407. if (result < 0) {
  408. /* May have partial neighbor information, release all. */
  409. __wlp_neighbors_release(wlp);
  410. goto error_dev_for_each;
  411. }
  412. /* Discover the properties of devices in neighborhood. */
  413. result = wlp_discover_all_neighbors(wlp);
  414. /* In case of failure we still print our partial results. */
  415. if (result < 0) {
  416. dev_err(dev, "Unable to fully discover neighborhood. \n");
  417. result = 0;
  418. }
  419. error_dev_for_each:
  420. mutex_unlock(&wlp->nbmutex);
  421. return result;
  422. }
  423. /**
  424. * Handle events from UWB stack
  425. *
  426. * We handle events conservatively. If a neighbor goes off the air we
  427. * remove it from the neighborhood. If an association process is in
  428. * progress this function will block waiting for the nbmutex to become
  429. * free. The association process will thus be allowed to complete before it
  430. * is removed.
  431. */
  432. static
  433. void wlp_uwb_notifs_cb(void *_wlp, struct uwb_dev *uwb_dev,
  434. enum uwb_notifs event)
  435. {
  436. struct wlp *wlp = _wlp;
  437. struct device *dev = &wlp->rc->uwb_dev.dev;
  438. struct wlp_neighbor_e *neighbor, *next;
  439. int result;
  440. switch (event) {
  441. case UWB_NOTIF_ONAIR:
  442. result = wlp_eda_create_node(&wlp->eda,
  443. uwb_dev->mac_addr.data,
  444. &uwb_dev->dev_addr);
  445. if (result < 0)
  446. dev_err(dev, "WLP: Unable to add new neighbor "
  447. "%02x:%02x to EDA cache.\n",
  448. uwb_dev->dev_addr.data[1],
  449. uwb_dev->dev_addr.data[0]);
  450. break;
  451. case UWB_NOTIF_OFFAIR:
  452. wlp_eda_rm_node(&wlp->eda, &uwb_dev->dev_addr);
  453. mutex_lock(&wlp->nbmutex);
  454. list_for_each_entry_safe(neighbor, next, &wlp->neighbors, node) {
  455. if (neighbor->uwb_dev == uwb_dev)
  456. __wlp_neighbor_release(neighbor);
  457. }
  458. mutex_unlock(&wlp->nbmutex);
  459. break;
  460. default:
  461. dev_err(dev, "don't know how to handle event %d from uwb\n",
  462. event);
  463. }
  464. }
  465. static void wlp_channel_changed(struct uwb_pal *pal, int channel)
  466. {
  467. struct wlp *wlp = container_of(pal, struct wlp, pal);
  468. if (channel < 0)
  469. netif_carrier_off(wlp->ndev);
  470. else
  471. netif_carrier_on(wlp->ndev);
  472. }
  473. int wlp_setup(struct wlp *wlp, struct uwb_rc *rc, struct net_device *ndev)
  474. {
  475. int result;
  476. BUG_ON(wlp->fill_device_info == NULL);
  477. BUG_ON(wlp->xmit_frame == NULL);
  478. BUG_ON(wlp->stop_queue == NULL);
  479. BUG_ON(wlp->start_queue == NULL);
  480. wlp->rc = rc;
  481. wlp->ndev = ndev;
  482. wlp_eda_init(&wlp->eda);/* Set up address cache */
  483. wlp->uwb_notifs_handler.cb = wlp_uwb_notifs_cb;
  484. wlp->uwb_notifs_handler.data = wlp;
  485. uwb_notifs_register(rc, &wlp->uwb_notifs_handler);
  486. uwb_pal_init(&wlp->pal);
  487. wlp->pal.rc = rc;
  488. wlp->pal.channel_changed = wlp_channel_changed;
  489. result = uwb_pal_register(&wlp->pal);
  490. if (result < 0)
  491. uwb_notifs_deregister(wlp->rc, &wlp->uwb_notifs_handler);
  492. return result;
  493. }
  494. EXPORT_SYMBOL_GPL(wlp_setup);
  495. void wlp_remove(struct wlp *wlp)
  496. {
  497. wlp_neighbors_release(wlp);
  498. uwb_pal_unregister(&wlp->pal);
  499. uwb_notifs_deregister(wlp->rc, &wlp->uwb_notifs_handler);
  500. wlp_eda_release(&wlp->eda);
  501. mutex_lock(&wlp->mutex);
  502. if (wlp->dev_info != NULL)
  503. kfree(wlp->dev_info);
  504. mutex_unlock(&wlp->mutex);
  505. wlp->rc = NULL;
  506. }
  507. EXPORT_SYMBOL_GPL(wlp_remove);
  508. /**
  509. * wlp_reset_all - reset the WLP hardware
  510. * @wlp: the WLP device to reset.
  511. *
  512. * This schedules a full hardware reset of the WLP device. The radio
  513. * controller and any other PALs will also be reset.
  514. */
  515. void wlp_reset_all(struct wlp *wlp)
  516. {
  517. uwb_rc_reset_all(wlp->rc);
  518. }
  519. EXPORT_SYMBOL_GPL(wlp_reset_all);