jerry_wlan.c 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652
  1. #include "jerry_wlan.h"
  2. #ifdef RT_USING_WIFI
  3. #include <rtgui/gb2312.h>
  4. #define DBG_ENABLE
  5. #define DBG_SECTION_NAME "JS WLAN"
  6. #define DBG_LEVEL DBG_LOG
  7. #include <rtdbg.h>
  8. static void get_wifi_info(void **info, jerry_value_t js_target)
  9. {
  10. jerry_value_t js_info = js_get_property(js_target, "info");
  11. if (js_info)
  12. {
  13. jerry_get_object_native_pointer(js_info, info, NULL);
  14. }
  15. jerry_release_value(js_info);
  16. }
  17. static void js_event_callback_func_wifi(const void *args, uint32_t size)
  18. {
  19. struct event_callback_info *cb_info = (struct event_callback_info*)args;
  20. if (cb_info->js_return != RT_NULL)
  21. {
  22. js_emit_event(cb_info->js_target, cb_info->event_name, &cb_info->js_return, 1);
  23. jerry_release_value(cb_info->js_return);
  24. }
  25. else
  26. {
  27. js_emit_event(cb_info->js_target, cb_info->event_name, NULL, 0);
  28. }
  29. free(cb_info->event_name);
  30. free(cb_info);
  31. }
  32. static int connect_wifi(struct wifi_info *info, char *ssid, char *password, char *bssid)
  33. {
  34. int ret = -2;
  35. if (info && ssid)
  36. {
  37. if (info->wifi_list.num)
  38. {
  39. int i = 0;
  40. char buffer[32];
  41. for (; i < info->wifi_list.num; i ++)
  42. {
  43. rt_sprintf(buffer, "%02x:%02x:%02x:%02x:%02x:%02x",
  44. info->wifi_list.info[i].bssid[0],
  45. info->wifi_list.info[i].bssid[1],
  46. info->wifi_list.info[i].bssid[2],
  47. info->wifi_list.info[i].bssid[3],
  48. info->wifi_list.info[i].bssid[4],
  49. info->wifi_list.info[i].bssid[5]
  50. );
  51. if (bssid)
  52. {
  53. if (rt_strcmp((const char *)bssid, (const char *)buffer) != 0)
  54. {
  55. continue;
  56. }
  57. }
  58. if (rt_strcmp((const char *)ssid, (const char *)info->wifi_list.info[i].ssid.val) == 0)
  59. {
  60. ret = rt_wlan_connect_adv(&(info->wifi_list.info[i]), password);
  61. break;
  62. }
  63. else if (info->gb_ssid[i].ssid && rt_strcmp((const char *)ssid, (const char *)info->gb_ssid[i].ssid) == 0)
  64. {
  65. ret = rt_wlan_connect_adv(&(info->wifi_list.info[info->gb_ssid[i].index]), password);
  66. break;
  67. }
  68. }
  69. if (ret != RT_EOK)
  70. {
  71. ret = -1;
  72. }
  73. if (i >= info->wifi_list.num)
  74. {
  75. LOG_W("The scanned wifi is not included %s", ssid);
  76. ret = -2;
  77. }
  78. }
  79. }
  80. return ret;
  81. }
  82. static void scanEvent_handler(int event, struct rt_wlan_buff *buff, void *parameter)
  83. {
  84. jerry_value_t js_wifi = (jerry_value_t)(parameter);
  85. struct wifi_info *info = RT_NULL;
  86. get_wifi_info((void**)&info, js_wifi);
  87. if (info)
  88. {
  89. int i;
  90. jerry_value_t js_return = 0;
  91. struct rt_wlan_scan_result *temp_result = (struct rt_wlan_scan_result*)buff->data;
  92. if (temp_result->num > 0)
  93. {
  94. if (info->wifi_list.info)
  95. {
  96. free(info->wifi_list.info);
  97. }
  98. if (info->gb_ssid)
  99. {
  100. for (i = 0; i < info->wifi_list.num; i++)
  101. {
  102. if (info->gb_ssid[i].ssid)
  103. {
  104. rt_free(info->gb_ssid[i].ssid);
  105. }
  106. }
  107. free(info->gb_ssid);
  108. }
  109. info->wifi_list.num = temp_result->num;
  110. info->wifi_list.info = (struct rt_wlan_info*)malloc(sizeof(struct rt_wlan_info) * info->wifi_list.num);
  111. info->gb_ssid = (struct wifi_ssid*)malloc(sizeof(struct wifi_ssid) * info->wifi_list.num);
  112. if (info->wifi_list.info)
  113. {
  114. memcpy(info->wifi_list.info, temp_result->info, sizeof(struct rt_wlan_info) * info->wifi_list.num);
  115. if (info->gb_ssid)
  116. {
  117. int j = 0;
  118. memset(info->gb_ssid, 0x00, sizeof(struct wifi_ssid) * info->wifi_list.num);
  119. for (i = 0; i < info->wifi_list.num; i++)
  120. {
  121. if (!is_utf8_string((void *)info->wifi_list.info[i].ssid.val, strlen((const char *)info->wifi_list.info[i].ssid.val)))
  122. {
  123. info->gb_ssid[j].index = i;
  124. Gb2312ToUtf8((char *)info->wifi_list.info[i].ssid.val, strlen((const char *)info->wifi_list.info[i].ssid.val), &info->gb_ssid[j].ssid);
  125. j ++;
  126. }
  127. }
  128. }
  129. if (info->ssid)
  130. {
  131. if (connect_wifi(info, info->ssid, info->password, info->bssid) == -2)
  132. {
  133. struct event_callback_info cb_info;
  134. cb_info.event_name = strdup("ConnectEvent");
  135. cb_info.js_target = js_wifi;
  136. cb_info.js_return = jerry_create_null();
  137. if (!js_send_callback(info->event_callback, &cb_info, sizeof(struct event_callback_info)))
  138. {
  139. jerry_release_value(js_return);
  140. }
  141. }
  142. free(info->ssid);
  143. free(info->password);
  144. free(info->bssid);
  145. info->ssid = NULL;
  146. info->password = NULL;
  147. info->bssid = NULL;
  148. return;
  149. }
  150. else
  151. {
  152. char buffer[32];
  153. jerry_value_t js_ssid, js_strength, js_bssid, js_secure, js_ret;
  154. js_return = jerry_create_array(info->wifi_list.num);
  155. for (i = 0; i < info->wifi_list.num; i++)
  156. {
  157. struct rt_wlan_info *wifi_info = &(info->wifi_list.info[i]);
  158. jerry_value_t js_wifi_info = jerry_create_object();
  159. js_ssid = js_string_to_value((const char*)wifi_info->ssid.val);
  160. js_set_property(js_wifi_info, "ssid", js_ssid);
  161. jerry_release_value(js_ssid);
  162. js_strength = jerry_create_number(wifi_info->rssi);
  163. js_set_property(js_wifi_info, "strength", js_strength);
  164. jerry_release_value(js_strength);
  165. rt_sprintf(buffer, "%02x:%02x:%02x:%02x:%02x:%02x",
  166. wifi_info->bssid[0],
  167. wifi_info->bssid[1],
  168. wifi_info->bssid[2],
  169. wifi_info->bssid[3],
  170. wifi_info->bssid[4],
  171. wifi_info->bssid[5]);
  172. js_bssid = jerry_create_string((const jerry_char_t*)buffer);
  173. js_set_property(js_wifi_info, "bssid", js_bssid);
  174. jerry_release_value(js_bssid);
  175. js_secure = jerry_create_boolean(wifi_info->security);
  176. js_set_property(js_wifi_info, "secure", js_secure);
  177. jerry_release_value(js_secure);
  178. js_ret = jerry_set_property_by_index(js_return, i, js_wifi_info);
  179. jerry_release_value(js_ret);
  180. jerry_release_value(js_wifi_info);
  181. }
  182. }
  183. }
  184. }
  185. {
  186. struct event_callback_info cb_info;
  187. cb_info.event_name = strdup("ScanEvent");
  188. cb_info.js_target = js_wifi;
  189. cb_info.js_return = js_return;
  190. if (!js_send_callback(info->event_callback, &cb_info, sizeof(struct event_callback_info)))
  191. {
  192. jerry_release_value(js_return);
  193. }
  194. }
  195. }
  196. }
  197. static void connectEvent_handler(int event, struct rt_wlan_buff *buff, void *parameter)
  198. {
  199. jerry_value_t js_wifi = (jerry_value_t)parameter;
  200. struct wifi_info *info = RT_NULL;
  201. get_wifi_info((void**)&info, js_wifi);
  202. if (info)
  203. {
  204. jerry_value_t js_return = 0;
  205. struct rt_wlan_info *wifi_info = (struct rt_wlan_info*)(buff->data);
  206. if (event == RT_WLAN_EVT_STA_CONNECTED)
  207. {
  208. char buffer[32];
  209. jerry_value_t js_ssid, js_strength, js_bssid, js_secure;
  210. js_return = jerry_create_object();
  211. js_ssid = js_string_to_value((const char*)wifi_info->ssid.val);
  212. js_set_property(js_return, "ssid", js_ssid);
  213. jerry_release_value(js_ssid);
  214. js_strength = jerry_create_number(wifi_info->rssi);
  215. js_set_property(js_return, "strength", js_strength);
  216. jerry_release_value(js_strength);
  217. rt_sprintf(buffer, "%02x:%02x:%02x:%02x:%02x:%02x",
  218. wifi_info->bssid[0],
  219. wifi_info->bssid[1],
  220. wifi_info->bssid[2],
  221. wifi_info->bssid[3],
  222. wifi_info->bssid[4],
  223. wifi_info->bssid[5]);
  224. js_bssid = jerry_create_string((const jerry_char_t*)buffer);
  225. js_set_property(js_return, "bssid", js_bssid);
  226. jerry_release_value(js_bssid);
  227. js_secure = jerry_create_boolean(wifi_info->security);
  228. js_set_property(js_return, "secure", js_secure);
  229. jerry_release_value(js_secure);
  230. }
  231. else
  232. {
  233. js_return = jerry_create_null();
  234. }
  235. {
  236. struct event_callback_info cb_info;
  237. cb_info.event_name = strdup("ConnectEvent");
  238. cb_info.js_target = js_wifi;
  239. cb_info.js_return = js_return;
  240. if (!js_send_callback(info->event_callback, &cb_info, sizeof(struct event_callback_info)))
  241. {
  242. jerry_release_value(js_return);
  243. }
  244. }
  245. }
  246. }
  247. static void networkEvent_handler(int event, struct rt_wlan_buff *buff, void *parameter)
  248. {
  249. jerry_value_t js_wifi = (jerry_value_t)parameter;
  250. struct wifi_info *info= RT_NULL;
  251. get_wifi_info((void**)&info, js_wifi);
  252. if (info)
  253. {
  254. jerry_value_t js_return = 0;
  255. struct event_callback_info cb_info;
  256. if (RT_WLAN_EVT_READY == event)
  257. {
  258. js_return = jerry_create_boolean(true);
  259. }
  260. else
  261. {
  262. js_return = jerry_create_boolean(false);
  263. }
  264. cb_info.event_name = strdup("NetworkEvent");
  265. cb_info.js_target = js_wifi;
  266. cb_info.js_return = js_return;
  267. if (!js_send_callback(info->event_callback, &cb_info, sizeof(struct event_callback_info)))
  268. {
  269. jerry_release_value(js_return);
  270. }
  271. }
  272. }
  273. void wifi_free_callback(void *native_p)
  274. {
  275. struct wifi_info *info = (struct wifi_info*)native_p;
  276. if (info)
  277. {
  278. if (info->wifi_list.info)
  279. free(info->wifi_list.info);
  280. if (info->event_callback)
  281. js_remove_callback(info->event_callback);
  282. if (info)
  283. free(info);
  284. }
  285. rt_wlan_unregister_event_handler(RT_WLAN_EVT_SCAN_DONE);
  286. rt_wlan_unregister_event_handler(RT_WLAN_EVT_STA_CONNECTED);
  287. rt_wlan_unregister_event_handler(RT_WLAN_EVT_STA_CONNECTED_FAIL);
  288. rt_wlan_unregister_event_handler(RT_WLAN_EVT_READY);
  289. rt_wlan_unregister_event_handler(RT_WLAN_EVT_STA_DISCONNECTED);
  290. }
  291. const static jerry_object_native_info_t wifi_free_info =
  292. {
  293. wifi_free_callback
  294. };
  295. void register_handler(jerry_value_t js_wifi)
  296. {
  297. rt_wlan_register_event_handler(RT_WLAN_EVT_SCAN_DONE, scanEvent_handler, (void*)js_wifi);
  298. rt_wlan_register_event_handler(RT_WLAN_EVT_STA_CONNECTED, connectEvent_handler, (void*)js_wifi);
  299. rt_wlan_register_event_handler(RT_WLAN_EVT_STA_CONNECTED_FAIL, connectEvent_handler, (void*)js_wifi);
  300. rt_wlan_register_event_handler(RT_WLAN_EVT_READY, networkEvent_handler, (void*)js_wifi);
  301. rt_wlan_register_event_handler(RT_WLAN_EVT_STA_DISCONNECTED, networkEvent_handler, (void*)js_wifi);
  302. }
  303. DECLARE_HANDLER(openWifi)
  304. {
  305. if (args_cnt >= 1)
  306. {
  307. char *name = RT_NULL;
  308. if (jerry_value_is_string(args[0]))
  309. {
  310. name = js_value_to_string(args[0]);
  311. }
  312. if (name)
  313. {
  314. rt_err_t ret = rt_wlan_set_mode(name, RT_WLAN_STATION);
  315. if (ret == RT_EOK)
  316. {
  317. return jerry_create_boolean(true);
  318. }
  319. }
  320. }
  321. return jerry_create_boolean(false);
  322. }
  323. DECLARE_HANDLER(scanWifi)
  324. {
  325. rt_err_t ret = rt_wlan_scan();
  326. if (ret == RT_EOK)
  327. {
  328. return jerry_create_boolean(true);
  329. }
  330. return jerry_create_boolean(false);
  331. }
  332. DECLARE_HANDLER(connectWifi)
  333. {
  334. if (args_cnt >= 1 && jerry_value_is_object(args[0]))
  335. {
  336. char *ssid = RT_NULL;
  337. char *bssid = RT_NULL;
  338. char *password = RT_NULL;
  339. struct wifi_info *info= RT_NULL;
  340. get_wifi_info((void**)&info, this_value);
  341. if (info)
  342. {
  343. jerry_value_t js_ssid = js_get_property(args[0], "ssid");
  344. jerry_value_t js_bssid = js_get_property(args[0], "bssid");
  345. jerry_value_t js_password = js_get_property(args[0], "password");
  346. if (jerry_value_is_string(js_ssid))
  347. {
  348. ssid = js_value_to_string(js_ssid);
  349. }
  350. jerry_release_value(js_ssid);
  351. if (jerry_value_is_string(js_bssid))
  352. {
  353. bssid = js_value_to_string(js_bssid);
  354. }
  355. jerry_release_value(js_bssid);
  356. if (jerry_value_is_string(js_password))
  357. {
  358. password = js_value_to_string(js_password);
  359. }
  360. jerry_release_value(js_password);
  361. if (ssid)
  362. {
  363. rt_err_t ret = -1;
  364. ret = connect_wifi(info, ssid, password, bssid);
  365. if (ret == RT_EOK)
  366. {
  367. free(ssid);
  368. free(password);
  369. free(bssid);
  370. return jerry_create_boolean(true);
  371. }
  372. if (ret == -2)
  373. {
  374. ret = rt_wlan_scan();
  375. if (ret == RT_EOK)
  376. {
  377. free(info->ssid);
  378. free(info->password);
  379. free(info->bssid);
  380. info->ssid = ssid;
  381. info->password = password;
  382. info->bssid = bssid;
  383. return jerry_create_boolean(true);
  384. }
  385. }
  386. }
  387. free(ssid);
  388. free(password);
  389. free(bssid);
  390. }
  391. }
  392. return jerry_create_boolean(false);
  393. }
  394. DECLARE_HANDLER(disconnectWifi)
  395. {
  396. rt_err_t ret = rt_wlan_disconnect();
  397. if (ret == RT_EOK)
  398. {
  399. return jerry_create_boolean(true);
  400. }
  401. return jerry_create_boolean(false);
  402. }
  403. DECLARE_HANDLER(onScanEvent)
  404. {
  405. if (args_cnt == 1 && jerry_value_is_function(args[0]))
  406. {
  407. js_add_event_listener(this_value, "ScanEvent", args[0]);
  408. }
  409. return jerry_create_undefined();
  410. }
  411. DECLARE_HANDLER(onConnectEvent)
  412. {
  413. if (args_cnt == 1 && jerry_value_is_function(args[0]))
  414. {
  415. js_add_event_listener(this_value, "ConnectEvent", args[0]);
  416. }
  417. return jerry_create_undefined();
  418. }
  419. DECLARE_HANDLER(onNetworkEvent)
  420. {
  421. if (args_cnt == 1 && jerry_value_is_function(args[0]))
  422. {
  423. js_add_event_listener(this_value, "NetworkEvent", args[0]);
  424. }
  425. return jerry_create_undefined();
  426. }
  427. DECLARE_HANDLER(getConnectedWifi)
  428. {
  429. struct rt_wlan_info info;
  430. if (rt_wlan_is_connected())
  431. {
  432. rt_err_t ret = rt_wlan_get_info(&info);
  433. if (ret == RT_EOK)
  434. {
  435. jerry_value_t js_ssid, js_strength, js_bssid, js_secure;
  436. jerry_value_t js_wifi_info = jerry_create_object();
  437. if (js_wifi_info)
  438. {
  439. char bssid[32];
  440. js_ssid = js_string_to_value((const char*)info.ssid.val);
  441. js_set_property(js_wifi_info, "ssid", js_ssid);
  442. jerry_release_value(js_ssid);
  443. js_strength = jerry_create_number(info.rssi);
  444. js_set_property(js_wifi_info, "strength", js_strength);
  445. jerry_release_value(js_strength);
  446. rt_sprintf(bssid, "%02x:%02x:%02x:%02x:%02x:%02x",
  447. info.bssid[0],
  448. info.bssid[1],
  449. info.bssid[2],
  450. info.bssid[3],
  451. info.bssid[4],
  452. info.bssid[5]);
  453. js_bssid = jerry_create_string((const jerry_char_t*)bssid);
  454. js_set_property(js_wifi_info, "bssid", js_bssid);
  455. jerry_release_value(js_bssid);
  456. js_secure = jerry_create_boolean(info.security);
  457. js_set_property(js_wifi_info, "secure", js_secure);
  458. jerry_release_value(js_secure);
  459. return js_wifi_info;
  460. }
  461. }
  462. }
  463. return jerry_create_null();
  464. }
  465. DECLARE_HANDLER(destroy)
  466. {
  467. struct wifi_info *info= RT_NULL;
  468. jerry_value_t js_info = js_get_property(this_value, "info");
  469. if (js_info)
  470. {
  471. jerry_get_object_native_pointer(js_info, (void **)&info, NULL);
  472. jerry_set_object_native_pointer(js_info, NULL, NULL);
  473. }
  474. jerry_release_value(js_info);
  475. rt_wlan_unregister_event_handler(RT_WLAN_EVT_SCAN_DONE);
  476. rt_wlan_unregister_event_handler(RT_WLAN_EVT_STA_CONNECTED);
  477. rt_wlan_unregister_event_handler(RT_WLAN_EVT_STA_CONNECTED_FAIL);
  478. rt_wlan_unregister_event_handler(RT_WLAN_EVT_READY);
  479. rt_wlan_unregister_event_handler(RT_WLAN_EVT_STA_DISCONNECTED);
  480. js_destroy_emitter(this_value);
  481. if (info)
  482. {
  483. if (info->wifi_list.info)
  484. free(info->wifi_list.info);
  485. if (info->event_callback)
  486. js_remove_callback(info->event_callback);
  487. if (info)
  488. free(info);
  489. }
  490. return jerry_create_undefined();
  491. }
  492. DECLARE_HANDLER(createWifi)
  493. {
  494. struct wifi_info* wifi_info = (struct wifi_info*)malloc(sizeof(struct wifi_info));
  495. if (wifi_info)
  496. {
  497. jerry_value_t js_wifi = jerry_create_object();
  498. jerry_value_t js_info = jerry_create_object();
  499. if (js_wifi && js_info)
  500. {
  501. memset(wifi_info, 0x00, sizeof(struct wifi_info));
  502. js_make_emitter(js_wifi, jerry_create_undefined());
  503. wifi_info->this_value = js_wifi;
  504. wifi_info->event_callback = js_add_callback(js_event_callback_func_wifi);
  505. js_set_property(js_wifi, "info", js_info);
  506. jerry_set_object_native_pointer(js_info, wifi_info, &wifi_free_info);
  507. jerry_release_value(js_info);
  508. REGISTER_METHOD_NAME(js_wifi, "open", openWifi);
  509. REGISTER_METHOD_NAME(js_wifi, "scan", scanWifi);
  510. REGISTER_METHOD_NAME(js_wifi, "connect", connectWifi);
  511. REGISTER_METHOD_NAME(js_wifi, "disconnect", disconnectWifi);
  512. REGISTER_METHOD_NAME(js_wifi, "getConnected", getConnectedWifi);
  513. REGISTER_METHOD_NAME(js_wifi, "onScanEvent", onScanEvent);
  514. REGISTER_METHOD_NAME(js_wifi, "onConnectEvent", onConnectEvent);
  515. REGISTER_METHOD_NAME(js_wifi, "onNetworkEvent", onNetworkEvent);
  516. REGISTER_METHOD(js_wifi, destroy);
  517. register_handler(js_wifi);
  518. return js_wifi;
  519. }
  520. else
  521. {
  522. jerry_release_value(js_wifi);
  523. jerry_release_value(js_info);
  524. }
  525. free(wifi_info);
  526. }
  527. return jerry_create_undefined();
  528. }
  529. int jerry_wifi_init(jerry_value_t obj)
  530. {
  531. REGISTER_METHOD(obj, createWifi);
  532. return 0;
  533. }
  534. #endif