1 /*
2  * Copyright (C) 2015-2019 Alibaba Group Holding Limited
3  */
4 
5 #include <stdio.h>
6 #include <string.h>
7 #include <stdarg.h>
8 
9 #include "amp_config.h"
10 #include "aos_system.h"
11 #include "amp_defines.h"
12 #include "aos_network.h"
13 #include "netmgr_wifi.h"
14 #include "amp_task.h"
15 #include "be_inl.h"
16 
17 #define MOD_STR "WIFI"
18 #define WIFI_CONNECT_WAIT_TIME_MS (10 * 1000)
19 #define WIFI_CHECKIP_INTERVAL_MS 200
20 
js_cb_wifi_conn_status(void * pdata)21 static void js_cb_wifi_conn_status(void *pdata)
22 {
23     int ret = -1;
24     int js_cb_ref = (int)pdata;
25     aos_wifi_info_t wifi_info;
26 
27     ret = aos_get_wifi_info(&wifi_info);
28     if (ret != 0) {
29         amp_debug(MOD_STR, "get wifi info failed");
30     }
31 
32     duk_context *ctx = be_get_context();
33     be_push_ref(ctx, js_cb_ref);
34 
35     if (strcmp(wifi_info.ip, "0,0,0,0") != 0)
36         duk_push_string(ctx, "CONNECTED");
37     else
38         duk_push_string(ctx, "DISCONNECT");
39     if (duk_pcall(ctx, 1) != DUK_EXEC_SUCCESS) {
40         amp_console("%s", duk_safe_to_stacktrace(ctx, -1));
41     }
42     duk_pop(ctx);
43     be_unref(ctx, js_cb_ref);
44     duk_gc(ctx, 0);
45 }
46 
wifi_check_ip_task(void * arg)47 static void wifi_check_ip_task(void *arg)
48 {
49     int ret = -1;
50     int count = 0;
51     aos_wifi_info_t wifi_info;
52 
53     ret = aos_get_wifi_info(&wifi_info);
54     if (ret != 0) {
55         amp_debug(MOD_STR, "get wifi info failed");
56     }
57 
58     while (1) {
59         if ((strcmp(wifi_info.ip, "0,0,0,0") != 0) ||
60             (count > WIFI_CONNECT_WAIT_TIME_MS / WIFI_CHECKIP_INTERVAL_MS)) {
61             amp_task_schedule_call(js_cb_wifi_conn_status, arg);
62             break;
63         }
64         aos_msleep(WIFI_CHECKIP_INTERVAL_MS);
65         count++;
66     }
67 
68     return;
69 }
70 
native_wifi_connect(duk_context * ctx)71 static duk_ret_t native_wifi_connect(duk_context *ctx)
72 {
73     int ret = -1;
74     aos_task_t wifi_connect_task;
75 
76     if (!duk_is_string(ctx, 0) || !duk_is_string(ctx, 1) ||
77         !duk_is_function(ctx, 2)) {
78         amp_warn(MOD_STR, "parameter must be string, string and function\n");
79         goto out;
80     }
81     const char *ssid = duk_get_string(ctx, 0);
82     const char *passwd = duk_get_string(ctx, 1);
83 
84     ret = aos_wifi_connect(ssid, passwd);
85     if (ret != 0) {
86         amp_warn(MOD_STR, "wifi connect failed\n");
87         goto out;
88     }
89     duk_dup(ctx, 2);
90     int js_cb_ref = be_ref(ctx);
91 
92     ret = aos_task_new_ext(&wifi_connect_task, "wifi connect task", wifi_check_ip_task, (void *)js_cb_ref, 1024 * 2, ADDON_TSK_PRIORRITY);
93 
94     if (ret != 0) {
95         amp_warn(MOD_STR, "jse_osal_create_task failed\n");
96         be_unref(ctx, js_cb_ref);
97     }
98 out:
99     duk_push_int(ctx, ret);
100     return 1;
101 }
102 
103 /*****************************************************************************
104  * Function:    native_wifi_getip
105  * Description: js native addon for WIFI.getip()
106  * Called by:   js api
107  * Input:       no input
108  * Output:      return a string object to js api,if it is NULL means can't get
109  *ip
110  *****************************************************************************/
native_wifi_set_ifconfig(duk_context * ctx)111 static duk_ret_t native_wifi_set_ifconfig(duk_context *ctx)
112 {
113     int ret = -1;
114     netmgr_ifconfig_info_t info;
115 
116     if (!duk_is_object(ctx, 0)) {
117         amp_warn(MOD_STR, "parameter must be object\n");
118         goto out;
119     }
120 
121     /* get device certificate */
122     duk_get_prop_string(ctx, 0, "dhcp_en");
123     duk_get_prop_string(ctx, 0, "ip_addr");
124     duk_get_prop_string(ctx, 0, "mask");
125     duk_get_prop_string(ctx, 0, "gw");
126     duk_get_prop_string(ctx, 0, "dns_server");
127     duk_get_prop_string(ctx, 0, "mac");
128 
129     memcpy(info.ip_addr, duk_get_string(ctx, -5), strlen(duk_get_string(ctx, -5)));
130     memcpy(info.mask, duk_get_string(ctx, -4), strlen(duk_get_string(ctx, -4)));
131     memcpy(info.gw, duk_get_string(ctx, -3), strlen(duk_get_string(ctx, -3)));
132     memcpy(info.dns_server, duk_get_string(ctx, -2), strlen(duk_get_string(ctx, -2)));
133     memcpy(info.mac, duk_get_string(ctx, -1), strlen(duk_get_string(ctx, -1)));
134 
135 
136     ret = aos_wifi_set_ifconfig(&info);
137     if (ret != 0) {
138         amp_debug(MOD_STR, "get wifi info failed");
139     }
140 
141 out:
142     duk_push_int(ctx, ret);
143     return 1;
144 }
145 
146 /*****************************************************************************
147  * Function:    native_wifi_getip
148  * Description: js native addon for WIFI.getip()
149  * Called by:   js api
150  * Input:       no input
151  * Output:      return a string object to js api,if it is NULL means can't get
152  *ip
153  *****************************************************************************/
native_wifi_get_ifconfig(duk_context * ctx)154 static duk_ret_t native_wifi_get_ifconfig(duk_context *ctx)
155 {
156     int ret = -1;
157     aos_wifi_info_t wifi_info;
158 
159     ret = aos_get_wifi_info(&wifi_info);
160     if (ret != 0) {
161         amp_debug(MOD_STR, "get wifi info failed");
162         goto out;
163     }
164 
165     const char *ssid = wifi_info.ssid;
166     const char *ip = wifi_info.ip;
167     const char *mac = wifi_info.mac;
168     int rssi = wifi_info.rssi;
169 
170     duk_push_object(ctx);
171 
172     duk_push_string(ctx, ssid);
173     duk_put_prop_string(ctx, -2, "ssid");
174 
175     duk_push_string(ctx, ip);
176     duk_put_prop_string(ctx, -2, "ip");
177 
178     duk_push_string(ctx, mac);
179     duk_put_prop_string(ctx, -2, "mac");
180 
181     duk_push_int(ctx, rssi);
182     duk_put_prop_string(ctx, -2, "rssi");
183 
184     return 1;
185 
186 out:
187     duk_push_int(ctx, ret);
188     return 1;
189 }
190 
191 /*****************************************************************************
192  * Function:    native_wifi_getssid
193  * Description: js native addon for WIFI.getssid()
194  * Called by:   js api
195  * Input:       no input
196  * Output:      return a string object to js api what the mac is
197  *****************************************************************************/
native_wifi_disconnect(duk_context * ctx)198 static duk_ret_t native_wifi_disconnect(duk_context *ctx)
199 {
200     int ret = -1;
201 
202     ret = aos_wifi_disconnect();
203     if (ret != 0) {
204         amp_debug(MOD_STR, "wifi disconnect failed");
205         goto out;
206     }
207 
208     return 1;
209 out:
210     duk_push_int(ctx, ret);
211     return 1;
212 }
213 
214 /*****************************************************************************
215  * Function:    native_wifi_getssid
216  * Description: js native addon for WIFI.getssid()
217  * Called by:   js api
218  * Input:       no input
219  * Output:      return a string object to js api what the mac is
220  *****************************************************************************/
native_wifi_get_type(duk_context * ctx)221 static duk_ret_t native_wifi_get_type(duk_context *ctx)
222 {
223     int ret = -1;
224 
225     ret = aos_get_network_type();
226 
227 out:
228     duk_push_int(ctx, ret);
229     return 1;
230 }
231 
232 /*****************************************************************************
233  * Function:    native_wifi_getssid
234  * Description: js native addon for WIFI.getssid()
235  * Called by:   js api
236  * Input:       no input
237  * Output:      return a string object to js api what the mac is
238  *****************************************************************************/
native_wifi_get_state(duk_context * ctx)239 static duk_ret_t native_wifi_get_state(duk_context *ctx)
240 {
241     int ret = -1;
242 
243     ret = aos_wifi_disconnect();
244     if (ret != 0) {
245         amp_debug(MOD_STR, "wifi disconnect failed");
246         goto out;
247     }
248 
249     return 1;
250 out:
251     duk_push_int(ctx, ret);
252     return 1;
253 }
254 
module_wifi_register(void)255 void module_wifi_register(void)
256 {
257     duk_context *ctx = be_get_context();
258 
259     duk_push_object(ctx);
260 
261     AMP_ADD_FUNCTION("getType", native_wifi_get_type, 0);
262     AMP_ADD_FUNCTION("setIfConfig", native_wifi_set_ifconfig, 1);
263     AMP_ADD_FUNCTION("getIfConfig", native_wifi_get_ifconfig, 0);
264     AMP_ADD_FUNCTION("connect", native_wifi_connect, 3);
265     AMP_ADD_FUNCTION("disconnect", native_wifi_disconnect, 0);
266     AMP_ADD_FUNCTION("getState", native_wifi_get_state, 0);
267 
268     duk_put_prop_string(ctx, -2, "WIFI");
269 }
270