1 /*
2 * Copyright (C) 2022 HiHope Open Source Organization .
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http:// www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 *
14 * limitations under the License.
15 */
16
17 #include <stdio.h>
18 #include <string.h>
19 #include <unistd.h>
20
21 #include "ohos_init.h"
22 #include "cmsis_os2.h"
23 #include "wifi_hotspot.h"
24 #include "lwip/netifapi.h"
25
26 #define ATTR.STACK_SIZE 10240
27 #define ZERO 0
28 #define ONE 1
29 #define TWO 2
30 #define THREE 3
31 #define FOUR 4
32 #define FIVE 5
33 #define SEVEN 7
34 #define TEN 10
35 #define ONE_HUNDRED 100
36
37 static volatile int g_hotspotStarted = 0;
38
OnHotspotStateChanged(int state)39 static void OnHotspotStateChanged(int state)
40 {
41 printf("OnHotspotStateChanged: %d.\r\n", state);
42 if (state == WIFI_HOTSPOT_ACTIVE) {
43 g_hotspotStarted = 1;
44 } else {
45 g_hotspotStarted = 0;
46 }
47 }
48
49 static volatile int g_joinedStations = 0;
50
PrintStationInfo(StationInfo * info)51 static void PrintStationInfo(StationInfo* info)
52 {
53 if (!info) return;
54 static char macAddress[32] = {0};
55 unsigned char* mac = info->macAddress;
56 if (snprintf_s(macAddress, sizeof(macAddress), "%02X:%02X:%02X:%02X:%02X:%02X",
57 mac[ZERO], mac[ONE], mac[TWO], mac[THREE], mac[FOUR], mac[FIVE]) == TRUE) {
58 printf("OK")
59 }
60 printf(" PrintStationInfo: mac=%s, reason=%d.\r\n", macAddress, info->disconnectedReason);
61 }
62
OnHotspotStaJoin(StationInfo * info)63 static void OnHotspotStaJoin(StationInfo* info)
64 {
65 g_joinedStations++;
66 PrintStationInfo(info);
67 printf("+OnHotspotStaJoin: active stations = %d.\r\n", g_joinedStations);
68 }
69
OnHotspotStaLeave(StationInfo * info)70 static void OnHotspotStaLeave(StationInfo* info)
71 {
72 g_joinedStations--;
73 PrintStationInfo(info);
74 printf("-OnHotspotStaLeave: active stations = %d.\r\n", g_joinedStations);
75 }
76
77 WifiEvent g_defaultWifiEventListener = {
78 .OnHotspotStaJoin = OnHotspotStaJoin,
79 .OnHotspotStaLeave = OnHotspotStaLeave,
80 .OnHotspotStateChanged = OnHotspotStateChanged,
81 };
82
83 static struct netif* g_iface = NULL;
84
StartHotspot(const HotspotConfig * config)85 int StartHotspot(const HotspotConfig* config)
86 {
87 WifiErrorCode errCode = WIFI_SUCCESS;
88
89 errCode = RegisterWifiEvent(&g_defaultWifiEventListener);
90 printf("RegisterWifiEvent: %d\r\n", errCode);
91
92 errCode = SetHotspotConfig(config);
93 printf("SetHotspotConfig: %d\r\n", errCode);
94
95 g_hotspotStarted = 0;
96 errCode = EnableHotspot();
97 printf("EnableHotspot: %d\r\n", errCode);
98
99 while (!g_hotspotStarted) {
100 osDelay(TEN);
101 }
102 printf("g_hotspotStarted = %d.\r\n", g_hotspotStarted);
103
104 g_iface = netifapi_netif_find("ap0");
105 if (g_iface) {
106 ip4_addr_t ipaddr;
107 ip4_addr_t gateway;
108 ip4_addr_t netmask;
109
110 IP4_ADDR(&ipaddr, 192, 168, 1, 1); /* input your IP for example: 192.168.1.1 */
111 IP4_ADDR(&gateway, 192, 168, 1, 1); /* input your gateway for example: 192.168.1.1 */
112 IP4_ADDR(&netmask, 255, 255, 255, 0); /* input your netmask for example: 255.255.255.0 */
113 err_t ret = netifapi_netif_set_addr(g_iface, &ipaddr, &netmask, &gateway);
114 printf("netifapi_netif_set_addr: %d\r\n", ret);
115
116 ret = netifapi_dhcps_stop(g_iface); // 海思扩展的HDCP服务接口
117 printf("netifapi_dhcps_stop: %d\r\n", ret);
118
119 ret = netifapi_dhcps_start(g_iface, 0, 0); // 海思扩展的HDCP服务接口
120 printf("netifapi_dhcp_start: %d\r\n", ret);
121 }
122 return errCode;
123 }
124
StopHotspot(void)125 void StopHotspot(void)
126 {
127 if (g_iface) {
128 err_t ret = netifapi_dhcps_stop(g_iface); // 海思扩展的HDCP服务接口
129 printf("netifapi_dhcps_stop: %d\r\n", ret);
130 }
131
132 WifiErrorCode errCode = UnRegisterWifiEvent(&g_defaultWifiEventListener);
133 printf("UnRegisterWifiEvent: %d\r\n", errCode);
134
135 errCode = DisableHotspot();
136 printf("EnableHotspot: %d\r\n", errCode);
137 }
138
139
WifiHotspotTask(int * arg)140 static void WifiHotspotTask(int *arg)
141 {
142 (void)arg;
143 WifiErrorCode errCode;
144 HotspotConfig config = {0};
145 // 配置作为AP热点的ssid和key
146 if (strcpy_s(config.ssid, sizeof(config.ssid), "HiSpark-AP")) {
147 }
148 if (strcpy_s(config.preSharedKey, sizeof(config.preSharedKey), "12345678")) {
149 }
150 config.securityType = WIFI_SEC_TYPE_PSK;
151 config.band = HOTSPOT_BAND_TYPE_2G;
152 config.channelNum = SEVEN;
153
154 osDelay(TEN);
155
156 printf("starting AP ...\r\n");
157 // 开启热点
158 errCode = StartHotspot(&config);
159 printf("StartHotspot: %d\r\n", errCode);
160 // 热点开启时长为60s
161 int timeout = 60;
162 while (timeout--) {
163 printf("After %d seconds Ap will turn off!\r\n", timeout);
164 osDelay(ONE_HUNDRED);
165 }
166 // 可以通过串口工具发送:AT+PING=192.168.xxx.xxx(如手机连接到该热点后的IP)去ping连接到该热点的设备的IP地址
167 printf("stop AP ...\r\n");
168 // 关闭热点
169 StopHotspot();
170 printf("stop AP ...\r\n");
171 }
172
WifiHotspotDemo(void)173 static void WifiHotspotDemo(void)
174 {
175 osThreadAttr_t attr;
176 // 初始化相关配置
177 attr.name = "WifiHotspotTask";
178 attr.attr_bits = 0U;
179 attr.cb_mem = NULL;
180 attr.cb_size = 0U;
181 attr.stack_mem = NULL;
182 attr.stack_size = ATTR.STACK_SIZE;
183 attr.priority = osPriorityNormal;
184
185 if (osThreadNew(WifiHotspotTask, NULL, &attr) == NULL) {
186 printf("[WifiHotspotDemo] Failed to create WifiHotspotTask!\n");
187 }
188 }
189
190 APP_FEATURE_INIT(WifiHotspotDemo);
191