Compare commits

..

48 Commits

Author SHA1 Message Date
Chaitanya Godavarthi
53ad416396 wifi-2342 wifi-2343: APC BDR/DR swap fix and monitor cloud connection
-Reduced the BDR->DR swap time.
-Monitor the cloud connection and start/stop APC
 based on the connection stability.

Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
2021-05-28 15:40:49 -04:00
Rick Sommerville
ebaa9b25ce WIFI-2416 Auto redirector bug fix (re-enable webserver, manage Maverick)
Signed-off-by: Rick Sommerville <rick.sommerville@netexperience.com>
2021-05-27 23:26:14 -04:00
Rick Sommerville
aea505ddf9 WIFI-2059 Handle br-wan/br-lan ip address conflict
Signed-off-by: Rick Sommerville <rick.sommerville@netexperience.com>
2021-05-27 14:03:26 -04:00
Owen Anderson
94bcfaf93f WIFI-1845: Added functionality to rotate the logs for ovsdb
Signed-off-by: Owen Anderson <owenthomasanderson@gmail.com>
2021-05-27 11:41:40 -04:00
Arif Alam
ed9379af7b WIFI-2426: start radius proxy service independent of ssid profile config
Proxy service is started only if
- Radius_Proxy_Config ovsdb table is present
- APC elects AP as DR

Also fixes WIFI-2377

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
2021-05-26 15:35:56 -04:00
Arif Alam
25e7374680 WIFI-2412: Fix radius client connectivity on OR/BDR
Update proxy config on DR to allow connection from other APs.

Also fixes WIFI-2344.

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
2021-05-26 15:30:18 -04:00
Rick Sommerville
167d2828b0 WIFI-2427 Preserve certs/redirector over factory-reset (minor fix)
Signed-off-by: Rick Sommerville <rick.sommerville@netexperience.com>
2021-05-25 12:32:14 -04:00
Rick Sommerville
e71df5ebe4 WIFI-2427 Preserve certs and redirector over factory-reset
Signed-off-by: Rick Sommerville <rick.sommerville@netexperience.com>
2021-05-25 11:28:41 -04:00
Rick Sommerville
d7b413bd0e WIFI-2416 Automatically DigiCert if no redirector setup
Signed-off-by: Rick Sommerville <rick.sommerville@netexperience.com>
2021-05-22 22:08:59 -04:00
Rick Sommerville
a1ff0f90f6 WIFI-2381 Query DigiCert's API for Redirector's address
Signed-off-by: Max Brenner <xamrennerb@gmail.com>
Signed-off-by: Rick Sommerville <rick.sommerville@netexperience.com>
2021-05-22 10:32:51 -04:00
Yashvardhan
a71436d27c wifi-2069 Fix for vifC not getting applied to vifS
- WM was getting stuck on recvmsg() while receiving netlink event notifications
   Since we are already using event loop to read data as and when it arrives, there was
   no need to keep nl_recvmsgs() in blocking mode for notifications.
   Setting socket to non-blocking mode resolves the issue.
 - Also removed a redundant reload_config call in captive.c.

Signed-off-by: Yashvardhan <yashvardhan@netexperience.com>
2021-05-21 00:06:08 -04:00
Arif Alam
915041e40f WIFI-2379: fix radius proxy config
Remove stale radius proxy config on ovsdb delete.

Signed-off-by: Arif Alam <arif.alam@netexperience.com>

WIFI-2377: check radius proxy service on APC state change

Start or stop radius proxy service as needed on APC state change.

Radius proxy service is only started if:
- AP is elected as a DR (Designated Router) via APC
- radproxy is set to true in vif config custom options for any
  ssid

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
2021-05-19 16:24:15 -04:00
John Crispin
5a5bdac405 ipq807x: fix eap101 leds
The LEDs defined in the dts did not match what UCI expected.

Signed-off-by: John Crispin <john@phrozen.org>
2021-05-19 13:18:22 -04:00
Chaitanya Godavarthi
82e7af0c77 APC:stop apc in case the wan iface is down
stop the APC if the wan interface is down
and start it once it comes up.

Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
2021-05-19 11:56:34 -04:00
ravi vaishnav
d3695266fc Wifi-2382. Fix for STA Assoc rejection with reason code 17
If a previously associated-and-authorized STA comes for a new
connection (Assoc Request), AP rejects the Assoc with code 17.
Solution is to delete the STA entry at AP before re-adding the
STA entry. This clears out the state-machine at the AP and
accepts the new connection from the STA.

Signed-off-by: ravi vaishnav <ravi.vaishnav@netexperience.com>
2021-05-17 23:48:46 -04:00
Chaitanya Godavarthi
d40e1f9d13 APC: relinquish DR/BDR mode on Cloud conn loss
If there is a cloud connectivity loss, we do not
want the AP to be elected as a DR/BDR since that would
mean the APs configuration could mismatch with all the
other APs linked to it.

Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
2021-05-17 23:46:04 -04:00
Chaitanya Godavarthi
acc7a24464 APC: Fix BDR takes place of DR
Raise the priority of BDR in case
when DR is inactive, so that in the
election process BDR is elected as
DR.

Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
2021-05-16 15:23:42 -04:00
John Crispin
327b85b44a ipq807x: add support for the new eap102 version
* import the patch provided by edgecore.

Signed-off-by: John Crispin <john@phrozen.org>
2021-05-16 15:20:17 -04:00
Arif Alam
811f5e60aa WIFI-2346: Fix proxy not initiating radsec connection
Fix server to tls block reference in configuration.

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
2021-05-12 22:18:50 -04:00
Chaitanya Godavarthi
93baf6d334 apc:Fix AP not receiving hello packets
Fix firewall setting not being applied.
return incase the interap socket fails.
Clean up in failure conditions.

Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
2021-05-12 15:38:31 -04:00
Yashvardhan
63f602a136 wifi-2069: Fix opensync vifS synchronization
- Make sure that uci_context used while loading a UCI is exclusive at
   any given time.
 - Some other improvements in the same area.

Signed-off-by: Yashvardhan <yashvardhan@netexperience.com>
2021-05-12 12:22:23 -04:00
Arif Alam
49383f1c01 WIFI-1664: Make some more radius proxy parameters configurable
- Add config parameters for accounting server in non-TLS case
- Allow server port to be configurable
- Fix up multiple realm to server mapping config

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
2021-05-07 18:49:18 -04:00
Owen Anderson
7ac036af0a WIFI-2085: Added logic to assign auto managment rate
Signed-off-by: Owen Anderson <owenthomasanderson@gmail.com>
2021-05-07 10:59:52 -04:00
Arif Alam
666e740e0b WIFI-2088: radsec: fix cert download from filestore
Create cert directory per configured radsec server.

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
2021-05-06 18:48:57 -04:00
ravi vaishnav
58572f81ae WiFi-1826. Add OVSDB params for RRM channel hop config
Adding Noise floor and OBSS related params to the RRM Config
OVSDB table.

Signed-off-by: ravi vaishnav <ravi.vaishnav@netexperience.com>
2021-04-30 18:40:16 -04:00
Arif Alam
0c621a4da1 WIFI-1898: Fix passpoint config parameters
Fixes the following passpoint config params:

- Network Auth Type
- Connection Capability
- IP Address Availability

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
2021-04-30 14:51:48 -04:00
Arif Alam
b0a660ba31 netifd: Add WPA3 Enterprise modes
Add configuration options for:
- WPA3 Enterprise Only mode
- WPA3 Enterprise Transition mode

Fixes: WIFI-1940

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
2021-04-30 14:31:10 -04:00
Chaitanya Godavarthi
5613bbb6f3 APC: Fix memory leaks
Fixed memory leaks in apc and interapcomm modules.

Signed-off-by: Rick Sommerville <rick.sommerville@netexperience.com>
2021-04-30 11:30:24 -04:00
ravi vaishnav
7ec23942a0 WiFi-2072. Populate the right fw version in the AWLAN_Node
Populating the fw version from FW_IMAGE_ACTIVE in the
AWLAN_Node.

Signed-off-by: ravi vaishnav <ravi.vaishnav@netexperience.com>
2021-04-28 14:54:11 -04:00
ravi vaishnav
655d284a8f WiFi-2071. Read model info from manufacturing block
Reading model info from flash. If no info present in flash,
then read it from /tmp/sysinfo/boardname.

Signed-off-by: ravi vaishnav <ravi.vaishnav@netexperience.com>
2021-04-27 15:00:31 -04:00
Chaitanya Godavarthi
593f654d3c opensync: Enable Proxy ARP and mcast to unicast
Add custom options to enable proxy arp and
mcast to ucast, this is used for Hotspot 2.0.
It is tested for ipv4.

Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
2021-04-27 14:57:35 -04:00
Yashvardhan
6021a14426 wifi-2070: Increase CSA count
- Channel switch in case of high interference was failing
   when multiple ssids are configured. Increasing CSA count helps
   all the vifs to reserve context and get ready before CSA can be
   finalized.
 - Log when we detect high interference

Signed-off-by: Yashvardhan <yashvardhan@netexperience.com>
2021-04-26 19:39:13 -04:00
Chaitanya Godavarthi
482cfee8d5 opensync: Fix SM crash during chan switch event
Fix SM crash event during chan switch event due
to global chan switch struct not being freed properly.

Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
2021-04-26 19:32:14 -04:00
Yashvardhan
3fc41fac2c wifi-1738: wifi6: Add missing channel switch event patch
- Channel switch event is generated from hostapd and is sent to cloud
   when AP switches channel due to high signal interference or radar detection.
   The patch was missing in wifi6 hostapd and is added in this commit.

Signed-off-by: Yashvardhan <yashvardhan@netexperience.com>
2021-04-25 22:35:38 -04:00
Yashvardhan
8b5e2058f3 wifi-1727: hostapd: Fix RRM channel switch issues
- Add support for multi-bss channel switch inside ubus switch_chan method
 - Fix hostapd crash occuring while sending channel switch event to cloud.
 - Fix memory leak.

Signed-off-by: Yashvardhan <yashvardhan@netexperience.com>
2021-04-25 14:27:41 -04:00
Arif Alam
5815e883a0 WIFI-2057: Fix current operating channel reporting in radio state table
Poll driver to get current operating channel as part of radio state update.

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
2021-04-24 23:55:29 -04:00
Nagendrababu
cc8e30e1d4 WIFI-1807-Channel-Change
This patch will resolve the channel switching issue when there is a single SSID on each radio

Signed-off-by: Nagendrababu <nagendrababu.bonkuri@connectus.ai>
2021-04-24 22:30:34 -04:00
Chaitanya Godavarthi
e5bc8c9550 opensync: fix Rate-set bug
Fix Rate set bug by deviding the given value by 10, since
the value is given in multiples of 10 by the cloud.
Increase wait time to 20 seconds for the FW to settle
before applying the rate

Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>

ath10k-ct: Fix mcast/bcast/mgt/beacon rate overrides.

Somewhere around 5.7 kernel, mac80211 started setting
mcast/bcast, and ath10k started auto-calculating the
mgt ratecodes.  This was overriding anything a user set through
debugfs.

Instead, have debugfs take precedence in case a user sets
a rate there.

Signed-off-by: Ben Greear <greearb@candelatech.com>
2021-04-23 17:36:57 -04:00
Arif Alam
a91e00337c WIFI-1940: Enable IEEE802.1X with SHA-256 AKM suite for WPA3-Enterprise Only mode
WPA3-Enterprise Only mode requires that the AP enables at least
AKM suite selector 00-0F-AC:5 (IEEE 802.1X with SHA-256) and not
enable AKM suite selector: 00-0F-AC:1 (IEEE 802.1X with SHA-1).

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
2021-04-23 15:24:49 -04:00
ravi vaishnav
b4e20e6289 WiFi-1921. Fix for hostapd error logs when configuring 16 SSID
When configuring 16 VLAN, we see hostapd complaining
about no buffer space available while handling receive
events. Hence, increasing the socket buffer memory size
to 512KB.

Signed-off-by: ravi vaishnav <ravi.vaishnav@netexperience.com>
2021-04-22 20:05:17 -04:00
Arif Alam
dd86dfceb0 opensync: add radsec, radius proxy and apc functionality
- add ovsdb schema for radsec and radius proxy config
- add radsec and radius proxy functionality
- add APC functionality for radsec and radius proxy
  Send APC mode information through ubus
  from APC application to WM.
  Use the APC mode to direct the configuration
  of radius proxy.
  We get this information from APC:
  mode:
	DR (Designated Router)
	BDR (Back up Designated Router)
	OR (Other Router)
	NC (Not connected/Not configured)
  bdr_addr: IP of the BDR
  dr_addr: IP of the DR
  enabled: If Enabled/Disabled

Signed-off-by: Arif Alam <arif.alam@netexperience.com>
Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
2021-04-22 00:44:40 -04:00
Nagendrababu
42a87e7fa4 WIFI-2001-CP-Radius-Auth
This patch will fix the radius MSCHAPv2 authentication failure problem

Signed-off-by: Nagendrababu <nagendrababu.bonkuri@connectus.ai>
2021-04-21 14:22:37 -04:00
ravi vaishnav
315e953110 Wifi-2040. ManufacturingRecord: Populate device mac in qr code.
Adding code to fall-back and read eth0 address incase the
manufacturing data is not present for the id/mac_address field.
The same is also populated in the qr code field of AWLAN_Node.

Signed-off-by: ravi vaishnav <ravi.vaishnav@netexperience.com>
2021-04-20 14:52:23 -04:00
ravi vaishnav
fa5c8b06ef Wifi-1914. Fix for FT-EAP roaming failure.
Adding the required uci options for FT-EAP roaming.

Signed-off-by: ravi vaishnav <ravi.vaishnav@netexperience.com>
2021-04-20 14:03:56 -04:00
ravi vaishnav
5d8ce34973 Wifi-2028. WF194C Serial number changes with every upgrade
This commit will fix changing serial-number on every sysupgrade.
2021-04-19 20:01:53 -04:00
Chaitanya Godavarthi
b717b1361d netifd: Dont renew dhcp on bridge topo change
Do not renew the dhcp on bridge topology change
as this causes some of the dhcp servers to fail.
This occurs when many interfaces are added on to
a bridge and for every interface there is a dhcp
renew. The server considers receiving renew many
times in a quick succession as a DOS attack. So for
now we disable dhcp lease renew when a new interface
is added.

Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
2021-04-19 17:34:16 -04:00
ravi vaishnav
45dcf6a878 Adding manufacturing data to the AWLAN_Node entry.
Tested on ECW5211, EA8300, EC420, and WF188n.

Signed-off-by: ravi vaishnav <ravi.vaishnav@netexperience.com>
2021-04-17 17:43:19 +02:00
Nagendrababu
0fb8809a28 WIFI-2002-Radius-CP-Service-Crash
This Patch will address the radius captive portal service crash problem

Signed-off-by: Nagendrababu <nagendrababu.bonkuri@connectus.ai>
2021-04-12 19:25:27 -04:00
76 changed files with 3459 additions and 293 deletions

View File

@@ -47,8 +47,18 @@ hostapd_append_wpa_key_mgmt() {
[ "${ieee80211w:-0}" -gt 0 ] && append wpa_key_mgmt "WPA-${auth_type_l}-SHA256"
[ "${ieee80211ai:-0}" -gt 0 ] && append wpa_key_mgmt "FILS-SHA256"
;;
eap-only)
append wpa_key_mgmt "WPA-EAP-SHA256"
[ "${ieee80211r:-0}" -gt 0 ] && append wpa_key_mgmt "FT-EAP"
;;
eap-transition)
append wpa_key_mgmt "WPA-EAP"
append wpa_key_mgmt "WPA-EAP-SHA256"
[ "${ieee80211r:-0}" -gt 0 ] && append wpa_key_mgmt "FT-EAP"
;;
eap192)
append wpa_key_mgmt "WPA-EAP-SUITE-B-192"
[ "${ieee80211w:-0}" -gt 0 ] && append wpa_key_mgmt "WPA-EAP-SHA256"
[ "${ieee80211r:-0}" -gt 0 ] && append wpa_key_mgmt "FT-EAP"
;;
eap-eap192)
@@ -311,14 +321,15 @@ hostapd_common_add_bss_config() {
config_add_string osu_ssid hs20_wan_metrics hs20_operating_class hs20_t_c_filename hs20_t_c_timestamp
config_add_boolean interworking internet
config_add_int access_network_type asra esr uesa venue_group venue_type ipaddr_type_availability \
config_add_int access_network_type asra esr uesa venue_group venue_type \
gas_address3
config_add_string hessid network_auth_type \
config_add_string hessid network_auth_type ipaddr_type_availability \
anqp_3gpp_cell_net anqp_elem domain_name qos_map_set hs20_t_c_server_url
config_add_array airtime_sta_weight
config_add_int airtime_bss_weight airtime_bss_limit
config_add_int rts_threshold
config_add_boolean multicast_to_unicast proxy_arp
}
hostapd_set_vlan_file() {
@@ -485,7 +496,8 @@ hostapd_set_bss_options() {
bss_load_update_period chan_util_avg_period sae_require_mfp \
multi_ap multi_ap_backhaul_ssid multi_ap_backhaul_key \
airtime_bss_weight airtime_bss_limit airtime_sta_weight \
rssi_reject_assoc_rssi rssi_ignore_probe_request rts_threshold
rssi_reject_assoc_rssi rssi_ignore_probe_request rts_threshold \
proxy_arp multicast_to_unicast
set_default isolate 0
set_default maxassoc 0
@@ -508,7 +520,8 @@ hostapd_set_bss_options() {
set_default rssi_reject_assoc_rssi 0
set_default rssi_ignore_probe_request 0
set_default rts_threshold -1
set_default proxy_arp 0
set_default multicast_to_unicast 0
append bss_conf "ctrl_interface=/var/run/hostapd"
if [ "$isolate" -gt 0 ]; then
append bss_conf "ap_isolate=$isolate" "$N"
@@ -537,6 +550,9 @@ hostapd_set_bss_options() {
append bss_conf "rssi_ignore_probe_request=$rssi_ignore_probe_request" "$N"
append bss_conf "rts_threshold=$rts_threshold" "$N"
[ -n "$proxy_arp" ] && append bss_conf "proxy_arp=$proxy_arp" "$N"
[ -n "$multicast_to_unicast" ] && append bss_conf "multicast_to_unicast=$multicast_to_unicast" "$N"
[ "$tdls_prohibit" -gt 0 ] && append bss_conf "tdls_prohibit=$tdls_prohibit" "$N"
[ "$wpa" -gt 0 ] && {
@@ -557,11 +573,11 @@ hostapd_set_bss_options() {
}
case "$auth_type" in
sae|owe|eap192|eap-eap192)
sae|owe|eap192|eap-eap192|eap-only)
set_default ieee80211w 2
set_default sae_require_mfp 1
;;
psk-sae)
psk-sae|eap-transition)
set_default ieee80211w 1
set_default sae_require_mfp 1
;;
@@ -603,7 +619,7 @@ hostapd_set_bss_options() {
vlan_possible=1
wps_possible=1
;;
eap|eap192|eap-eap192)
eap|eap192|eap-eap192|eap-only|eap-transition)
json_get_vars \
auth_server auth_secret auth_port \
dae_client dae_secret dae_port \
@@ -940,7 +956,6 @@ hostapd_set_bss_options() {
set_default access_network_type 0
set_default venue_group 0
set_default venue_type 0
set_default ipaddr_type_availability 0
set_default gas_address3 0
set_default hs20_deauth_req_timeout 60
if [ "$hs20" = "1" ]; then
@@ -972,7 +987,7 @@ hostapd_set_bss_options() {
[ "$uesa" -gt 0 ] && append bss_conf "uesa=$uesa" "$N"
[ "$venue_group" -gt 0 ] && append bss_conf "venue_group=$venue_group" "$N"
[ "$venue_type" -gt 0 ] && append bss_conf "venue_type=$venue_type" "$N"
[ "$ipaddr_type_availability" -gt 0 ] && append bss_conf "ipaddr_type_availability=$ipaddr_type_availability" "$N"
[ -n "$ipaddr_type_availability" ] && append bss_conf "ipaddr_type_availability=$ipaddr_type_availability" "$N"
[ "$gas_address3" -gt 0 ] && append bss_conf "gas_address3=$gas_address3" "$N"
[ -n "$hessid" ] && append bss_conf "hessid=$hessid" "$N"
[ -n "$network_auth_type" ] && append bss_conf "network_auth_type=$network_auth_type" "$N"

View File

@@ -0,0 +1,24 @@
--- a/src/ap/ubus.c
+++ b/src/ap/ubus.c
@@ -722,6 +722,7 @@ hostapd_switch_chan(struct ubus_context
struct blob_attr *tb[__CSA_MAX];
struct hostapd_data *hapd = get_hapd_from_object(obj);
struct csa_settings css;
+ int i;
blobmsg_parse(csa_policy, __CSA_MAX, tb, blob_data(msg), blob_len(msg));
@@ -746,9 +747,10 @@ hostapd_switch_chan(struct ubus_context
SET_CSA_SETTING(CSA_VHT, freq_params.vht_enabled, bool);
SET_CSA_SETTING(CSA_BLOCK_TX, block_tx, bool);
-
- if (hostapd_switch_channel(hapd, &css) != 0)
- return UBUS_STATUS_NOT_SUPPORTED;
+ for (i = 0; i < hapd->iface->num_bss; i++) {
+ if (hostapd_switch_channel(hapd->iface->bss[i], &css) != 0)
+ return UBUS_STATUS_NOT_SUPPORTED;
+ }
return UBUS_STATUS_OK;
#undef SET_CSA_SETTING
}

View File

@@ -0,0 +1,186 @@
--- a/src/ap/dfs.c
+++ b/src/ap/dfs.c
@@ -19,7 +19,7 @@
#include "dfs.h"
#include "beacon.h"
#include "eloop.h"
-
+#include "ubus.h"
static int dfs_get_used_n_chans(struct hostapd_iface *iface, int *seg1)
{
@@ -1207,6 +1207,11 @@ static int hostapd_dfs_start_channel_swi
break;
}
+ if (!err) {
+ wpa_printf(MSG_DEBUG, "Reporting DFS event to ubus");
+ hostapd_ubus_handle_channel_switch_event(iface, HOSTAPD_UBUS_DFS_SWITCH, channel->freq);
+ }
+
if (err) {
wpa_printf(MSG_WARNING, "DFS failed to schedule CSA (%d) - trying fallback",
err);
--- a/src/ap/ubus.c
+++ b/src/ap/ubus.c
@@ -29,6 +29,8 @@ static int ctx_ref;
static char** bss_lst = NULL;
static size_t bss_nr = 0;
+static LIST_HEAD(chan_events);
+
static inline struct hapd_interfaces *get_hapd_interfaces_from_object(struct ubus_object *obj)
{
return container_of(obj, struct hapd_interfaces, ubus);
@@ -714,6 +716,42 @@ static int hostapd_sessions(struct ubus_
return 0;
}
+static int hostapd_get_chan_switch_events(struct ubus_context *ctx,
+ struct ubus_object *obj,
+ struct ubus_request_data *req,
+ const char *method,
+ struct blob_attr *msg)
+{
+ void *a = NULL;
+ void *t = NULL;
+ struct hostapd_chan_event_list *entry, *tmp;
+
+ blob_buf_init(&b_ev, 0);
+ a = blobmsg_open_table(&b_ev, "chan_switch_event");
+ list_for_each_entry(entry, &chan_events, list) {
+ t = blobmsg_open_table(&b_ev, "event");
+ blobmsg_add_u32(&b_ev, "radio_name", entry->records.band);
+ blobmsg_add_u32(&b_ev, "reason", entry->records.reason);
+ blobmsg_add_u64(&b_ev, "timestamp", entry->records.ts);
+ blobmsg_add_u32(&b_ev, "frequency", entry->records.freq);
+ blobmsg_close_table(&b_ev, t);
+ }
+
+ blobmsg_close_table(&b_ev, a);
+ ubus_send_reply(ctx, req, b_ev.head);
+
+ /*delete list*/
+
+ if (!list_empty(&chan_events)) {
+ list_for_each_entry_safe(entry, tmp, &chan_events, list) {
+ list_del(&entry->list);
+ free(entry);
+ }
+ }
+
+ return 0;
+}
+
static int
hostapd_switch_chan(struct ubus_context *ctx, struct ubus_object *obj,
struct ubus_request_data *req, const char *method,
@@ -751,6 +789,9 @@ hostapd_switch_chan(struct ubus_context
if (hostapd_switch_channel(hapd->iface->bss[i], &css) != 0)
return UBUS_STATUS_NOT_SUPPORTED;
}
+
+ hostapd_ubus_handle_channel_switch_event(hapd->iface, HOSTAPD_UBUS_HIGH_INTERFERENCE, css.freq_params.freq);
+
return UBUS_STATUS_OK;
#undef SET_CSA_SETTING
}
@@ -1446,6 +1487,7 @@ static const struct ubus_method daemon_m
UBUS_METHOD("config_add", hostapd_config_add, config_add_policy),
UBUS_METHOD("config_remove", hostapd_config_remove, config_remove_policy),
UBUS_METHOD_NOARG("get_bss_list", hostapd_get_bss_list),
+ UBUS_METHOD_NOARG("get_chan_switch_events", hostapd_get_chan_switch_events),
};
static struct ubus_object_type daemon_object_type =
@@ -1509,6 +1551,26 @@ ubus_event_cb(struct ubus_notify_request
ureq->resp = ret;
}
+void hostapd_ubus_handle_channel_switch_event(struct hostapd_iface *iface, int reason,
+ int freq)
+{
+ struct hostapd_chan_event_list *rec = NULL;
+ struct timespec ts;
+ uint64_t timestamp = 0;
+
+ clock_gettime(CLOCK_REALTIME, &ts);
+ timestamp = get_time_in_ms(&ts);
+
+ rec = os_zalloc(sizeof(struct hostapd_chan_event_list));
+
+ rec->records.reason = reason;
+ rec->records.band = iface->freq;
+ rec->records.ts = timestamp;
+ rec->records.freq = freq;
+
+ list_add_tail(&rec->list, &chan_events);
+}
+
int hostapd_ubus_handle_rt_event(struct hostapd_data *hapd,
struct hostapd_ubus_request *req)
{
--- a/src/ap/ubus.h
+++ b/src/ap/ubus.h
@@ -17,9 +17,15 @@ enum hostapd_ubus_event_type {
HOSTAPD_UBUS_DEAUTH_REQ,
HOSTAPD_UBUS_FDATA_REQ,
HOSTAPD_UBUS_IP_REQ,
+ HOSTAPD_UBUS_CHAN_SWITCH,
HOSTAPD_UBUS_TYPE_MAX
};
+enum hostapd_ubus_chan_event_reason {
+ HOSTAPD_UBUS_DFS_SWITCH,
+ HOSTAPD_UBUS_HIGH_INTERFERENCE
+};
+
struct hostapd_ubus_request {
enum hostapd_ubus_event_type type;
const struct ieee80211_mgmt *mgmt_frame;
@@ -40,6 +46,7 @@ struct rrm_measurement_beacon_report;
#include <libubox/avl.h>
#include <libubus.h>
+#include <libubox/list.h>
struct hostapd_ubus_bss {
struct ubus_object obj;
@@ -121,11 +128,24 @@ struct hostapd_event_avl_rec {
struct avl_node avl;
};
+struct channel_switch_event {
+ int band; /* Radio name*/
+ uint8_t reason;
+ uint64_t ts;
+ uint32_t freq;
+};
+
+struct hostapd_chan_event_list {
+ struct channel_switch_event records;
+ struct list_head list;
+};
+
void hostapd_ubus_add_iface(struct hostapd_iface *iface);
void hostapd_ubus_free_iface(struct hostapd_iface *iface);
void hostapd_ubus_add_bss(struct hostapd_data *hapd);
void hostapd_ubus_free_bss(struct hostapd_data *hapd);
-
+void hostapd_ubus_handle_channel_switch_event(struct hostapd_iface *iface,
+ int reason, int channel);
int hostapd_ubus_handle_event(struct hostapd_data *hapd, struct hostapd_ubus_request *req);
int hostapd_ubus_handle_rt_event(struct hostapd_data *hapd, struct hostapd_ubus_request *req);
void hostapd_ubus_notify(struct hostapd_data *hapd, const char *type, const u8 *mac);
@@ -157,6 +177,11 @@ static inline void hostapd_ubus_free_bss
{
}
+static inline void hostapd_ubus_handle_channel_switch_event(struct hostapd_iface *iface,
+ int reason, int channel)
+{
+}
+
static inline int hostapd_ubus_handle_event(struct hostapd_data *hapd, struct hostapd_ubus_request *req)
{
return 0;

View File

@@ -0,0 +1,28 @@
Index: hostapd-2020-06-08-5a8b3662/src/ap/ieee802_11.c
===================================================================
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/ieee802_11.c
+++ hostapd-2020-06-08-5a8b3662/src/ap/ieee802_11.c
@@ -3675,6 +3675,13 @@ static int add_associated_sta(struct hos
* drivers to accept the STA parameter configuration. Since this is
* after a new FT-over-DS exchange, a new TK has been derived, so key
* reinstallation is not a concern for this case.
+ *
+ * If the STA was associated and authorized earlier, but came for a new
+ * connection (!added_unassoc + !reassoc), remove the existing STA entry
+ * so that it can be re-added. This case is rarely seen when the AP could
+ * not receive the deauth/disassoc frame from the STA. And the STA comes
+ * back with new connection within a short period or before the inactive
+ * STA entry is removed from the list.
*/
wpa_printf(MSG_DEBUG, "Add associated STA " MACSTR
" (added_unassoc=%d auth_alg=%u ft_over_ds=%u reassoc=%d authorized=%d ft_tk=%d fils_tk=%d)",
@@ -3688,7 +3695,8 @@ static int add_associated_sta(struct hos
(!(sta->flags & WLAN_STA_AUTHORIZED) ||
(reassoc && sta->ft_over_ds && sta->auth_alg == WLAN_AUTH_FT) ||
(!wpa_auth_sta_ft_tk_already_set(sta->wpa_sm) &&
- !wpa_auth_sta_fils_tk_already_set(sta->wpa_sm)))) {
+ !wpa_auth_sta_fils_tk_already_set(sta->wpa_sm)) ||
+ (!reassoc && (sta->flags & WLAN_STA_AUTHORIZED)))) {
hostapd_drv_sta_remove(hapd, sta->addr);
wpa_auth_sm_event(sta->wpa_sm, WPA_DRV_STA_REMOVED);
set = 0;

View File

@@ -8,8 +8,8 @@ PKG_LICENSE_FILES:=
PKG_SOURCE_URL:=https://github.com/greearb/ath10k-ct.git
PKG_SOURCE_PROTO:=git
PKG_SOURCE_DATE:=2020-08-26
PKG_SOURCE_VERSION:=13319ff0b5dc3c86e8313f49fca583b829878736
PKG_SOURCE_DATE:=2021-05-22b
PKG_SOURCE_VERSION:=54a9ac02f1139596ea4361ebbc3e444955d86cfd
#PKG_MIRROR_HASH:=97cf22a4a57381c7eb7a9b8a8b1e347e9711ce51c89db971b4ab9a35af476ece
# Build the 5.4 ath10k-ct driver version. Other option is "-4.19".

View File

@@ -47,8 +47,18 @@ hostapd_append_wpa_key_mgmt() {
[ "${ieee80211w:-0}" -gt 0 ] && append wpa_key_mgmt "WPA-${auth_type_l}-SHA256"
[ "${ieee80211ai:-0}" -gt 0 ] && append wpa_key_mgmt "FILS-SHA256"
;;
eap-only)
append wpa_key_mgmt "WPA-EAP-SHA256"
[ "${ieee80211r:-0}" -gt 0 ] && append wpa_key_mgmt "FT-EAP"
;;
eap-transition)
append wpa_key_mgmt "WPA-EAP"
append wpa_key_mgmt "WPA-EAP-SHA256"
[ "${ieee80211r:-0}" -gt 0 ] && append wpa_key_mgmt "FT-EAP"
;;
eap192)
append wpa_key_mgmt "WPA-EAP-SUITE-B-192"
[ "${ieee80211w:-0}" -gt 0 ] && append wpa_key_mgmt "WPA-EAP-SHA256"
[ "${ieee80211r:-0}" -gt 0 ] && append wpa_key_mgmt "FT-EAP"
;;
eap-eap192)
@@ -294,15 +304,17 @@ hostapd_common_add_bss_config() {
config_add_string osu_ssid hs20_wan_metrics hs20_operating_class hs20_t_c_filename hs20_t_c_timestamp
config_add_boolean interworking internet
config_add_int access_network_type asra esr uesa venue_group venue_type ipaddr_type_availability \
config_add_int access_network_type asra esr uesa venue_group venue_type \
gas_address3
config_add_string hessid network_auth_type \
config_add_string hessid network_auth_type ipaddr_type_availability \
anqp_3gpp_cell_net anqp_elem domain_name qos_map_set hs20_t_c_server_url
config_add_int airtime_bss_weight airtime_bss_limit
config_add_int rts_threshold
config_add_array radius_auth_req_attr
config_add_array radius_acct_req_attr
config_add_boolean multicast_to_unicast proxy_arp
}
hostapd_set_vlan_file() {
@@ -446,7 +458,8 @@ hostapd_set_bss_options() {
bss_load_update_period chan_util_avg_period sae_require_mfp \
multi_ap multi_ap_backhaul_ssid multi_ap_backhaul_key \
airtime_bss_weight airtime_bss_limit \
rssi_reject_assoc_rssi rssi_ignore_probe_request rts_threshold
rssi_reject_assoc_rssi rssi_ignore_probe_request rts_threshold \
proxy_arp multicast_to_unicast
set_default isolate 0
set_default maxassoc 0
@@ -474,6 +487,9 @@ hostapd_set_bss_options() {
set_default signal_poll_time 5
set_default signal_drop_reason 3
set_default signal_strikes 3
set_default proxy_arp 0
set_default multicast_to_unicast 0
append bss_conf "ctrl_interface=/var/run/hostapd"
if [ "$isolate" -gt 0 ]; then
@@ -507,6 +523,9 @@ hostapd_set_bss_options() {
append bss_conf "signal_strikes=$signal_strikes" "$N"
append bss_conf "signal_drop_reason=$signal_drop_reason" "$N"
[ -n "$proxy_arp" ] && append bss_conf "proxy_arp=$proxy_arp" "$N"
[ -n "$multicast_to_unicast" ] && append bss_conf "multicast_to_unicast=$multicast_to_unicast" "$N"
[ "$tdls_prohibit" -gt 0 ] && append bss_conf "tdls_prohibit=$tdls_prohibit" "$N"
[ "$wpa" -gt 0 ] && {
@@ -529,11 +548,11 @@ hostapd_set_bss_options() {
}
case "$auth_type" in
sae|owe|eap192|eap-eap192)
sae|owe|eap192|eap-eap192|eap-only)
set_default ieee80211w 2
set_default sae_require_mfp 1
;;
psk-sae)
psk-sae|eap-transition)
set_default ieee80211w 1
set_default sae_require_mfp 1
;;
@@ -575,7 +594,7 @@ hostapd_set_bss_options() {
vlan_possible=1
wps_possible=1
;;
eap|eap192|eap-eap192)
eap|eap192|eap-eap192|eap-only|eap-transition)
json_get_vars \
auth_server auth_secret auth_port \
dae_client dae_secret dae_port \
@@ -871,7 +890,6 @@ hostapd_set_bss_options() {
set_default access_network_type 0
set_default venue_group 0
set_default venue_type 0
set_default ipaddr_type_availability 0
set_default gas_address3 0
set_default hs20_deauth_req_timeout 60
if [ "$hs20" = "1" ]; then
@@ -903,7 +921,7 @@ hostapd_set_bss_options() {
[ "$uesa" -gt 0 ] && append bss_conf "uesa=$uesa" "$N"
[ "$venue_group" -gt 0 ] && append bss_conf "venue_group=$venue_group" "$N"
[ "$venue_type" -gt 0 ] && append bss_conf "venue_type=$venue_type" "$N"
[ "$ipaddr_type_availability" -gt 0 ] && append bss_conf "ipaddr_type_availability=$ipaddr_type_availability" "$N"
[ -n "$ipaddr_type_availability" ] && append bss_conf "ipaddr_type_availability=$ipaddr_type_availability" "$N"
[ "$gas_address3" -gt 0 ] && append bss_conf "gas_address3=$gas_address3" "$N"
[ -n "$hessid" ] && append bss_conf "hessid=$hessid" "$N"
[ -n "$network_auth_type" ] && append bss_conf "network_auth_type=$network_auth_type" "$N"

View File

@@ -1,7 +1,5 @@
Index: hostapd-2020-06-08-5a8b3662/src/ap/dfs.c
===================================================================
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/dfs.c
+++ hostapd-2020-06-08-5a8b3662/src/ap/dfs.c
--- a/src/ap/dfs.c
+++ b/src/ap/dfs.c
@@ -18,7 +18,7 @@
#include "drivers/driver.h"
#include "dfs.h"
@@ -23,10 +21,8 @@ Index: hostapd-2020-06-08-5a8b3662/src/ap/dfs.c
if (err) {
wpa_printf(MSG_WARNING, "DFS failed to schedule CSA (%d) - trying fallback",
err);
Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
===================================================================
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/ubus.c
+++ hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
--- a/src/ap/ubus.c
+++ b/src/ap/ubus.c
@@ -29,6 +29,8 @@ static int ctx_ref;
static char** bss_lst = NULL;
static size_t bss_nr = 0;
@@ -36,7 +32,7 @@ Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
static inline struct hapd_interfaces *get_hapd_interfaces_from_object(struct ubus_object *obj)
{
return container_of(obj, struct hapd_interfaces, ubus);
@@ -714,6 +716,43 @@ static int hostapd_sessions(struct ubus_
@@ -714,6 +716,44 @@ static int hostapd_sessions(struct ubus_
return 0;
}
@@ -48,7 +44,7 @@ Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
+{
+ void *a = NULL;
+ void *t = NULL;
+ struct hostapd_chan_event_list *entry;
+ struct hostapd_chan_event_list *entry, *tmp;
+
+ blob_buf_init(&b_ev, 0);
+ a = blobmsg_open_table(&b_ev, "chan_switch_event");
@@ -68,9 +64,10 @@ Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
+ /*delete list*/
+
+ if (!list_empty(&chan_events)) {
+ list_for_each_entry(entry, &chan_events, list)
+ list_for_each_entry_safe(entry, tmp, &chan_events, list)
+ {
+ list_del(&entry->list);
+ free(entry);
+ }
+ }
+
@@ -80,7 +77,7 @@ Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
static int
hostapd_switch_chan(struct ubus_context *ctx, struct ubus_object *obj,
struct ubus_request_data *req, const char *method,
@@ -749,6 +788,9 @@ hostapd_switch_chan(struct ubus_context
@@ -749,6 +789,9 @@ hostapd_switch_chan(struct ubus_context
if (hostapd_switch_channel(hapd, &css) != 0)
return UBUS_STATUS_NOT_SUPPORTED;
@@ -90,7 +87,7 @@ Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
return UBUS_STATUS_OK;
#undef SET_CSA_SETTING
}
@@ -1444,6 +1486,7 @@ static const struct ubus_method daemon_m
@@ -1444,6 +1487,7 @@ static const struct ubus_method daemon_m
UBUS_METHOD("config_add", hostapd_config_add, config_add_policy),
UBUS_METHOD("config_remove", hostapd_config_remove, config_remove_policy),
UBUS_METHOD_NOARG("get_bss_list", hostapd_get_bss_list),
@@ -98,7 +95,7 @@ Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
};
static struct ubus_object_type daemon_object_type =
@@ -1507,6 +1550,28 @@ ubus_event_cb(struct ubus_notify_request
@@ -1507,6 +1551,28 @@ ubus_event_cb(struct ubus_notify_request
ureq->resp = ret;
}
@@ -127,10 +124,8 @@ Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.c
int hostapd_ubus_handle_rt_event(struct hostapd_data *hapd,
struct hostapd_ubus_request *req)
{
Index: hostapd-2020-06-08-5a8b3662/src/ap/ubus.h
===================================================================
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/ubus.h
+++ hostapd-2020-06-08-5a8b3662/src/ap/ubus.h
--- a/src/ap/ubus.h
+++ b/src/ap/ubus.h
@@ -17,9 +17,15 @@ enum hostapd_ubus_event_type {
HOSTAPD_UBUS_DEAUTH_REQ,
HOSTAPD_UBUS_FDATA_REQ,

View File

@@ -0,0 +1,23 @@
--- a/src/ap/ubus.c
+++ b/src/ap/ubus.c
@@ -762,6 +762,7 @@ hostapd_switch_chan(struct ubus_context
struct blob_attr *tb[__CSA_MAX];
struct hostapd_data *hapd = get_hapd_from_object(obj);
struct csa_settings css;
+ int i;
blobmsg_parse(csa_policy, __CSA_MAX, tb, blob_data(msg), blob_len(msg));
@@ -787,8 +788,10 @@ hostapd_switch_chan(struct ubus_context
SET_CSA_SETTING(CSA_BLOCK_TX, block_tx, bool);
- if (hostapd_switch_channel(hapd, &css) != 0)
- return UBUS_STATUS_NOT_SUPPORTED;
+ for (i = 0; i < hapd->iface->num_bss; i++) {
+ if (hostapd_switch_channel(hapd->iface->bss[i], &css) != 0)
+ return UBUS_STATUS_NOT_SUPPORTED;
+ }
hostapd_ubus_handle_channel_switch_event(hapd->iface,HOSTAPD_UBUS_HIGH_INTERFERENCE, css.freq_params.freq);

View File

@@ -0,0 +1,28 @@
Index: hostapd-2020-06-08-5a8b3662/src/ap/ieee802_11.c
===================================================================
--- hostapd-2020-06-08-5a8b3662.orig/src/ap/ieee802_11.c
+++ hostapd-2020-06-08-5a8b3662/src/ap/ieee802_11.c
@@ -3675,6 +3675,13 @@ static int add_associated_sta(struct hos
* drivers to accept the STA parameter configuration. Since this is
* after a new FT-over-DS exchange, a new TK has been derived, so key
* reinstallation is not a concern for this case.
+ *
+ * If the STA was associated and authorized earlier, but came for a new
+ * connection (!added_unassoc + !reassoc), remove the existing STA entry
+ * so that it can be re-added. This case is rarely seen when the AP could
+ * not receive the deauth/disassoc frame from the STA. And the STA comes
+ * back with new connection within a short period or before the inactive
+ * STA entry is removed from the list.
*/
wpa_printf(MSG_DEBUG, "Add associated STA " MACSTR
" (added_unassoc=%d auth_alg=%u ft_over_ds=%u reassoc=%d authorized=%d ft_tk=%d fils_tk=%d)",
@@ -3688,7 +3695,8 @@ static int add_associated_sta(struct hos
(!(sta->flags & WLAN_STA_AUTHORIZED) ||
(reassoc && sta->ft_over_ds && sta->auth_alg == WLAN_AUTH_FT) ||
(!wpa_auth_sta_ft_tk_already_set(sta->wpa_sm) &&
- !wpa_auth_sta_fils_tk_already_set(sta->wpa_sm)))) {
+ !wpa_auth_sta_fils_tk_already_set(sta->wpa_sm)) ||
+ (!reassoc && (sta->flags & WLAN_STA_AUTHORIZED)))) {
hostapd_drv_sta_remove(hapd, sta->addr);
wpa_auth_sm_event(sta->wpa_sm, WPA_DRV_STA_REMOVED);
set = 0;

View File

@@ -11,7 +11,7 @@ include $(INCLUDE_DIR)/package.mk
define Package/apc
SECTION:=base
DEPENDS:=+libev +libinterapcomm
DEPENDS:=+libev +libinterapcomm +libubus +libubox
CATEGORY:=Base system
TITLE:=Access Point Coordinator
endef
@@ -33,5 +33,11 @@ endef
define Package/apc/install
$(INSTALL_DIR) $(1)/usr/bin
$(INSTALL_DATA) $(PKG_BUILD_DIR)/apc $(1)/usr/bin
chmod 0700 $(1)/usr/bin/apc
$(INSTALL_DIR) $(1)/etc/init.d
$(INSTALL_BIN) ./files/apc.init $(1)/etc/init.d/apc
$(INSTALL_DIR) $(1)/etc/config
$(INSTALL_BIN) ./files/apc.config $(1)/etc/config/apc
endef
$(eval $(call BuildPackage,apc))

View File

View File

@@ -0,0 +1,20 @@
#!/bin/sh /etc/rc.common
USE_PROCD=1
START=40
STOP=40
PROG="/usr/bin/apc"
start_service() {
procd_open_instance
echo "Starting APC"
procd_set_param command ${PROG}
procd_set_param respawn
procd_close_instance
}
stop_service() {
echo "Killing APC"
killall -s SIGTERM apc
}

View File

@@ -3,19 +3,21 @@ srcdir ?= .
VPATH ?= $(srcdir)/src
LIBS = -lpthread -lrt -linterapcomm -lev
LIBS = -lpthread -lrt -linterapcomm -lev -lubus -lubox
$(call output,usr/sbin/wc-apc)
CFLAGS += -I./include/ \
-I../include/
CFLAGS += -DUBUS_SUPPORT
CFLAGS += -Wall -g
CFLAGS += -MMD -Wall -g -Wpointer-arith -Wcast-qual -Wshadow \
-Waggregate-return -Wnested-externs -Wstrict-prototypes \
-fno-omit-frame-pointer -g -rdynamic -fexceptions -funwind-tables -funsigned-char
OBJS := apc_main.o \
hello.o iface.o neighbor.o apc.o
hello.o iface.o neighbor.o apc.o ubus.o
all: apc

View File

@@ -262,6 +262,8 @@ struct apc_neighbor
#define APC_IS_DROTHER 4 /* I'm on BCAST or NBMA and I'm not DR */
#define APC_IS_BACKUP 5 /* I'm BDR */
#define APC_IS_DR 6 /* I'm DR */
#define APC_MAX_MODE 7
/* Definitions for interface state machine */
#define ISM_UP 0 /* Interface Up */

View File

@@ -30,4 +30,9 @@ static inline timer * tm_new_set( void (*hook)(struct _timer *), void *data, uns
return t;
}
static inline void tm_free(timer *t)
{
free(t);
}
#endif

View File

@@ -0,0 +1,22 @@
/*
* netifd - network interface daemon
* Copyright (C) 2012 Felix Fietkau <nbd@openwrt.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2
* as published by the Free Software Foundation
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef __NETIFD_UBUS_H
#define __NETIFD_UBUS_H
extern struct ubus_context *ubus_ctx;
int ubus_init();
void ubus_done(void);
#endif

View File

@@ -26,7 +26,8 @@ static void apc_dump( struct proto * P )
static struct proto * apc_init(struct proto_config * c)
{
struct proto * P = mb_allocz(sizeof(struct apc_proto));
printf("apc_init\n");
P->cf = c;
P->debug = c->debug;
P->mrtdump = c->mrtdump;

View File

@@ -21,9 +21,11 @@
#include <nest/apcn.h>
#include <apc.h>
#include <protocol.h>
#include <ubus.h>
static ev_io iac_io;
static ev_timer check_timer;
#include <libubus.h>
static struct uloop_timeout check_timer;
static void check_timer_handler(struct uloop_timeout *timeout);
static unsigned int CheckIp;
static int CheckCount;
@@ -228,8 +230,7 @@ int set_socket(void)
/*************************************/
static void check_timer_handler(struct ev_loop *loop, ev_timer *timer,
int revents)
static void check_timer_handler(struct uloop_timeout *timeout)
{
timers_go();
if (WaitingToReelect)
@@ -252,29 +253,56 @@ static void check_timer_handler(struct ev_loop *loop, ev_timer *timer,
if (CheckIp && (MyIpAddr != CheckIp))
{
printf("IP address changed from %x to %x - restart APC election\n", MyIpAddr, CheckIp);
system("/usr/opensync/bin/ovsh u APC_State dr_addr:=0.0.0.0 bdr_addr:=0.0.0.0 enabled:=false mode:=NC");
uloop_done();
ubus_done();
interap_rcv_close();
exit(0);
}
CheckCount = 0;
if (ApcSpecSaved.IsApc == I_AM_APC)
{
//Radius stuff
}
}
uloop_timeout_set(&check_timer, 1000);
uloop_timeout_add(&check_timer);
}
static void handle_signal(int signo)
{
uloop_done();
ubus_done();
interap_rcv_close();
system("/usr/opensync/bin/ovsh u APC_State dr_addr:=0.0.0.0 bdr_addr:=0.0.0.0 enabled:=false mode:=NC");
}
static void set_signals(void)
{
struct sigaction s;
memset(&s, 0, sizeof(s));
s.sa_handler = handle_signal;
s.sa_flags = 0;
sigaction(SIGINT, &s, NULL);
sigaction(SIGTERM, &s, NULL);
sigaction(SIGPIPE, &s, NULL);
}
extern struct ubus_context *ubus_ctx;
int main(int argc, char *const* argv)
{
struct proto_config c;
struct proto * apc_proto;
struct ev_loop *loop = EV_DEFAULT;
uloop_init();
/*init term signals*/
set_signals();
/*Socket*/
set_socket();
/*Radius stuff*/
printf("Basic MAC\n");
memset(MyBasicMac, 0, 6);
if (get_mac_addr("br-wan", MyBasicMac) == 0) {
printf("APC: br-wan mac:%02X:%02X:%02X:%02X:%02X:%02X\n",
@@ -291,6 +319,7 @@ int main(int argc, char *const* argv)
/*get local ip of br-wan*/
MyIpAddr = 0;
printf("Getting br-wan IP\n");
while(1)
{
GetLocalIpv4Addr((unsigned char *)&MyIpAddr, "br-wan");
@@ -303,9 +332,13 @@ int main(int argc, char *const* argv)
/*listening interAP*/
callback cb = receive_from_socket;
if (interap_recv(IAC_APC_ELECTION_PORT, cb, 1000,
loop, &iac_io) < 0)
NULL, NULL) < 0) {
printf("Error: Failed InterAP receive");
return 1;
}
memset(Timers, 0, sizeof(Timers));
@@ -319,11 +352,15 @@ int main(int argc, char *const* argv)
ApcProto = (struct apc_proto *)apc_proto;
proto_apc.start(apc_proto);
ev_timer_init(&check_timer, check_timer_handler, 1, 1);
check_timer.cb = check_timer_handler;
uloop_timeout_set(&check_timer, 1000);
uloop_timeout_add(&check_timer);
ev_timer_start(loop, &check_timer);
ev_run(loop, 0);
ubus_init();
uloop_run();
uloop_done();
ubus_done();
interap_rcv_close();
return(1);
}

View File

@@ -103,6 +103,7 @@ void apc_send_hello(struct apc_iface * ifa, int kind )
struct apc_hello2_packet ps;
unsigned int length, report = 0;
struct apc_spec ApcSpec;
char dst_ip[16];
if (WaitingToReelect )
return;
@@ -188,8 +189,11 @@ void apc_send_hello(struct apc_iface * ifa, int kind )
else
ApcSpec.FloatIp = ApcSpecSaved.FloatIp;
}
else
else if (ApcSpec.IsApc == I_AM_BAPC )
{
ifa->priority = 0x12;
}
else {
ifa->priority = 0x11;
if ((ApcSpecSaved.IsApc == I_AM_APC) || BackingUpRadius )
{
@@ -202,8 +206,7 @@ void apc_send_hello(struct apc_iface * ifa, int kind )
length += i * sizeof(u32);
printf("HELLO packet sent via %s\n", ifa->ifname );
char *dst_ip = malloc(16);
printf("HELLO packet sent via %s\n", ifa->ifname );
memset(dst_ip, 0, 16);
if ((get_current_ip(dst_ip, IAC_IFACE)) < 0) {
printf("Error: Cannot get IP for %s", IAC_IFACE);

View File

@@ -65,7 +65,7 @@ void apc_iface_chstate(struct apc_iface * ifa, u8 state)
if (state == oldstate)
return;
printf("Interface %s changed state from %s to %s\n",
ifa->ifname, apc_is_names[oldstate], apc_is_names[state]);
@@ -168,7 +168,7 @@ void apc_iface_new( void )
ifa->priority = 0x11;
ifa->drip = MyIpAddr;
ifa->helloint = 4;
ifa->deadint = 16;
ifa->deadint = 12;
ifa->waitint = 16;
ifa->type = APC_IT_BCAST;

View File

@@ -33,11 +33,10 @@ reset_lists(struct apc_proto *p, struct apc_neighbor *n)
{
}
struct apc_neighbor * apc_neighbor_new(struct apc_iface * ifa)
{
struct apc_neighbor * n = mb_allocz(sizeof(struct apc_neighbor));
printf("apc_new_neighbor\n");
n->ifa = ifa;
add_tail(&ifa->neigh_list, NODE n);
n->adj = 0;
@@ -52,7 +51,6 @@ struct apc_neighbor * apc_neighbor_new(struct apc_iface * ifa)
return(n);
}
static void apc_neigh_down(struct apc_neighbor * n)
{
struct apc_iface * ifa = n->ifa;
@@ -60,9 +58,10 @@ static void apc_neigh_down(struct apc_neighbor * n)
rem_node(NODE n);
printf("Neighbor %x on %s removed", n->rid, ifa->ifname );
tm_free(n->inactim);
mb_free(n);
}
/**
* apc_neigh_chstate - handles changes related to new or lod state of neighbor
* @n: APC neighbor
@@ -81,7 +80,8 @@ static void apc_neigh_chstate(struct apc_neighbor * n, u8 state)
return;
printf("Neighbor %x on %s changed state from %s to %s\n",
n->rid, ifa->ifname, apc_ns_names[old_state], apc_ns_names[state] );
n->rid, ifa->ifname, apc_ns_names[old_state],
apc_ns_names[state]);
n->state = state;
@@ -121,7 +121,6 @@ static void apc_neigh_chstate(struct apc_neighbor * n, u8 state)
apc_iface_sm(ifa, ISM_NEICH);
}
/**
* apc_neigh_sm - apc neighbor state machine
* @n: neighor
@@ -218,7 +217,6 @@ void apc_neigh_sm(struct apc_neighbor * n, int event)
}
}
static int can_do_adj(struct apc_neighbor * n)
{
struct apc_iface * ifa = n->ifa;
@@ -257,13 +255,11 @@ static int can_do_adj(struct apc_neighbor * n)
return i;
}
static inline u32 neigh_get_id(struct apc_proto *p, struct apc_neighbor *n)
{
return ipa_to_u32(n->ip);
}
static struct apc_neighbor * elect_bdr( struct apc_proto * p, list nl)
{
struct apc_neighbor *neigh, *n1, *n2;
@@ -271,7 +267,7 @@ static struct apc_neighbor * elect_bdr( struct apc_proto * p, list nl)
n1 = NULL;
n2 = NULL;
WALK_LIST( neigh, nl ) /* First try those decl. themselves */
WALK_LIST( neigh, nl ) /* First try those decl. themselves */
{
nid = neigh_get_id( p, neigh );
@@ -317,7 +313,6 @@ static struct apc_neighbor * elect_bdr( struct apc_proto * p, list nl)
return( n1 );
}
static struct apc_neighbor * elect_dr( struct apc_proto * p, list nl )
{
struct apc_neighbor *neigh, *n;
@@ -351,7 +346,6 @@ static struct apc_neighbor * elect_dr( struct apc_proto * p, list nl )
return( n );
}
/**
* apc_dr_election - (Backup) Designed Router election
* @ifa: actual interface
@@ -450,7 +444,6 @@ void apc_dr_election(struct apc_iface * ifa)
}
}
struct apc_neighbor * find_neigh_by_ip(struct apc_iface * ifa, ip_addr ip)
{
struct apc_neighbor * n;
@@ -463,7 +456,6 @@ struct apc_neighbor * find_neigh_by_ip(struct apc_iface * ifa, ip_addr ip)
return NULL;
}
static void inactivity_timer_hook(struct _timer * tmr)
{
struct apc_neighbor * n = (struct apc_neighbor *) tmr->data;
@@ -490,13 +482,17 @@ static void inactivity_timer_hook(struct _timer * tmr)
n_neigh += 1;
//Radius stuff
BackingUpRadius = 1;
apc_ifa->priority = 0x33;
}
else
apc_ifa->priority = 0x11;
apc_ifa->drip = MyIpAddr;
apc_ifa->priority = 0x11;
apc_ifa->bdrip = 0;
memset(&ApcSpec, 0, sizeof(struct apc_spec));
WaitingToReelect = 12;
WaitingToReelect = 3;
return;
}
printf("Inactivity timer expired for nbr %x on %s", n->rid,

View File

@@ -0,0 +1,211 @@
/* SPDX-License-Identifier: BSD-3-Clause */
#define _GNU_SOURCE
#include <arpa/inet.h>
#include <string.h>
#include <stdio.h>
#include <ev.h>
#include "ubus.h"
#include <libubus.h>
#include <libubox/blobmsg.h>
#include <apc.h>
#include <libubox/uloop.h>
struct ubus_context *ubus_ctx = NULL;
static struct blob_buf b;
static struct blob_buf nb;
timer *notify_timer;
extern struct apc_iface * apc_ifa;
/* Mandatorily Notify APC_State period */
#define APC_NOTIFY_INTERVAL 10
/* Check if any change in APC State and notify period */
#define APC_NOTIFY_CHECK 1
static ip_addr old_drip;
static ip_addr old_bdrip;
static u8 old_state;
static unsigned int ucount = 0;
struct apc_state {
char mode[4];
char dr_addr[17];
char bdr_addr[17];
bool enabled;
} state;
static int
apc_info_handle(struct ubus_context *ctx, struct ubus_object *obj,
struct ubus_request_data *req, const char *method,
struct blob_attr *msg);
static void ubus_reconnect_timer(struct uloop_timeout *timeout);
static struct uloop_timeout reconnect = {
.cb = ubus_reconnect_timer,
};
static void ubus_reconnect_timer(struct uloop_timeout *timeout)
{
if (ubus_reconnect(ubus_ctx, NULL) != 0) {
printf("APC ubus failed to reconnect\n");
uloop_timeout_set(&reconnect, 2000);
return;
}
printf("APC ubus reconnected\n");
#ifdef FD_CLOEXEC
fcntl(ubus_ctx->sock.fd, F_SETFD,
fcntl(ubus_ctx->sock.fd, F_GETFD) | FD_CLOEXEC);
#endif
}
static void ubus_connection_lost(struct ubus_context *ctx)
{
printf("APC ubus connection lost\n");
ubus_reconnect_timer(NULL);
}
static const struct blobmsg_policy apc_policy = {
.name = "info",
.type = BLOBMSG_TYPE_STRING,
};
static struct ubus_method apc_object_methods[] = {
UBUS_METHOD_NOARG("info", apc_info_handle),
};
static struct ubus_object_type apc_object_type =
UBUS_OBJECT_TYPE("apc", apc_object_methods);
static struct ubus_object apc_object = {
.name = "apc",
.type = &apc_object_type,
.methods = apc_object_methods,
.n_methods = ARRAY_SIZE(apc_object_methods),
};
static int
apc_info_handle(struct ubus_context *ctx, struct ubus_object *obj,
struct ubus_request_data *req, const char *method,
struct blob_attr *msg)
{
blob_buf_init(&b, 0);
blobmsg_add_string(&b, "mode", state.mode);
blobmsg_add_string(&b, "dr_addr", state.dr_addr);
blobmsg_add_string(&b, "bdr_addr", state.bdr_addr);
blobmsg_add_u8(&b, "enabled", state.enabled);
ubus_notify(ctx, &apc_object, "apc", b.head, -1);
ubus_send_event(ctx, "apc", b.head);
ubus_send_reply(ctx, req, b.head);
return 0;
}
static char apc_mode[APC_MAX_MODE][8] = {"DOWN", "LOOP", "WT", "PTP", "OR", "BDR", "DR"};
int apc_update_state(void)
{
struct in_addr dr_addr;
struct in_addr bdr_addr;
ip_addr cur_drip;
ip_addr cur_bdrip;
u8 cur_state;
cur_drip = apc_ifa->drip;
cur_bdrip = apc_ifa->bdrip;
cur_state = apc_ifa->state;
ucount++;
if (cur_drip == old_drip &&
cur_bdrip == old_bdrip &&
cur_state == old_state && ucount < APC_NOTIFY_INTERVAL) {
return -1;
}
printf("APC State update %u", ucount);
ucount = 0;
dr_addr.s_addr = htonl(cur_drip);
bdr_addr.s_addr = htonl(cur_bdrip);
state.enabled = true;
if ((cur_state == APC_IS_DR) ||
(cur_state == APC_IS_BACKUP) ||
(cur_state == APC_IS_DROTHER)) {
snprintf(state.mode, sizeof(state.mode), "%s",
&apc_mode[cur_state][0]);
snprintf(state.dr_addr, sizeof(state.dr_addr),
"%s", inet_ntoa(dr_addr));
snprintf(state.bdr_addr, sizeof(state.bdr_addr),
"%s", inet_ntoa(bdr_addr));
} else if (apc_ifa->state == APC_IS_WAITING) {
snprintf(state.mode, sizeof(state.mode), "%s",
&apc_mode[cur_state][0]);
snprintf(state.dr_addr, sizeof(state.dr_addr), "0.0.0.0");
snprintf(state.bdr_addr, sizeof(state.bdr_addr), "0.0.0.0");
} else {
snprintf(state.mode, sizeof(state.mode), "NC");
snprintf(state.dr_addr, sizeof(state.dr_addr), "0.0.0.0");
snprintf(state.bdr_addr, sizeof(state.bdr_addr), "0.0.0.0");
}
old_drip = cur_drip;
old_bdrip = cur_bdrip;
old_state = cur_state;
return 0;
}
void apc_send_notification(struct _timer * tmr)
{
int ustate = 0;
ustate = apc_update_state();
if(ustate != 0)
return;
printf("APC send ubus notification\n");
blob_buf_init(&nb, 0);
blobmsg_add_string(&nb, "mode", state.mode);
blobmsg_add_string(&nb, "dr_addr", state.dr_addr);
blobmsg_add_string(&nb, "bdr_addr", state.bdr_addr);
blobmsg_add_u8(&nb, "enabled", state.enabled);
ubus_notify(ubus_ctx, &apc_object, "apc", nb.head, -1);
}
static void add_object(struct ubus_object *obj)
{
int ret = ubus_add_object(ubus_ctx, obj);
if (ret != 0)
fprintf(stderr, "Add object fail '%s': %s\n",
obj->name, ubus_strerror(ret));
}
int
ubus_init(void) {
ubus_ctx = ubus_connect(NULL);
if (!ubus_ctx)
return -EIO;
ubus_add_uloop(ubus_ctx);
#ifdef FD_CLOEXEC
fcntl(ubus_ctx->sock.fd, F_SETFD,
fcntl(ubus_ctx->sock.fd, F_GETFD) | FD_CLOEXEC);
#endif
add_object(&apc_object);
notify_timer = tm_new_set(apc_send_notification, NULL,
0, APC_NOTIFY_CHECK);
if (notify_timer) {
printf("APC Start state check and notify timer\n");
tm_start(notify_timer, APC_NOTIFY_CHECK);
}
ubus_ctx->connection_lost = ubus_connection_lost;
return 0;
}
void
ubus_done(void)
{
ubus_free(ubus_ctx);
}

View File

@@ -11,6 +11,7 @@ include $(INCLUDE_DIR)/package.mk
define Package/libinterapcomm
SECTION:=libs
DEPENDS:=+libev +libubox +libubus
CATEGORY:=Libraries
TITLE:=Inter AP communication library
endef
@@ -29,5 +30,8 @@ endef
define Package/libinterapcomm/install
$(INSTALL_DIR) $(1)/usr/lib
$(INSTALL_DATA) $(PKG_BUILD_DIR)/libinterapcomm.so $(1)/usr/lib/
$(INSTALL_DIR) $(1)/etc/init.d
$(INSTALL_BIN) ./files/interap.init $(1)/etc/init.d/interap
endef
$(eval $(call BuildPackage,libinterapcomm))

View File

@@ -0,0 +1,35 @@
#!/bin/sh /etc/rc.common
START=12
STOP=12
start() {
apc=`cat /etc/config/firewall | grep Allow-APC`
ucc=`cat /etc/config/firewall | grep Allow-UCC`
if [ -z "$apc" ]; then
uci add firewall rule
uci set firewall.@rule[-1].name='Allow-APC'
uci set firewall.@rule[-1].src='wan'
uci set firewall.@rule[-1].proto='udp'
uci set firewall.@rule[-1].dst_port='50010'
uci set firewall.@rule[-1].target='ACCEPT'
uci set firewall.@rule[-1].family='ipv4'
uci commit firewall
fi
if [ -z "$ucc" ]; then
uci add firewall rule
uci set firewall.@rule[-1].name='Allow-UCC'
uci set firewall.@rule[-1].src='wan'
uci set firewall.@rule[-1].proto='udp'
uci set firewall.@rule[-1].dst_port='50000'
uci set firewall.@rule[-1].target='ACCEPT'
uci set firewall.@rule[-1].family='ipv4'
uci commit firewall
fi
}
stop() {
echo stop
}

View File

@@ -6,7 +6,7 @@ subdirs=src/test
CFLAGS += -O -Wall -Werror -Wshadow
CFLAGS += -I./include/
LIBS = -lev
LIBS = -lev -lubox -lubus
all: $(LIBNAME) $(subdirs)

View File

@@ -5,6 +5,7 @@ int interap_send(unsigned short port, char *dst_ip,
int interap_recv(unsigned short port, int (*recv_cb)(void *, ssize_t),
unsigned int len, struct ev_loop *loop,
ev_io *io);
void interap_rcv_close(void);
typedef int (*callback)(void *, ssize_t);
typedef struct recv_arg {

View File

@@ -7,12 +7,31 @@
#include <string.h>
#include <unistd.h>
#include <interAPcomm.h>
#include <libubox/uloop.h>
/*Receiver socket*/
int recv_sock = -1;
recv_arg ra;
static void receive_data_uloop(struct uloop_fd *fd, unsigned int events)
{
void *recv_data;
ssize_t recv_data_len;
recv_data = malloc(ra.len);
memset(recv_data, 0, ra.len);
if ((recv_data_len = recvfrom(recv_sock, recv_data, ra.len,
0, NULL, 0)) < 0) {
printf("recvfrom() failed");
return;
}
ra.cb(recv_data, recv_data_len);
free(recv_data);
}
static void receive_data(struct ev_loop *ev, ev_io *io, int event)
{
void *recv_data;
@@ -25,11 +44,14 @@ static void receive_data(struct ev_loop *ev, ev_io *io, int event)
printf("recvfrom() failed");
ra.cb(recv_data, recv_data_len);
free(recv_data);
}
int interap_recv(unsigned short port, int (*recv_cb)(void *, ssize_t), unsigned int len,
struct ev_loop *loop, ev_io *io)
static struct uloop_fd server;
int interap_recv(unsigned short port, int (*recv_cb)(void *, ssize_t),
unsigned int len, struct ev_loop *loop, ev_io *io)
{
struct sockaddr_in addr;
int bcast_perm;
@@ -65,12 +87,25 @@ int interap_recv(unsigned short port, int (*recv_cb)(void *, ssize_t), unsigned
}
printf("Interap recving: p:%d\n", port);
ev_io_init(io, receive_data, recv_sock, EV_READ);
ev_io_start(loop, io);
if (io && loop) {
ev_io_init(io, receive_data, recv_sock, EV_READ);
ev_io_start(loop, io);
} else {
server.cb = receive_data_uloop;
server.fd = recv_sock;
uloop_fd_add(&server, ULOOP_READ);
}
return 0;
}
void interap_rcv_close(void)
{
close(recv_sock);
}
int interap_send(unsigned short port, char *dst_ip, void *data,
unsigned int len)
{

View File

@@ -3,7 +3,7 @@ OBJS = interapcommtest.o
CFLAGS += -Wall $(EXTRA_CFLAGS) $(extra_cflags-y)
LIBS = -L ../../ -linterapcomm -lev
LIBS = -L ../../ -linterapcomm -lev -lubox -lubus
CFLAGS += -I. \
-I../../include/

View File

@@ -6,6 +6,8 @@
#include <ev.h>
#include <interAPcomm.h>
#include <libubus.h>
struct my_data {
int x;
char y;
@@ -13,7 +15,8 @@ struct my_data {
};
int recv_process(void *data) {
int recv_process(void *data, ssize_t n)
{
struct my_data *dat = (struct my_data*) data;
printf("Recv process: %d, %c, %d\n", dat->x, dat->y, dat->z);
@@ -22,34 +25,37 @@ int recv_process(void *data) {
int main (int argc, char *argv[ ])
{
unsigned int send = atoi(argv[1]); /* First arg: broadcast port */
unsigned short port = 50000;
unsigned int send = atoi(argv[1]);
unsigned short port = 50020;
// char *dst_ip = "255.255.255.255";
char *dst_ip = "192.168.9.255";
char *dst_ip = "10.42.0.255";
// char *data = "InterAP Hello";
struct my_data data;
data.x = 1001;
data.y = 'H';
data.z = 3003;
// callback cb = recv_process;
printf("arg1 = %d\n", send);
printf("send = %d\n", send);
if (send) {
printf("Send");
interap_send(port, dst_ip, &data, sizeof(data));
while (1)
{
sleep(3);
printf("Sending...\n");
interap_send(port, dst_ip, &data, sizeof(data));
}
}
else {
printf("Recieve");
// interap_recv(port, cb, sizeof(struct my_data));
uloop_init();
callback cb = recv_process;
interap_recv(port, cb, sizeof(struct my_data), NULL, NULL);
uloop_run();
uloop_done();
}
while (1)
{
sleep(3);
printf("In while loop\n");
}
return 1;
}

View File

@@ -0,0 +1,7 @@
#!/bin/sh
if="$(uci get network.wan.ifname)"
[ "$(cat /sys/class/net/"${if}"/carrier)" = 0 ] && {
return 0
}
return 1

View File

@@ -0,0 +1,4 @@
#!/bin/sh
tar czf /sysupgrade.tgz /usr/opensync/certs/
jffs2reset -r -y -k

View File

@@ -1,12 +1,49 @@
#!/bin/sh
if [ $# -ne 1 ] ; then
echo "Usage: $0 <redirector address>" >&2
exit 1
AP_PRIVATE_KEY_FILE="/usr/opensync/certs/client_dec.key"
AP_CERTIFICATE_FILE="/usr/opensync/certs/client.pem"
AP_DEVICE_ID_FILE="/usr/opensync/certs/client_deviceid.txt"
DIGICERT_API_URI="clientauth.one.digicert.com"
if [ "$1" = "-h" ]; then
echo "Usage: $0 [redirector address]" >&2
exit 1
fi
redirector_addr=$1
# Query DigiCert's API if redirector wasn't specified
if [ -z "$1" ]; then
if [ ! -f "$AP_DEVICE_ID_FILE" ]; then
echo "Device ID file $AP_DEVICE_ID_FILE does not exist. Make sure to create it or specify the redirector address manually."
exit 1
fi
digicert_device_id=`cat ${AP_DEVICE_ID_FILE}`
device_data=`curl -s \
--retry 5 \
--show-error \
--key "${AP_PRIVATE_KEY_FILE}" \
--cert "${AP_CERTIFICATE_FILE}" \
"https://${DIGICERT_API_URI}/iot/api/v2/device/${digicert_device_id}"`
controller_url=`echo ${device_data} | jsonfilter -e '@.fields[@.name="Redirector"].value'`
if [ -z "$controller_url" ]; then
echo "No redirector found for this device"
exit 1
fi
controller_port=`echo ${controller_url} | cut -s -d ":" -f2)`
if [ -z "$controller_port" ]; then
redirector_addr="ssl:${controller_url}:6643"
else
redirector_addr="ssl:${controller_url}"
fi
else
redirector_addr=$1
fi
echo "${redirector_addr}" > /usr/opensync/certs/redirector.txt
/etc/init.d/uhttpd enable
/etc/init.d/uhttpd start
uci set system.tip.redirector="${redirector_addr}"
uci set system.tip.deployed=0
uci commit system
/etc/init.d/opensync restart

View File

@@ -10,11 +10,11 @@ hwmode=$(uci get wireless.${radio}.hwmode)
[ "${hwmode}" = "11a" ] && band=5 || band=2
bcn_rate=$(uci get wireless.${DEVICENAME}.bcn_rate)
bcn_rate=$(($(uci get wireless.${DEVICENAME}.bcn_rate)/10))
mcast_rate=$(uci get wireless.${DEVICENAME}.mcast_rate)
# ath10k rate-codes: 0x43 1M, 0x42 2M, 0x41 5.5M, 0x40 11M, 0x3 6M, 0x7 9M, 0x2 12M, 0x6 18M, 0x1 24M, 0x5 36M, 0x0 48M, 0x4 54M, 0xFF default
rate_codes="1:0x43 2:0x42 5.5:0x41 11:0x40 6:0x3 9:0x7 12:0x2 18:0x6 24:0x1 36:0x5 48:0x0 54:0x4"
rate_codes="1:0x43 2:0x42 5:0x41 11:0x40 6:0x3 9:0x7 12:0x2 18:0x6 24:0x1 36:0x5 48:0x0 54:0x4"
# Default codes
beacon_code=0xFF
@@ -33,6 +33,6 @@ done
# set rates
logger -t hotplug "Set Tx rates for device ${DEVICENAME}"
sleep 5
sleep 20
echo "${DEVICENAME} beacon ${band} ${beacon_code}" > /sys/kernel/debug/ieee80211/${phy}/ath10k/set_rates
echo "${DEVICENAME} mcast ${band} ${mcast_code}" > /sys/kernel/debug/ieee80211/${phy}/ath10k/set_rates

View File

@@ -0,0 +1,10 @@
/tmp/log/openvswitch/* {
daily
rotate 5
size 1M
compress
delaycompress
dateext
dateformat -%d%m%Y
notifempty
}

View File

@@ -0,0 +1,143 @@
Index: opensync-2.0.5.0/interfaces/opensync.ovsschema
===================================================================
--- opensync-2.0.5.0.orig/interfaces/opensync.ovsschema
+++ opensync-2.0.5.0/interfaces/opensync.ovsschema
@@ -9368,6 +9368,69 @@
}
},
"isRoot": true
+ },
+ "APC_Config": {
+ "columns": {
+ "enabled": {
+ "type": {
+ "key": {
+ "type": "boolean"
+ },
+ "min": 0,
+ "max": 1
+ }
+ }
+ },
+ "isRoot": true,
+ "maxRows": 1
+ },
+ "APC_State": {
+ "columns": {
+ "dr_addr": {
+ "type": {
+ "key": {
+ "type": "string"
+ }
+ }
+ },
+ "bdr_addr": {
+ "type": {
+ "key": {
+ "type": "string"
+ }
+ }
+ },
+ "enabled": {
+ "type": {
+ "key": {
+ "type": "boolean"
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "mode": {
+ "type": {
+ "key": {
+ "type": "string",
+ "enum": [
+ "set",
+ [
+ "DR",
+ "BDR",
+ "OR",
+ "WT",
+ "NC"
+ ]
+ ]
+ },
+ "min": 0,
+ "max": 1
+ }
+ }
+ },
+ "isRoot": true,
+ "maxRows": 1
}
}
}
Index: opensync-2.0.5.0/platform/openwrt/src/lib/target/src/radio_ubus.c
===================================================================
--- opensync-2.0.5.0.orig/platform/openwrt/src/lib/target/src/radio_ubus.c
+++ opensync-2.0.5.0/platform/openwrt/src/lib/target/src/radio_ubus.c
@@ -10,6 +10,7 @@
extern struct ev_loop *wifihal_evloop;
static struct ubus_context *ubus;
extern struct ev_loop *wifihal_evloop;
+extern void apc_state_set(struct blob_attr *msg);
int hapd_rrm_enable(char *name, int neighbor, int beacon)
{
@@ -179,6 +180,7 @@ radio_ubus_add_vif_cb(struct ubus_contex
return UBUS_STATUS_OK;
}
+
static const struct ubus_method radio_ubus_methods[] = {
UBUS_METHOD("dbg_add_vif", radio_ubus_add_vif_cb, add_vif_policy),
UBUS_METHOD("dummy", radio_ubus_dummy_cb, dummy_policy),
@@ -201,8 +203,36 @@ static void radio_ubus_connect(struct ub
ubus_add_object(ubus, &radio_ubus_object);
}
+static int radio_ubus_notify(struct ubus_context *ctx, struct ubus_object *obj,
+ struct ubus_request_data *req, const char *method,
+ struct blob_attr *msg)
+{
+ char *str;
+
+ str = blobmsg_format_json(msg, true);
+ LOGD("ubus: Received ubus notify '%s': %s\n", method, str);
+ free(str);
+
+ if (!strncmp(method, "apc", 3)) {
+ LOGD("APC notification Received");
+ apc_state_set(msg);
+ }
+
+ return 0;
+}
+
+
+
static struct ubus_instance ubus_instance = {
.connect = radio_ubus_connect,
+ .notify = radio_ubus_notify,
+ .list = {
+ {
+ .path = "apc",
+ },
+ },
+ .len = 1,
+
};
int radio_ubus_init(void)
Index: opensync-2.0.5.0/src/lib/schema/inc/schema_consts.h
===================================================================
--- opensync-2.0.5.0.orig/src/lib/schema/inc/schema_consts.h
+++ opensync-2.0.5.0/src/lib/schema/inc/schema_consts.h
@@ -154,6 +154,7 @@ typedef enum {
#define SCHEMA_CONSTS_DISABLE_B_RATES "disable_b_rates"
#define SCHEMA_CONSTS_IEEE80211k "ieee80211k"
#define SCHEMA_CONSTS_DYNAMIC_VLAN "dynamic_vlan"
+#define SCHEMA_CONSTS_RADPROXY "radproxy"
/* radio Custom options */
#define SCHEMA_CONSTS_LOCAL_PWR_CONSTRAINT "local_pwr_constraint"

View File

@@ -0,0 +1,270 @@
Index: opensync-2.0.5.0/interfaces/opensync.ovsschema
===================================================================
--- opensync-2.0.5.0.orig/interfaces/opensync.ovsschema
+++ opensync-2.0.5.0/interfaces/opensync.ovsschema
@@ -199,6 +199,59 @@
"type": "integer"
}
}
+ },
+ "qr_code": {
+ "type": {
+ "key": "string",
+ "value": {
+ "type": "string",
+ "maxLength": 128
+ },
+ "min": 0,
+ "max": "unlimited"
+ }
+ },
+ "model_description": {
+ "type": {
+ "key": {
+ "type": "string"
+ }
+ }
+ },
+ "manufacturer_name": {
+ "type": {
+ "key": {
+ "type": "string"
+ }
+ }
+ },
+ "manufacturer_date": {
+ "type": {
+ "key": {
+ "type": "string"
+ }
+ }
+ },
+ "manufacturer_url": {
+ "type": {
+ "key": {
+ "type": "string"
+ }
+ }
+ },
+ "reference_design": {
+ "type": {
+ "key": {
+ "type": "string"
+ }
+ }
+ },
+ "certification_region": {
+ "type": {
+ "key": {
+ "type": "string"
+ }
+ }
}
},
"isRoot": true,
Index: opensync-2.0.5.0/src/lib/target/inc/target.h
===================================================================
--- opensync-2.0.5.0.orig/src/lib/target/inc/target.h
+++ opensync-2.0.5.0/src/lib/target/inc/target.h
@@ -332,6 +332,115 @@ bool target_hw_revision_get(void *buff,
*/
bool target_platform_version_get(void *buff, size_t buffsz);
+/**
+ * @brief Return device model revision
+ *
+ * This function provides a null terminated byte string containing the
+ * model revision. The model revision is a part of AWLAN_Node table.
+ *
+ * @param buff pointer to a string buffer
+ * @param buffsz size of string buffer
+ * @return true on success
+ */
+bool target_model_revision_get(void *buff, size_t buffsz);
+
+/**
+ * @brief Return device model description
+ *
+ * This function provides a null terminated byte string containing the
+ * model description. The model description is a part of AWLAN_Node table.
+ *
+ * @param buff pointer to a string buffer
+ * @param buffsz size of string buffer
+ * @return true on success
+ */
+bool target_model_description_get(void *buff, size_t buffsz);
+
+/**
+ * @brief Return device manufacturer name
+ *
+ * This function provides a null terminated byte string containing the
+ * manufacturer name. The manufacturer name is a part of AWLAN_Node table.
+ *
+ * @param buff pointer to a string buffer
+ * @param buffsz size of string buffer
+ * @return true on success
+ */
+bool target_manuf_name_get(void *buff, size_t buffsz);
+
+/**
+ * @brief Return device manufacturer date
+ *
+ * This function provides a null terminated byte string containing the
+ * manufacturer date. The manufacturer date is a part of AWLAN_Node table.
+ *
+ * @param buff pointer to a string buffer
+ * @param buffsz size of string buffer
+ * @return true on success
+ */
+bool target_manuf_date_get(void *buff, size_t buffsz);
+
+/**
+ * @brief Return device manufacturer url
+ *
+ * This function provides a null terminated byte string containing the
+ * manufacturer url. The manufacturer url is a part of AWLAN_Node table.
+ *
+ * @param buff pointer to a string buffer
+ * @param buffsz size of string buffer
+ * @return true on success
+ */
+bool target_manuf_url_get(void *buff, size_t buffsz);
+
+/**
+ * @brief Return device manufacturer name abbreviation
+ *
+ * This function provides a null terminated byte string containing the
+ * manufacturer name abbreviation. This is one of the pieces that form
+ * the QR code entry which is a part of AWLAN_Node table.
+ *
+ * @param buff pointer to a string buffer
+ * @param buffsz size of string buffer
+ * @return true on success
+ */
+bool target_manuf_abbr_get(void *buff, size_t buffsz);
+
+/**
+ * @brief Return device reference design
+ *
+ * This function provides a null terminated byte string containing the
+ * reference design. The reference design is a part of AWLAN_Node table.
+ *
+ * @param buff pointer to a string buffer
+ * @param buffsz size of string buffer
+ * @return true on success
+ */
+bool target_ref_design_get(void *buff, size_t buffsz);
+
+/**
+ * @brief Return device certification region
+ *
+ * This function provides a null terminated byte string containing the
+ * certification region. The certification region is a part of AWLAN_Node table.
+ *
+ * @param buff pointer to a string buffer
+ * @param buffsz size of string buffer
+ * @return true on success
+ */
+bool target_cert_region_get(void *buff, size_t buffsz);
+
+/**
+ * @brief Return device mac address
+ *
+ * This function provides a null terminated byte string containing the
+ * mac address. The mac address is a part of AWLAN_Node table.
+ *
+ * @param buff pointer to a string buffer
+ * @param buffsz size of string buffer
+ * @return true on success
+ */
+bool target_mac_addr_get(void *buff, size_t buffsz);
+
/// @} LIB_TARGET_ENTITY
/// @defgroup LIB_TARGET_MAP Interface Mapping API
Index: opensync-2.0.5.0/src/dm/src/dm_ovsdb.c
===================================================================
--- opensync-2.0.5.0.orig/src/dm/src/dm_ovsdb.c
+++ opensync-2.0.5.0/src/dm/src/dm_ovsdb.c
@@ -326,7 +326,7 @@ void fill_entity_data(struct schema_AWLA
s_awlan_node->sku_number_exists = true;
}
- if (true == target_hw_revision_get(buff, sizeof(buff)))
+ if (true == target_model_revision_get(buff, sizeof(buff)))
{
STRSCPY(s_awlan_node->revision, buff);
}
@@ -359,6 +359,58 @@ void fill_entity_data(struct schema_AWLA
}
s_awlan_node->model_exists = true;
+ if (true == target_model_description_get(buff, sizeof(buff)))
+ {
+ STRSCPY(s_awlan_node->model_description, buff);
+ s_awlan_node->model_description_exists = true;
+ }
+
+ if (true == target_manuf_name_get(buff, sizeof(buff)))
+ {
+ STRSCPY(s_awlan_node->manufacturer_name, buff);
+ s_awlan_node->manufacturer_name_exists = true;
+ }
+
+ if (true == target_manuf_date_get(buff, sizeof(buff)))
+ {
+ STRSCPY(s_awlan_node->manufacturer_date, buff);
+ s_awlan_node->manufacturer_date_exists = true;
+ }
+
+ if (true == target_manuf_url_get(buff, sizeof(buff)))
+ {
+ STRSCPY(s_awlan_node->manufacturer_url, buff);
+ s_awlan_node->manufacturer_url_exists = true;
+ }
+
+ if (true == target_ref_design_get(buff, sizeof(buff)))
+ {
+ STRSCPY(s_awlan_node->reference_design, buff);
+ s_awlan_node->reference_design_exists = true;
+ }
+
+ if (true == target_cert_region_get(buff, sizeof(buff)))
+ {
+ STRSCPY(s_awlan_node->certification_region, buff);
+ s_awlan_node->certification_region_exists = true;
+ }
+
+ if (true == target_mac_addr_get(buff, sizeof(buff)))
+ {
+ STRSCPY(s_awlan_node->id, buff);
+ s_awlan_node->id_exists = true;
+ }
+
+ SCHEMA_KEY_VAL_APPEND(s_awlan_node->qr_code, "DT", "AP");
+ SCHEMA_KEY_VAL_APPEND(s_awlan_node->qr_code, "DM", s_awlan_node->id);
+ if (true == target_manuf_abbr_get(buff, sizeof(buff)))
+ {
+ SCHEMA_KEY_VAL_APPEND(s_awlan_node->qr_code, "VN", buff);
+ }
+ SCHEMA_KEY_VAL_APPEND(s_awlan_node->qr_code, "SN", s_awlan_node->serial_number);
+ SCHEMA_KEY_VAL_APPEND(s_awlan_node->qr_code, "MN", s_awlan_node->model);
+ SCHEMA_KEY_VAL_APPEND(s_awlan_node->qr_code, "HW", s_awlan_node->revision);
+
LOG(NOTICE, "Device entity {serial=%s id=%s version=%s platform=%s sku=%s}",
s_awlan_node->serial_number,
s_awlan_node->id,
@@ -422,6 +474,13 @@ bool act_update_entity (void)
"sku_number",
"upgrade_status",
"upgrade_timer",
+ "qr_code",
+ "model_description",
+ "manufacturer_name",
+ "manufacturer_date",
+ "manufacturer_url",
+ "reference_design",
+ "certification_region",
NULL)
);

View File

@@ -0,0 +1,140 @@
--- a/interfaces/opensync.ovsschema
+++ b/interfaces/opensync.ovsschema
@@ -9492,6 +9492,137 @@
},
"isRoot": true,
"maxRows": 1
+ },
+ "Radius_Proxy_Config": {
+ "columns": {
+ "radius_config_name": {
+ "type": {
+ "key": {
+ "type": "string"
+ },
+ "min": 1,
+ "max": 1
+ }
+ },
+ "radsec": {
+ "type": {
+ "key": {
+ "type": "boolean"
+ },
+ "min": 1,
+ "max": 1
+ }
+ },
+ "server": {
+ "type": {
+ "key": {
+ "type": "string"
+ },
+ "min": 1,
+ "max": 1
+ }
+ },
+ "port": {
+ "type": {
+ "key": {
+ "type": "integer"
+ },
+ "min": 1,
+ "max": 1
+ }
+ },
+ "secret": {
+ "type": {
+ "key": {
+ "type": "string"
+ },
+ "min": 1,
+ "max": 1
+ }
+ },
+ "acct_server": {
+ "type": {
+ "key": {
+ "type": "string"
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "acct_port": {
+ "type": {
+ "key": {
+ "type": "integer"
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "acct_secret": {
+ "type": {
+ "key": {
+ "type": "string"
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "ca_cert": {
+ "type": {
+ "key": {
+ "type": "string",
+ "minLength": 1,
+ "maxLength": 256
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "client_cert": {
+ "type": {
+ "key": {
+ "type": "string",
+ "minLength": 1,
+ "maxLength": 256
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "client_key": {
+ "type": {
+ "key": {
+ "type": "string",
+ "minLength": 1,
+ "maxLength": 256
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "passphrase": {
+ "type": {
+ "key": {
+ "type": "string",
+ "minLength": 0,
+ "maxLength": 128
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "realm": {
+ "type": {
+ "key": {
+ "type": "string",
+ "maxLength": 256
+ },
+ "min": 0,
+ "max": 16
+ }
+ }
+ },
+ "isRoot": true
}
}
}

View File

@@ -0,0 +1,13 @@
Index: opensync-2.0.5.0/src/lib/schema/inc/schema_consts.h
===================================================================
--- opensync-2.0.5.0.orig/src/lib/schema/inc/schema_consts.h
+++ opensync-2.0.5.0/src/lib/schema/inc/schema_consts.h
@@ -155,6 +155,8 @@ typedef enum {
#define SCHEMA_CONSTS_IEEE80211k "ieee80211k"
#define SCHEMA_CONSTS_DYNAMIC_VLAN "dynamic_vlan"
#define SCHEMA_CONSTS_RADPROXY "radproxy"
+#define SCHEMA_CONSTS_PROXY_ARP "proxy_arp"
+#define SCHEMA_CONSTS_MCAST_TO_UCAST "mcast_to_ucast"
/* radio Custom options */
#define SCHEMA_CONSTS_LOCAL_PWR_CONSTRAINT "local_pwr_constraint"

View File

@@ -0,0 +1,34 @@
Index: opensync-2.0.5.0/src/lib/datapipeline/src/dppline.c
===================================================================
--- opensync-2.0.5.0.orig/src/lib/datapipeline/src/dppline.c
+++ opensync-2.0.5.0/src/lib/datapipeline/src/dppline.c
@@ -652,8 +652,8 @@ static bool dppline_copysts(dppline_stat
dst->u.events.client_event_qty++;
}
- size = dst->u.events.client_event_qty * sizeof(dpp_event_record_session_t);
- dst->u.events.client_event_list = calloc(1, size);
+ int size_cl = dst->u.events.client_event_qty * sizeof(dpp_event_record_session_t);
+ dst->u.events.client_event_list = calloc(1, size_cl);
int count = 0;
ds_dlist_foreach(&report_data->client_event_list, result)
{
@@ -671,8 +671,8 @@ static bool dppline_copysts(dppline_stat
dst->u.events.channel_event_qty++;
}
- size = dst->u.events.channel_event_qty * sizeof(dpp_event_record_channel_switch_t);
- dst->u.events.channel_event_list = calloc(1, size);
+ int size_ch = dst->u.events.channel_event_qty * sizeof(dpp_event_record_channel_switch_t);
+ dst->u.events.channel_event_list = calloc(1, size_ch);
ds_dlist_foreach(&report_data->channel_switch_list, channel_result)
{
assert(count < (int)dst->u.events.channel_event_qty);
@@ -680,6 +680,7 @@ static bool dppline_copysts(dppline_stat
sizeof(dpp_event_record_channel_switch_t));
count++;
}
+ size = size_cl + size_ch;
} break;

View File

@@ -0,0 +1,66 @@
Index: opensync-2.0.5.0/interfaces/opensync.ovsschema
===================================================================
--- opensync-2.0.5.0.orig/interfaces/opensync.ovsschema
+++ opensync-2.0.5.0/interfaces/opensync.ovsschema
@@ -8982,6 +8982,61 @@
"min": 0,
"max": 1
}
+ },
+ "noise_floor_thresh": {
+ "type": {
+ "key": {
+ "type": "integer",
+ "minInteger": -90,
+ "maxInteger": -10
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "noise_floor_time": {
+ "type": {
+ "key": {
+ "type": "integer",
+ "minInteger": 60,
+ "maxInteger": 600
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "non_wifi_thresh": {
+ "type": {
+ "key": {
+ "type": "integer",
+ "minInteger": 0,
+ "maxInteger": 100
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "non_wifi_time": {
+ "type": {
+ "key": {
+ "type": "integer",
+ "minInteger": 60,
+ "maxInteger": 600
+ },
+ "min": 0,
+ "max": 1
+ }
+ },
+ "obss_hop_mode": {
+ "type": {
+ "key": {
+ "type": "integer",
+ "minInteger": 1,
+ "maxInteger": 2
+ },
+ "min": 0,
+ "max": 1
+ }
}
},
"isRoot": true

View File

@@ -37,6 +37,20 @@ start_service() {
echo "Setting certificates"
mkdir -p ${CERTS_DEST_PATH}
cp ${CERTS_SRC_PATH}/* ${CERTS_DEST_PATH}/
echo "Checking Redirector"
redirector=$(uci get system.tip.redirector)
if [ -z "$redirector" ]; then
[[ -f /usr/opensync/certs/redirector.txt ]] && redirector=$(cat /usr/opensync/certs/redirector.txt | tr -d '\r\n')
if [ -z "$redirector" ]; then
logger -t opensync "Contacting DigiCert for redirector address"
wlan_ap_redirector.sh
else
logger -t opensync "Restoring redirector ${redirector} after factory reset"
wlan_ap_redirector.sh ${redirector}
fi
fi
[[ -f /usr/opensync/certs/redirector.txt ]] || echo "${redirector}" > /usr/opensync/certs/redirector.txt
echo "Starting OpenSync"
procd_set_param command ${PROG}
procd_close_instance

View File

@@ -215,6 +215,7 @@ pid_t cmd_handler_tcpdump_wifi(struct task *task)
char *argv[] = { "/usr/sbin/tcpdump", "-c", "1000", "-G", duration, "-W", "1", "-w", pcap, "-i", phy, NULL };
char iw[128];
pid_t pid;
int ret = 0;
task->arg = SCHEMA_KEY_VAL(task->conf.payload, "wifi");
if (!task->arg) {
@@ -225,15 +226,23 @@ pid_t cmd_handler_tcpdump_wifi(struct task *task)
blob_buf_init(&b, 0);
uci = uci_alloc_context();
uci_load(uci, "wireless", &p);
s = uci_lookup_section(uci, p, task->arg);
if (!s) {
task_status(task, TASK_FAILED, "unknown wifi");
ret = uci_load(uci, "wireless", &p);
if (ret) {
LOGE("%s: uci_load() failed with rc %d", __func__, ret);
uci_free_context(uci);
return -1;
return -1;
}
s = uci_lookup_section(uci, p, task->arg);
if (!s) {
task_status(task, TASK_FAILED, "unknown wifi");
uci_unload(uci, p);
uci_free_context(uci);
return -1;
}
uci_to_blob(&b, s, &phy_param);
uci_to_blob(&b, s, &phy_param);
uci_unload(uci, p);
uci_free_context(uci);
blobmsg_parse(phy_policy, __PHY_ATTR_MAX, tb, blob_data(b.head), blob_len(b.head));

View File

@@ -88,9 +88,14 @@ static void syslog_state(int config)
struct uci_element *e = NULL;
struct uci_section *s = NULL;
char val[128];
int ret = 0;
blob_buf_init(&b, 0);
uci_load(uci, "system", &system);
ret = uci_load(uci, "system", &system);
if (ret) {
LOGE("%s: uci_load() failed with rc %d", __func__, ret);
return;
}
uci_foreach_element(&system->sections, e) {
s = uci_to_section(e);
if (!strcmp(s->type, "system"))
@@ -179,14 +184,20 @@ static void ntp_state(int config)
struct uci_section *s;
struct blob_attr *cur = NULL;
char val[128] = {};
int first = 1, rem = 0;
int first = 1, rem = 0, ret = 0;
blob_buf_init(&b, 0);
uci_load(uci, "system", &p);
ret = uci_load(uci, "system", &p);
if (ret) {
LOGE("%s: uci_load() failed with rc %d", __func__, ret);
return;
}
s = uci_lookup_section(uci, p, "ntp");
if (!s)
if (!s) {
uci_unload(uci, p);
return;
}
uci_to_blob(&b, s, &ntp_param);
blobmsg_parse(ntp_policy, __NTP_ATTR_MAX, tb, blob_data(b.head), blob_len(b.head));

View File

@@ -21,4 +21,6 @@ extern int hapd_rrm_set_neighbors(char *name, struct rrm_neighbor *neigh, int co
extern void radio_maverick(void *arg);
int nl80211_channel_get(char *name, unsigned int *chan);
#endif

View File

@@ -0,0 +1,38 @@
/* SPDX-License-Identifier: BSD-3-Clause */
#ifndef RADIUS_PROXY_H_INCLUDED
#define RADIUS_PROXY_H_INCLUDED
#include <stdbool.h>
#include <jansson.h>
#include <ev.h>
#include <sys/time.h>
#include <syslog.h>
#include "log.h"
#include "os_nif.h"
#include "target.h"
#include "dppline.h"
#include "os.h"
#include "util.h"
#include "ovsdb.h"
#include "ovsdb_update.h"
#include "ovsdb_sync.h"
#include "ovsdb_table.h"
#include "ovsdb_cache.h"
#include "schema.h"
#include "target.h"
#include "utils.h"
#include <libubox/list.h>
#include <evsched.h>
extern ovsdb_table_t table_Radius_Proxy_Config;
void callback_Radius_Proxy_Config(ovsdb_update_monitor_t *mon,
struct schema_Radius_Proxy_Config *old, struct schema_Radius_Proxy_Config *conf);
#endif /* RADIUS_PROXY_H_INCLUDED */

View File

@@ -13,6 +13,7 @@ struct mode_map {
char *ucihwmode;
char *htmode;
char *ucihtmode;
int sec_channel_offset;
};
extern struct mode_map *mode_map_get_uci(const char *band, const char *htmode, const char *hwmode);
@@ -20,6 +21,7 @@ extern struct mode_map *mode_map_get_cloud(const char *htmode, const char *hwmod
extern int vif_get_mac(char *vap, char *mac);
extern int vif_is_ready(const char *name);
bool vif_get_key_for_key_distr(const char *secret, char *key_str);
#define blobmsg_add_bool blobmsg_add_u8
extern int blobmsg_add_hex16(struct blob_buf *buf, const char *name, uint16_t val);
@@ -38,4 +40,5 @@ extern int iface_is_up(const char *ifname);
extern int net_get_mtu(char *iface);
extern int net_get_mac(char *iface, char *mac);
extern int net_is_bridge(char *iface);
extern char* get_max_channel_bw_channel(int channel_freq, const char* htmode);
#endif

View File

@@ -37,5 +37,6 @@ void vif_hs20_update(struct schema_Hotspot20_Config *hs2conf);
void vif_hs20_osu_update(struct schema_Hotspot20_OSU_Providers *hs2osuconf);
void vif_hs20_icon_update(struct schema_Hotspot20_Icon_Config *hs2iconconf);
void vif_section_del(char *section_name);
void vif_check_radius_proxy(void);
#endif

View File

@@ -46,6 +46,7 @@ UNIT_SRC_TOP += $(OVERRIDE_DIR)/src/sysupgrade.c
UNIT_SRC_TOP += $(OVERRIDE_DIR)/src/dhcpdiscovery.c
UNIT_SRC_TOP += $(OVERRIDE_DIR)/src/radius_probe.c
UNIT_SRC_TOP += $(OVERRIDE_DIR)/src/rrm_config.c
UNIT_SRC_TOP += $(OVERRIDE_DIR)/src/radius_proxy.c
CONFIG_USE_KCONFIG=y
CONFIG_INET_ETH_LINUX=y

View File

@@ -258,12 +258,8 @@ void vif_state_captive_portal_options_get(struct schema_Wifi_VIF_State *vstate)
} else if (!strcmp(opt, "authentication")) {
if(tc[NDS_ATTR_AUTHENTICATION]) {
buf = blobmsg_get_string(tc[NDS_ATTR_AUTHENTICATION]);
if (!strcmp(buf, "None")) {
if (!strcmp(buf, "None") || !strcmp(buf, "username") || !strcmp(buf, "radius")) {
set_captive_portal_state(vstate, &index,
captive_portal_options_table[i],
buf);
} else if (!strcmp(buf,"username")) {
set_captive_portal_state(vstate, &index,
captive_portal_options_table[i],
buf);
@@ -505,26 +501,30 @@ void opennds_parameters(char *ifname)
void opennds_section_del(char *section_name)
{
struct uci_package *opennds;
struct uci_context *nds_ctx;
struct uci_element *e = NULL, *tmp = NULL;
int ret=0;
int ret = 0;
ret= uci_load(uci, "opennds", &opennds);
nds_ctx = uci_alloc_context();
ret = uci_load(nds_ctx, "opennds", &opennds);
if (ret) {
LOGD("%s: uci_load() failed with rc %d", section_name, ret);
LOGE("%s: %s uci_load() failed with rc %d", section_name, __func__, ret);
uci_free_context(nds_ctx);
return;
}
uci_foreach_element_safe(&opennds->sections, tmp, e) {
struct uci_section *s = uci_to_section(e);
if (!strcmp(s->e.name, section_name)) {
uci_section_del(uci, "vif", "opennds", (char *)s->e.name, section_name);
uci_section_del(nds_ctx, "vif", "opennds", (char *)s->e.name, section_name);
}
else {
continue;
}
}
uci_commit(uci, &opennds, false);
uci_unload(uci, opennds);
reload_config = 1;
uci_commit(nds_ctx, &opennds, false);
uci_unload(nds_ctx, opennds);
uci_free_context(nds_ctx);
}
void vif_captive_portal_set(const struct schema_Wifi_VIF_Config *vconf, char *ifname)
@@ -596,7 +596,7 @@ void vif_captive_portal_set(const struct schema_Wifi_VIF_Config *vconf, char *if
blobmsg_add_string(&cap, "enabled", "1");
blobmsg_add_string(&cap, "gatewayinterface","br-lan");
blobmsg_add_string(&cap, "preauth", "/usr/lib/opennds/radius.sh");
ipset_create(ifname);
ipset_create("opennds");
d = blobmsg_open_array(&cap, "preauthenticated_users");
blobmsg_add_string(&cap, NULL, ipset_tcp80);
blobmsg_add_string(&cap, NULL, ipset_tcp443);
@@ -616,8 +616,12 @@ void vif_captive_portal_set(const struct schema_Wifi_VIF_Config *vconf, char *if
else if (strcmp(opt, "radius_server_secret") == 0)
blobmsg_add_string(&cap, "radius_server_secret", value);
else if (strcmp(opt, "radius_auth_type") == 0)
blobmsg_add_string(&cap, "radius_auth_type", value);
else if (strcmp(opt, "radius_auth_type") == 0) {
if(!strcmp(value, "MSCHAPv2"))
blobmsg_add_string(&cap, "radius_auth_type", "MSCHAPV2");
else
blobmsg_add_string(&cap, "radius_auth_type", value);
}
else if (strcmp(opt, "session_timeout") == 0)
blobmsg_add_string(&cap, "sessiontimeout", value);

View File

@@ -26,10 +26,17 @@
#include "captive.h"
#include "rrm_config.h"
#include "vlan.h"
#include "radius_proxy.h"
ovsdb_table_t table_Hotspot20_Config;
ovsdb_table_t table_Hotspot20_OSU_Providers;
ovsdb_table_t table_Hotspot20_Icon_Config;
ovsdb_table_t table_Radius_Proxy_Config;
ovsdb_table_t table_APC_Config;
ovsdb_table_t table_APC_State;
unsigned int radproxy_apc = 0;
extern json_t* ovsdb_table_where(ovsdb_table_t *table, void *record);
static struct uci_package *wireless;
struct uci_context *uci;
@@ -72,7 +79,7 @@ static const struct blobmsg_policy wifi_device_policy[__WDEV_ATTR_MAX] = {
[WDEV_ATTR_RX_ANTENNA] = { .name = "rxantenna", .type = BLOBMSG_TYPE_INT32 },
[WDEV_ATTR_FREQ_BAND] = { .name = "freq_band", .type = BLOBMSG_TYPE_STRING },
[WDEV_AATR_CHANNELS] = {.name = "channels", .type = BLOBMSG_TYPE_ARRAY},
[WDEV_ATTR_DISABLE_B_RATES] = { .name = "legacy_rates", .type = BLOBMSG_TYPE_BOOL },
[WDEV_ATTR_DISABLE_B_RATES] = { .name = "legacy_rates", .type = BLOBMSG_TYPE_BOOL },
[WDEV_ATTR_MAXASSOC_CLIENTS] = { .name = "maxassoc", .type = BLOBMSG_TYPE_INT32 },
[WDEV_ATTR_LOCAL_PWR_CONSTRAINT] = { .name = "local_pwr_constraint", .type = BLOBMSG_TYPE_INT32 },
};
@@ -186,7 +193,7 @@ static bool radio_state_update(struct uci_section *s, struct schema_Wifi_Radio_C
struct schema_Wifi_Radio_State rstate;
char phy[6];
int antenna;
int32_t chan;
uint32_t chan = 0;
LOGT("%s: get state", s->e.name);
@@ -211,7 +218,7 @@ static bool radio_state_update(struct uci_section *s, struct schema_Wifi_Radio_C
}
if (tb[WDEV_ATTR_CHANNEL]) {
chan = get_current_channel(phy);
nl80211_channel_get(phy, &chan);
if(chan)
SCHEMA_SET_INT(rstate.channel, chan);
else
@@ -401,8 +408,9 @@ bool target_radio_config_set2(const struct schema_Wifi_Radio_Config *rconf,
}
if ((changed->ht_mode) || (changed->hw_mode) || (changed->freq_band)) {
struct mode_map *m = mode_map_get_uci(rconf->freq_band, rconf->ht_mode,
rconf->hw_mode);
int channel_freq;
channel_freq = ieee80211_channel_to_frequency(rconf->channel);
struct mode_map *m = mode_map_get_uci(rconf->freq_band, get_max_channel_bw_channel(channel_freq, rconf->ht_mode), rconf->hw_mode);
if (m) {
blobmsg_add_string(&b, "htmode", m->ucihtmode);
blobmsg_add_string(&b, "hwmode", m->ucihwmode);
@@ -439,6 +447,7 @@ static void periodic_task(void *arg)
{
static int counter = 0;
struct uci_element *e = NULL, *tmp = NULL;
int ret = 0;
if ((counter % 15) && !reload_config)
goto done;
@@ -455,16 +464,19 @@ static void periodic_task(void *arg)
}
if (reload_config) {
LOGT("periodic: reload config");
LOGD("periodic: reload_config");
reload_config = 0;
uci_commit_all(uci);
sync();
system("reload_config");
}
LOGT("periodic: start state update ");
uci_load(uci, "wireless", &wireless);
LOGD("periodic: start state update ");
ret = uci_load(uci, "wireless", &wireless);
if (ret) {
LOGE("%s: uci_load() failed with rc %d", __func__, ret);
return;
}
uci_foreach_element_safe(&wireless->sections, tmp, e) {
struct uci_section *s = uci_to_section(e);
@@ -479,7 +491,7 @@ static void periodic_task(void *arg)
vif_state_update(s, NULL);
}
uci_unload(uci, wireless);
LOGT("periodic: stop state update ");
LOGD("periodic: stop state update ");
done:
counter++;
@@ -669,6 +681,259 @@ static void callback_Hotspot20_Icon_Config(ovsdb_update_monitor_t *mon,
}
enum {
WIF_APC_ENABLE,
__WIF_APC_MAX,
};
static const struct blobmsg_policy apc_enpolicy[__WIF_APC_MAX] = {
[WIF_APC_ENABLE] = { .name = "enabled", BLOBMSG_TYPE_BOOL },
};
const struct uci_blob_param_list apc_param = {
.n_params = __WIF_APC_MAX,
.params = apc_enpolicy,
};
void APC_config_update(struct schema_APC_Config *conf)
{
struct blob_buf apcb = { };
struct uci_context *apc_uci;
apc_uci = uci_alloc_context();
blob_buf_init(&apcb, 0);
if (conf && conf->enabled == true) {
blobmsg_add_bool(&apcb, "enabled", 1);
system("/etc/init.d/apc start");
} else {
blobmsg_add_bool(&apcb, "enabled", 0);
system("/etc/init.d/apc stop");
}
blob_to_uci_section(apc_uci, "apc", "apc", "apc",
apcb.head, &apc_param, NULL);
uci_commit_all(apc_uci);
uci_free_context(apc_uci);
}
static void callback_APC_Config(ovsdb_update_monitor_t *mon,
struct schema_APC_Config *old,
struct schema_APC_Config *conf)
{
if (mon->mon_type == OVSDB_UPDATE_DEL)
APC_config_update(NULL);
else
APC_config_update(conf);
}
static void callback_APC_State(ovsdb_update_monitor_t *mon,
struct schema_APC_State *old,
struct schema_APC_State *conf)
{
LOGN("APC_state: enabled:%s dr_addr:%s bdr_addr:%s mode:%s",
(conf->enabled_changed)? "changed":"unchanged",
(conf->dr_addr_changed)? "changed":"unchanged",
(conf->bdr_addr_changed)? "changed":"unchanged",
(conf->mode_changed)? "changed":"unchanged");
/* APC changed: if radproxy enabled then restart wireless */
if (radproxy_apc) {
radproxy_apc = 0;
system("ubus call service event '{\"type\": \"config.change\", \"data\": { \"package\": \"wireless\" }}'");
}
/* APC changed: start / stop radius proxy service if needed */
vif_check_radius_proxy();
}
struct schema_APC_State apc_state;
enum {
APC_ATTR_MODE,
APC_ATTR_DR_ADDR,
APC_ATTR_BDR_ADDR,
APC_ATTR_ENABLED,
__APC_ATTR_MAX,
};
static const struct blobmsg_policy apc_policy[__APC_ATTR_MAX] = {
[APC_ATTR_MODE] = { .name = "mode", .type = BLOBMSG_TYPE_STRING },
[APC_ATTR_DR_ADDR] = { .name = "dr_addr", .type = BLOBMSG_TYPE_STRING },
[APC_ATTR_BDR_ADDR] = { .name = "bdr_addr", .type = BLOBMSG_TYPE_STRING },
[APC_ATTR_ENABLED] = { .name = "enabled", .type = BLOBMSG_TYPE_BOOL },
};
struct schema_APC_Config apc_conf;
void apc_state_set(struct blob_attr *msg)
{
struct blob_attr *tb[__APC_ATTR_MAX] = { };
blobmsg_parse(apc_policy, __APC_ATTR_MAX, tb,
blob_data(msg), blob_len(msg));
if (tb[APC_ATTR_MODE]) {
LOGD("APC mode: %s", blobmsg_get_string(tb[APC_ATTR_MODE]));
SCHEMA_SET_STR(apc_state.mode,
blobmsg_get_string(tb[APC_ATTR_MODE]));
}
if (tb[APC_ATTR_DR_ADDR]) {
LOGD("APC dr-addr: %s", blobmsg_get_string(tb[APC_ATTR_DR_ADDR]));
SCHEMA_SET_STR(apc_state.dr_addr,
blobmsg_get_string(tb[APC_ATTR_DR_ADDR]));
}
if (tb[APC_ATTR_BDR_ADDR]) {
LOGD("APC bdr-addr: %s", blobmsg_get_string(tb[APC_ATTR_BDR_ADDR]));
SCHEMA_SET_STR(apc_state.bdr_addr,
blobmsg_get_string(tb[APC_ATTR_BDR_ADDR]));
}
if (tb[APC_ATTR_ENABLED]) {
LOGD("APC enabled: %d", blobmsg_get_bool(tb[APC_ATTR_ENABLED]));
if (blobmsg_get_bool(tb[APC_ATTR_ENABLED])) {
SCHEMA_SET_INT(apc_state.enabled, true);
}
else {
SCHEMA_SET_INT(apc_state.enabled, false);
}
}
LOGI("APC_state Updating: mode: %s, dr-addr: %s bdr-addr: %s",
apc_state.mode, apc_state.dr_addr, apc_state.bdr_addr);
if (!ovsdb_table_update(&table_APC_State, &apc_state))
LOG(ERR, "APC_state: failed to update");
}
static ovsdb_table_t table_Manager;
static int conn_since = 0;
#define APC_CLOUD_MON_PERIOD 60
static void apc_enable(bool flag) {
SCHEMA_SET_INT(apc_conf.enabled, flag);
if (!ovsdb_table_update(&table_APC_Config, &apc_conf)) {
LOG(ERR, "%s:APC_Config: failed to update", __func__);
return;
}
LOGI("APC %s: %s APC", __func__, flag?"enable":"disable");
}
static void
apc_cld_mon_cb(struct schema_Manager *mgr)
{
int i = 0;
conn_since = 0;
struct schema_APC_State apc_state;
json_t *where;
int ret = 0;
int link = 1;
where = ovsdb_table_where(&table_APC_State, &apc_state);
if (false == ovsdb_table_select_one_where(&table_APC_State,
where, &apc_state)) {
LOG(ERR, "%s: APC_State read failed", __func__);
return;
}
/*Checks if wan ethernet port is down and disables apc*/
ret = system("/bin/check_wan_link.sh");
if (WIFEXITED(ret)) {
LOGI("The return value: %d\n", WEXITSTATUS(ret));
link = WEXITSTATUS(ret);
if (link == 0) {
apc_enable(false);
return;
}
}
/*if cloud conn is false then disable apc*/
if (mgr->is_connected == false) {
apc_enable(false);
}
else {
for(i=0; i < mgr->status_len; i++) {
if(!strncmp(mgr->status_keys[i] , "sec_since_connect",
strlen("sec_since_connect"))) {
conn_since = atoi(mgr->status[i]);
LOGI("conn_since: %d", conn_since);
break;
}
}
/*if the APC was stopped earlier, start it if connection good
* for atleast 60 secs*/
if (!apc_state.enabled && conn_since > APC_CLOUD_MON_PERIOD) {
apc_enable(true);
}
}
}
/*Monitor the cloud connection*/
static void callback_Manager(ovsdb_update_monitor_t *mon,
struct schema_Manager *old,
struct schema_Manager *conf)
{
switch (mon->mon_type)
{
case OVSDB_UPDATE_NEW:
case OVSDB_UPDATE_MODIFY:
apc_cld_mon_cb(conf);
break;
case OVSDB_UPDATE_DEL:
apc_enable(false);
break;
default:
break;
}
return;
}
void cloud_disconn_mon(void)
{
OVSDB_TABLE_INIT_NO_KEY(Manager);
OVSDB_TABLE_MONITOR(Manager, false);
}
void apc_init()
{
/* APC Config */
OVSDB_TABLE_INIT_NO_KEY(APC_Config);
OVSDB_TABLE_MONITOR(APC_Config, false);
/* Disable APC by default, enable when cloud connected*/
SCHEMA_SET_INT(apc_conf.enabled, false);
LOGI("APC state/config Initialize");
if (!ovsdb_table_insert(&table_APC_Config, &apc_conf)) {
LOG(ERR, "APC_Config: failed to initialize");
return;
}
/* APC State */
OVSDB_TABLE_INIT_NO_KEY(APC_State);
OVSDB_TABLE_MONITOR(APC_State, false);
SCHEMA_SET_STR(apc_state.mode, "NC");
SCHEMA_SET_STR(apc_state.dr_addr, "0.0.0.0");
SCHEMA_SET_STR(apc_state.bdr_addr, "0.0.0.0");
SCHEMA_SET_INT(apc_state.enabled, false);
if (!ovsdb_table_insert(&table_APC_State, &apc_state)) {
LOG(ERR, "APC_state: failed to initialize");
return;
}
/* Cloud connection monitor - if cloud unreachable
* for certain time, disable APC and enable after the
* cloud connection becomes stable. */
cloud_disconn_mon();
}
bool target_radio_init(const struct target_radio_ops *ops)
{
uci = uci_alloc_context();
@@ -691,13 +956,18 @@ bool target_radio_init(const struct target_radio_ops *ops)
OVSDB_TABLE_INIT(Hotspot20_Icon_Config, _uuid);
OVSDB_TABLE_MONITOR(Hotspot20_Icon_Config, false);
OVSDB_TABLE_INIT(Wifi_RRM_Config, _uuid);
OVSDB_TABLE_MONITOR(Wifi_RRM_Config, false);
OVSDB_TABLE_INIT(Wifi_RRM_Config, _uuid);
OVSDB_TABLE_MONITOR(Wifi_RRM_Config, false);
OVSDB_TABLE_INIT(Radius_Proxy_Config, _uuid);
OVSDB_TABLE_MONITOR(Radius_Proxy_Config, false);
evsched_task(&periodic_task, NULL, EVSCHED_SEC(5));
radio_nl80211_init();
radio_ubus_init();
apc_init();
clock_gettime(CLOCK_MONOTONIC, &startup_time);

View File

@@ -50,7 +50,8 @@
extern struct ev_loop *wifihal_evloop;
extern ovsdb_table_t table_Wifi_VIF_State;
extern ovsdb_table_t table_Wifi_Associated_Clients;
static struct unl unl;
static struct unl unl_req;
static struct unl unl_notify;
static ev_io unl_io;
static int avl_addrcmp(const void *k1, const void *k2, void *ptr)
@@ -430,15 +431,55 @@ static void nl80211_del_phy(struct nlattr **tb, char *name)
free(phy);
}
static void nl80211_update_current_channel(struct nlattr **tb, char *name, int freq)
static int nl80211_channel_recv(struct nl_msg *msg, void *arg)
{
struct genlmsghdr *gnlh = nlmsg_data(nlmsg_hdr(msg));
struct nlattr *tb[NL80211_ATTR_MAX + 1];
unsigned int *chan = (unsigned int *)arg;
memset(tb, 0, sizeof(tb));
nla_parse(tb, NL80211_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
genlmsg_attrlen(gnlh, 0), NULL);
if (tb[NL80211_ATTR_WIPHY_FREQ]) {
*chan = ieee80211_frequency_to_channel(nla_get_u32(tb[NL80211_ATTR_WIPHY_FREQ]));
}
return NL_OK;
}
int nl80211_channel_get(char *name, unsigned int *chan)
{
struct nl_msg *msg;
struct wifi_phy *phy;
struct wifi_iface *wif=NULL;
int idx = 0;
phy = avl_find_element(&phy_tree, name, phy, avl);
if (!phy)
return;
return -1;
phy->current_channel = ieee80211_frequency_to_channel(freq);
if (list_empty(&phy->wifs))
return -1;
wif = list_first_entry(&phy->wifs, struct wifi_iface, phy);
if (!wif)
return -1;
idx = if_nametoindex(wif->name);
if (!idx)
return -1;
msg = unl_genl_msg(&unl_req, NL80211_CMD_GET_INTERFACE, true);
nla_put_u32(msg, NL80211_ATTR_IFINDEX, idx);
unl_genl_request(&unl_req, msg, nl80211_channel_recv, chan);
phy->current_channel = *chan;
return NL_OK;
}
static int nl80211_recv(struct nl_msg *msg, void *arg)
@@ -449,7 +490,6 @@ static int nl80211_recv(struct nl_msg *msg, void *arg)
char *pif_name=NULL;
char phyname[IFNAMSIZ] = {};
int ifidx = -1, phy = -1;
int freq = 0;
memset(tb, 0, sizeof(tb));
nla_parse(tb, NL80211_ATTR_MAX, genlmsg_attrdata(gnlh, 0),
@@ -465,16 +505,11 @@ static int nl80211_recv(struct nl_msg *msg, void *arg)
if (tb[NL80211_ATTR_WIPHY]) {
phy = nla_get_u32(tb[NL80211_ATTR_WIPHY]);
if (tb[NL80211_ATTR_WIPHY_NAME])
strncpy(phyname, nla_get_string(tb[NL80211_ATTR_WIPHY_NAME]), IFNAMSIZ);
else
snprintf(phyname, sizeof(phyname), "phy%d", phy);
}
if(tb[NL80211_ATTR_WIPHY_FREQ]) {
freq = nla_get_u32(tb[NL80211_ATTR_WIPHY_FREQ]);
snprintf(phyname, sizeof(phyname), "phy%d", phy);
nl80211_update_current_channel(tb, phyname, freq);
} else if (tb[NL80211_ATTR_WIPHY_NAME]) {
strncpy(phyname, nla_get_string(tb[NL80211_ATTR_WIPHY_NAME]), IFNAMSIZ);
} else if (sscanf(ifname, "wlan%d", &phy)) {
snprintf(phyname, sizeof(phyname), "phy%d", phy);
}
switch (gnlh->cmd) {
@@ -528,7 +563,7 @@ static void nl80211_ev(struct ev_loop *ev, struct ev_io *io, int event)
nl_cb_set(cb, NL_CB_FINISH, NL_CB_CUSTOM, finish_handler, NULL);
nl_cb_set(cb, NL_CB_SEQ_CHECK, NL_CB_CUSTOM, no_seq_check, NULL);
nl_cb_set(cb, NL_CB_VALID, NL_CB_CUSTOM, nl80211_recv, NULL);
nl_recvmsgs(unl.sock, cb);
nl_recvmsgs(unl_notify.sock, cb);
nl_cb_put(cb);
}
@@ -546,24 +581,33 @@ int radio_nl80211_init(void)
{
struct nl_msg *msg;
if (unl_genl_init(&unl, "nl80211") < 0) {
if (unl_genl_init(&unl_req, "nl80211") < 0) {
syslog(0, "nl80211: failed to connect\n");
return -1;
}
msg = unl_genl_msg(&unl, NL80211_CMD_GET_WIPHY, true);
unl_genl_request(&unl, msg, nl80211_recv, NULL);
msg = unl_genl_msg(&unl, NL80211_CMD_GET_INTERFACE, true);
unl_genl_request(&unl, msg, nl80211_recv, NULL);
if (unl_genl_init(&unl_notify, "nl80211") < 0) {
syslog(0, "nl80211: failed to connect\n");
return -1;
}
unl_genl_subscribe(&unl, "config");
unl_genl_subscribe(&unl, "mlme");
unl_genl_subscribe(&unl, "vendor");
msg = unl_genl_msg(&unl_req, NL80211_CMD_GET_WIPHY, true);
unl_genl_request(&unl_req, msg, nl80211_recv, NULL);
msg = unl_genl_msg(&unl_req, NL80211_CMD_GET_INTERFACE, true);
unl_genl_request(&unl_req, msg, nl80211_recv, NULL);
if (nl_socket_set_buffer_size(unl.sock, 262144, 0) < 0)
unl_genl_subscribe(&unl_notify, "config");
unl_genl_subscribe(&unl_notify, "mlme");
unl_genl_subscribe(&unl_notify, "vendor");
if (nl_socket_set_buffer_size(unl_notify.sock, 262144, 0) < 0)
LOGE("radio_nl80211: Failed to set nl socket buffer size");
ev_io_init(&unl_io, nl80211_ev, unl.sock->s_fd, EV_READ);
if (nl_socket_set_nonblocking(unl_notify.sock))
LOGE("radio_nl80211: Failed to set socket in the non blocking mode");
ev_io_init(&unl_io, nl80211_ev, unl_notify.sock->s_fd, EV_READ);
ev_io_start(wifihal_evloop, &unl_io);
evsched_task(&vif_poll_stations, NULL, EVSCHED_SEC(5));

View File

@@ -0,0 +1,417 @@
/* SPDX-License-Identifier: BSD-3-Clause */
#include <stdio.h>
#include <stdbool.h>
#include <time.h>
#include <uci.h>
#include <uci_blob.h>
#include <target.h>
#include <curl/curl.h>
#include "ovsdb.h"
#include "ovsdb_update.h"
#include "ovsdb_sync.h"
#include "ovsdb_table.h"
#include "ovsdb_cache.h"
#include "nl80211.h"
#include "radio.h"
#include "vif.h"
#include "phy.h"
#include "log.h"
#include "evsched.h"
#include "uci.h"
#include "utils.h"
#include "radius_proxy.h"
struct blob_buf uci_buf = {};
struct blob_attr *n;
extern ovsdb_table_t table_APC_State;
extern json_t* ovsdb_table_where(ovsdb_table_t *table, void *record);
enum {
RADIUS_PROXY_OPTIONS_LISTEN_UDP,
RADIUS_PROXY_OPTIONS_NAME,
__RADIUS_PROXY_OPTIONS_MAX
};
enum {
RADIUS_PROXY_CLIENT_NAME,
RADIUS_PROXY_CLIENT_HOST,
RADIUS_PROXY_CLIENT_TYPE,
RADIUS_PROXY_CLIENT_SECRET,
__RADIUS_PROXY_CLIENT_MAX
};
enum {
RADIUS_PROXY_SERVER_NAME,
RADIUS_PROXY_SERVER_HOST,
RADIUS_PROXY_SERVER_TYPE,
RADIUS_PROXY_SERVER_SECRET,
RADIUS_PROXY_SERVER_PORT,
RADIUS_PROXY_SERVER_STATUS,
RADIUS_PROXY_SERVER_TLS,
RADIUS_PROXY_SERVER_CERT_NAME_CHECK,
__RADIUS_PROXY_SERVER_MAX
};
enum {
RADIUS_PROXY_TLS_NAME,
RADIUS_PROXY_TLS_CA_CERT,
RADIUS_PROXY_TLS_CLIENT_CERT,
RADIUS_PROXY_TLS_CLIENT_KEY,
RADIUS_PROXY_TLS_CERT_PASSWORD,
__RADIUS_PROXY_TLS_MAX,
};
enum {
RADIUS_PROXY_REALM_NAME,
RADIUS_PROXY_REALM_AUTH_SERVER,
RADIUS_PROXY_REALM_ACCT_SERVER,
__RADIUS_PROXY_REALM_MAX
};
static const struct blobmsg_policy radius_proxy_options_policy[__RADIUS_PROXY_OPTIONS_MAX] = {
[RADIUS_PROXY_OPTIONS_LISTEN_UDP] = { .name = "ListenUDP", BLOBMSG_TYPE_ARRAY },
[RADIUS_PROXY_OPTIONS_NAME] = { .name = "name", BLOBMSG_TYPE_STRING },
};
static const struct blobmsg_policy radius_proxy_client_policy[__RADIUS_PROXY_CLIENT_MAX] = {
[RADIUS_PROXY_CLIENT_NAME] = { .name = "name", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_CLIENT_HOST] = { .name = "host", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_CLIENT_TYPE] = { .name = "type", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_CLIENT_SECRET] = { .name = "secret", BLOBMSG_TYPE_STRING },
};
static const struct blobmsg_policy radius_proxy_tls_policy[__RADIUS_PROXY_TLS_MAX] = {
[RADIUS_PROXY_TLS_NAME] = { .name = "name", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_TLS_CA_CERT] = { .name = "CACertificateFile", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_TLS_CLIENT_CERT] = { .name = "certificateFile", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_TLS_CLIENT_KEY] = { .name = "certificateKeyFile", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_TLS_CERT_PASSWORD] = { .name = "certificateKeyPassword", BLOBMSG_TYPE_STRING },
};
static const struct blobmsg_policy radius_proxy_server_policy[__RADIUS_PROXY_SERVER_MAX] = {
[RADIUS_PROXY_SERVER_NAME] = { .name = "name", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_SERVER_HOST] = { .name = "host", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_SERVER_TYPE] = { .name = "type", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_SERVER_SECRET] = { .name = "secret", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_SERVER_PORT] = { .name = "port", BLOBMSG_TYPE_INT32 },
[RADIUS_PROXY_SERVER_STATUS] = { .name = "statusServer", BLOBMSG_TYPE_BOOL },
[RADIUS_PROXY_SERVER_TLS] = { .name = "tls", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_SERVER_CERT_NAME_CHECK] = { .name = "certificateNameCheck", BLOBMSG_TYPE_BOOL },
};
static const struct blobmsg_policy radius_proxy_realm_policy[__RADIUS_PROXY_REALM_MAX] = {
[RADIUS_PROXY_REALM_NAME] = { .name = "name", BLOBMSG_TYPE_STRING },
[RADIUS_PROXY_REALM_AUTH_SERVER] = { .name = "server", BLOBMSG_TYPE_ARRAY },
[RADIUS_PROXY_REALM_ACCT_SERVER] = { .name = "accountingServer", BLOBMSG_TYPE_ARRAY },
};
const struct uci_blob_param_list radius_proxy_options_param = {
.n_params = __RADIUS_PROXY_OPTIONS_MAX,
.params = radius_proxy_options_policy,
};
const struct uci_blob_param_list radius_proxy_client_param = {
.n_params = __RADIUS_PROXY_CLIENT_MAX,
.params = radius_proxy_client_policy,
};
const struct uci_blob_param_list radius_proxy_tls_param = {
.n_params = __RADIUS_PROXY_TLS_MAX,
.params = radius_proxy_tls_policy,
};
const struct uci_blob_param_list radius_proxy_server_param = {
.n_params = __RADIUS_PROXY_SERVER_MAX,
.params = radius_proxy_server_policy,
};
const struct uci_blob_param_list radius_proxy_realm_param = {
.n_params = __RADIUS_PROXY_REALM_MAX,
.params = radius_proxy_realm_policy,
};
size_t file_write(void *ptr, size_t size, size_t nmemb, FILE *stream) {
size_t written = fwrite(ptr, size, nmemb, stream);
return written;
}
static bool radsec_download_cert(char *cert_name, char *dir_name, char *cert_url)
{
CURL *curl;
FILE *fp;
CURLcode curl_ret;
char path[200];
char dir_path[200];
char name[32];
char dir[32];
char *gw_clientcert = "/usr/opensync/certs/client.pem";
char *gw_clientkey = "/usr/opensync/certs/client_dec.key";
struct stat stat_buf;
strcpy(name, cert_name);
strcpy(dir, dir_name);
sprintf(dir_path, "/tmp/radsec/certs/%s", dir);
sprintf(path, "/tmp/radsec/certs/%s/%s", dir, name);
if (stat(dir_path, &stat_buf) == -1)
{
char cmd[200];
sprintf(cmd, "mkdir -p %s", dir_path);
system(cmd);
}
curl = curl_easy_init();
if (curl)
{
fp = fopen(path, "wb");
if (fp == NULL)
{
curl_easy_cleanup(curl);
return false;
}
if (cert_url == NULL)
{
curl_easy_cleanup(curl);
fclose(fp);
return false;
}
curl_easy_setopt(curl, CURLOPT_SSLCERT, gw_clientcert);
curl_easy_setopt(curl, CURLOPT_SSLKEY, gw_clientkey);
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 0L);
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, 0L);
curl_easy_setopt(curl, CURLOPT_HEADER, 0L);
curl_easy_setopt(curl, CURLOPT_URL, cert_url);
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, file_write);
curl_easy_setopt(curl, CURLOPT_WRITEDATA, fp);
curl_ret = curl_easy_perform(curl);
if (curl_ret != CURLE_OK)
{
LOGE("radsec: certificate download failed %s", curl_easy_strerror(curl_ret));
curl_easy_cleanup(curl);
fclose(fp);
remove(path);
return false;
}
curl_easy_cleanup(curl);
fclose(fp);
}
return true;
}
static bool radius_proxy_config_set(struct schema_Radius_Proxy_Config *conf)
{
int i = 0;
char path[200];
char name[256];
char server_name[256] = {};
char acct_server_name[256] = {};
char tls_name[256] = {};
struct schema_APC_State apc_conf;
json_t *where = ovsdb_table_where(&table_APC_State, &apc_conf);
if (false == ovsdb_table_select_one_where(&table_APC_State,
where, &apc_conf)) {
LOG(INFO, "APC_State read failed");
return false;
}
/* Configure options block */
blob_buf_init(&uci_buf, 0);
n = blobmsg_open_array(&uci_buf,"ListenUDP");
blobmsg_add_string(&uci_buf, NULL, "*:1812");
blobmsg_add_string(&uci_buf, NULL, "*:1813");
blobmsg_close_array(&uci_buf, n);
memset(name, '\0', sizeof(name));
sprintf(name, "%s%s", conf->radius_config_name, "options");
blobmsg_add_string(&uci_buf, "name", name);
blob_to_uci_section(uci, "radsecproxy", name, "options",
uci_buf.head, &radius_proxy_options_param, NULL);
/* Configure client block */
blob_buf_init(&uci_buf, 0);
blobmsg_add_string(&uci_buf, "host", "0.0.0.0/0");
blobmsg_add_string(&uci_buf, "type", "udp");
blobmsg_add_string(&uci_buf, "secret", "secret");
memset(name, '\0', sizeof(name));
sprintf(name, "%s%s", conf->radius_config_name, "client");
blobmsg_add_string(&uci_buf, "name", name);
blob_to_uci_section(uci, "radsecproxy", name, "client",
uci_buf.head, &radius_proxy_client_param, NULL);
/* Configure TLS/non-TLS and server blocks */
sprintf(server_name, "%s%s", conf->radius_config_name, "server");
sprintf(acct_server_name, "%s%s", conf->radius_config_name, "Acctserver");
sprintf(tls_name, "%s%s", conf->radius_config_name, "tls");
if (conf->radsec)
{
blob_buf_init(&uci_buf, 0);
radsec_download_cert("cacert.pem",
conf->radius_config_name, conf->ca_cert);
radsec_download_cert("clientcert.pem",
conf->radius_config_name, conf->client_cert);
radsec_download_cert("clientdec.key",
conf->radius_config_name, conf->client_key);
blobmsg_add_string(&uci_buf, "name", tls_name);
memset(path, '\0', sizeof(path));
sprintf(path, "/tmp/radsec/certs/%s/cacert.pem",
conf->radius_config_name);
blobmsg_add_string(&uci_buf, "CACertificateFile", path);
memset(path, '\0', sizeof(path));
sprintf(path, "/tmp/radsec/certs/%s/clientcert.pem",
conf->radius_config_name);
blobmsg_add_string(&uci_buf, "certificateFile", path);
memset(path, '\0', sizeof(path));
sprintf(path, "/tmp/radsec/certs/%s/clientdec.key",
conf->radius_config_name);
blobmsg_add_string(&uci_buf, "certificateKeyFile", path);
if (strlen(conf->passphrase) > 0)
blobmsg_add_string(&uci_buf, "certificateKeyPassword", conf->passphrase);
blob_to_uci_section(uci, "radsecproxy", tls_name,
"tls", uci_buf.head, &radius_proxy_tls_param, NULL);
blob_buf_init(&uci_buf, 0);
blobmsg_add_string(&uci_buf, "name", server_name);
blobmsg_add_string(&uci_buf, "host", conf->server);
blobmsg_add_string(&uci_buf, "type", "tls");
blobmsg_add_string(&uci_buf, "tls", tls_name);
blobmsg_add_u32(&uci_buf, "port", conf->port);
blobmsg_add_string(&uci_buf, "secret", "radsec");
blobmsg_add_bool(&uci_buf, "statusServer", 0);
blobmsg_add_bool(&uci_buf, "certificateNameCheck", 0);
blob_to_uci_section(uci, "radsecproxy", server_name, "server",
uci_buf.head, &radius_proxy_server_param, NULL);
}
else /* non-TLS block */
{
/* Authentication server */
blob_buf_init(&uci_buf, 0);
blobmsg_add_string(&uci_buf, "name", server_name);
blobmsg_add_string(&uci_buf, "host", conf->server);
blobmsg_add_string(&uci_buf, "type", "udp");
if (strlen(conf->secret) > 0)
blobmsg_add_string(&uci_buf, "secret", conf->secret);
if (conf->port > 0)
blobmsg_add_u32(&uci_buf, "port", conf->port);
blob_to_uci_section(uci, "radsecproxy", server_name, "server",
uci_buf.head, &radius_proxy_server_param, NULL);
/* Accounting server */
if (strlen(conf->acct_server) > 0)
{
blob_buf_init(&uci_buf, 0);
blobmsg_add_string(&uci_buf, "name", acct_server_name);
blobmsg_add_string(&uci_buf, "host", conf->acct_server);
blobmsg_add_string(&uci_buf, "type", "udp");
if (strlen(conf->secret) > 0)
blobmsg_add_string(&uci_buf, "secret", conf->acct_secret);
if (conf->acct_port > 0)
blobmsg_add_u32(&uci_buf, "port", conf->acct_port);
blob_to_uci_section(uci, "radsecproxy", acct_server_name, "server",
uci_buf.head, &radius_proxy_server_param, NULL);
}
}
/* Configure realm block */
for (i = 0; i < conf->realm_len; i++)
{
blob_buf_init(&uci_buf, 0);
blobmsg_add_string(&uci_buf, "name", conf->realm[i]);
n = blobmsg_open_array(&uci_buf,"server");
blobmsg_add_string(&uci_buf, NULL, server_name);
blobmsg_close_array(&uci_buf, n);
if (conf->radsec)
{ /* Accounting server same as auth server */
n = blobmsg_open_array(&uci_buf, "accountingServer");
blobmsg_add_string(&uci_buf, NULL, server_name);
blobmsg_close_array(&uci_buf, n);
}
else if (strlen(conf->acct_server) > 0)
{ /* non-TLS case where accounting server is configured */
n = blobmsg_open_array(&uci_buf, "accountingServer");
blobmsg_add_string(&uci_buf, NULL, acct_server_name);
blobmsg_close_array(&uci_buf, n);
}
memset(name, '\0', sizeof(name));
sprintf(name, "%s%s%d", conf->radius_config_name, "realm", i);
blob_to_uci_section(uci, "radsecproxy", name, "realm",
uci_buf.head, &radius_proxy_realm_param, NULL);
}
uci_commit_all(uci);
return true;
}
static bool radius_proxy_config_delete()
{
struct uci_package *radsecproxy;
struct uci_context *rad_uci;
struct uci_element *e = NULL, *tmp = NULL;
int ret = 0;
rad_uci = uci_alloc_context();
ret = uci_load(rad_uci, "radsecproxy", &radsecproxy);
if (ret) {
LOGE("%s: uci_load() failed with rc %d", __func__, ret);
uci_free_context(rad_uci);
return false;
}
uci_foreach_element_safe(&radsecproxy->sections, tmp, e) {
struct uci_section *s = uci_to_section(e);
if ((s == NULL) || (s->type == NULL)) continue;
uci_section_del(rad_uci, "radsecproxy", "radsecproxy",
(char *)s->e.name, s->type);
}
uci_commit(rad_uci, &radsecproxy, false);
uci_unload(rad_uci, radsecproxy);
uci_free_context(rad_uci);
reload_config = 1;
return true;
}
void callback_Radius_Proxy_Config(ovsdb_update_monitor_t *self,
struct schema_Radius_Proxy_Config *old,
struct schema_Radius_Proxy_Config *conf)
{
switch (self->mon_type)
{
case OVSDB_UPDATE_NEW:
case OVSDB_UPDATE_MODIFY:
(void) radius_proxy_config_set(conf);
vif_check_radius_proxy();
break;
case OVSDB_UPDATE_DEL:
(void) radius_proxy_config_delete();
vif_check_radius_proxy();
break;
default:
LOG(ERR, "Radius_Proxy_Config: unexpected mon_type %d %s",
self->mon_type, self->mon_uuid);
break;
}
return;
}

View File

@@ -47,8 +47,19 @@ void rrm_config_vif(struct blob_buf *b, struct blob_buf *del, const char * freq_
blobmsg_add_u32(b, "rssi_ignore_probe_request", conf.probe_resp_threshold);
blobmsg_add_u32(b, "signal_connect", conf.client_disconnect_threshold);
blobmsg_add_u32(b, "signal_stay", conf.client_disconnect_threshold);
blobmsg_add_u32(b, "bcn_rate", conf.beacon_rate);
blobmsg_add_u32(b, "mcast_rate", conf.mcast_rate);
if (conf.beacon_rate == 0) {
// Default to the lowest possible bit rate for each frequency band
if (!strcmp(freq_band, "2.4G")) {
blobmsg_add_u32(b, "bcn_rate", 10);
} else {
blobmsg_add_u32(b, "bcn_rate", 60);
}
} else {
blobmsg_add_u32(b, "bcn_rate", conf.beacon_rate);
}
}
return;
}

View File

@@ -291,7 +291,7 @@ static void cb_osp_start_factory_reboot(EV_P_ ev_timer *w, int events)
if (!strcmp(upg_url, "reboot"))
system("reboot");
else
system("jffs2reset -y -r");
system("wlan_ap_factory_reset.sh");
upg_running = false;

View File

@@ -210,8 +210,10 @@ int uci_section_to_blob(struct uci_context *uci, char *package, char *section,
if (uci_load(uci, package, &p))
p = uci_lookup_package(uci, package);
if (!p)
if (!p) {
uci_unload(uci, p);
return -1;
}
s = uci_lookup_section(uci, p, section);
if (!s)
goto out;

View File

@@ -23,41 +23,79 @@
#include "vif.h"
static struct mode_map mode_map[] = {
{ 0, "11b", "11b", NULL, "NOHT" },
{ 0, "11g", "11g", NULL, "NOHT" },
{ 1, "11a", "11a", NULL, "NOHT" },
{ 0, "11n", "11g", "HT20", "HT20" },
{ 0, "11n", "11g", "HT40", "HT40" },
{ 0, "11n", "11g", "HT40-", "HT40-" },
{ 0, "11n", "11g", "HT40+", "HT40+" },
{ 0, "11n", "11g", "HT80", "HT40" },
{ 0, "11n", "11g", "HT160", "HT40" },
{ 1, "11n", "11a", "HT20", "HT20" },
{ 1, "11n", "11a", "HT40", "HT40" },
{ 1, "11n", "11a", "HT40-", "HT40-" },
{ 1, "11n", "11a", "HT40+", "HT40+" },
{ 1, "11n", "11a", "HT80", "HT40" },
{ 1, "11n", "11a", "HT160", "HT40" },
{ 1, "11ac", "11a", "HT20", "VHT20" },
{ 1, "11ac", "11a", "HT40", "VHT40" },
{ 1, "11ac", "11a", "HT40-", "VHT40" },
{ 1, "11ac", "11a", "HT40+", "VHT40" },
{ 1, "11ac", "11a", "HT80", "VHT80" },
{ 1, "11ac", "11a", "HT160", "VHT160" },
{ 0, "11ax", "11g", "HT20", "HE20" },
{ 0, "11ax", "11g", "HT40", "HE40" },
{ 0, "11ax", "11g", "HT40-", "HE40" },
{ 0, "11ax", "11g", "HT40+", "HE40" },
{ 0, "11ax", "11g", "HT80", "HE80" },
{ 0, "11ax", "11g", "HT160", "HE80" },
{ 1, "11ax", "11a", "HT20", "HE20" },
{ 1, "11ax", "11a", "HT40", "HE40" },
{ 1, "11ax", "11a", "HT40-", "HE40" },
{ 1, "11ax", "11a", "HT40+", "HE40" },
{ 1, "11ax", "11a", "HT80", "HE80" },
{ 1, "11ax", "11a", "HT160", "HE160" },
{ 0, "11b", "11b", NULL, "NOHT", 0 },
{ 0, "11g", "11g", NULL, "NOHT", 0 },
{ 1, "11a", "11a", NULL, "NOHT", 0 },
{ 0, "11n", "11g", "HT20", "HT20", 0 },
{ 0, "11n", "11g", "HT40", "HT40", 1 },
{ 0, "11n", "11g", "HT40-", "HT40-", 1 },
{ 0, "11n", "11g", "HT40+", "HT40+", 1 },
{ 0, "11n", "11g", "HT80", "HT40", 1 },
{ 0, "11n", "11g", "HT160", "HT40", 1 },
{ 1, "11n", "11a", "HT20", "HT20", 0 },
{ 1, "11n", "11a", "HT40", "HT40", 1 },
{ 1, "11n", "11a", "HT40-", "HT40-", 1 },
{ 1, "11n", "11a", "HT40+", "HT40+", 1 },
{ 1, "11n", "11a", "HT80", "HT40", 1 },
{ 1, "11n", "11a", "HT160", "HT40", 1 },
{ 1, "11ac", "11a", "HT20", "VHT20", 0 },
{ 1, "11ac", "11a", "HT40", "VHT40", 1 },
{ 1, "11ac", "11a", "HT40-", "VHT40", 1 },
{ 1, "11ac", "11a", "HT40+", "VHT40", 1 },
{ 1, "11ac", "11a", "HT80", "VHT80", 1 },
{ 1, "11ac", "11a", "HT160", "VHT160", 1 },
{ 0, "11ax", "11g", "HT20", "HE20", 0 },
{ 0, "11ax", "11g", "HT40", "HE40", 1 },
{ 0, "11ax", "11g", "HT40-", "HE40", 1 },
{ 0, "11ax", "11g", "HT40+", "HE40", 1 },
{ 0, "11ax", "11g", "HT80", "HE80", 1 },
{ 0, "11ax", "11g", "HT160", "HE80", 1 },
{ 1, "11ax", "11a", "HT20", "HE20", 0 },
{ 1, "11ax", "11a", "HT40", "HE40", 1 },
{ 1, "11ax", "11a", "HT40-", "HE40", 1 },
{ 1, "11ax", "11a", "HT40+", "HE40", 1 },
{ 1, "11ax", "11a", "HT80", "HE80", 1 },
{ 1, "11ax", "11a", "HT160", "HE160", 1 },
};
typedef enum {
MHz20=0,
MHz40 = 1,
MHz80 = 2,
MHz160 = 4
} bm_AllowedBw;
typedef struct {
int freq;
bm_AllowedBw bw;
} freqBwListEntry;
freqBwListEntry freqBwList[] ={{2412, MHz20},{2417, MHz20},{2422, MHz20},{2427, MHz20},{2432, MHz20},{2437, MHz20},{2442, MHz20},{2447, MHz20},{2452, MHz20},{2457, MHz20},{2462, MHz20},{2467, MHz20},{2472, MHz20}, {2484, MHz20},
{ 5180, MHz20|MHz40|MHz80},{5200, MHz20},{5220, MHz20|MHz40},{5240, MHz20},{5260, MHz20|MHz40|MHz80},{5280, MHz20},{5300,MHz20|MHz40},{5320, MHz20},{5500, MHz20|MHz40|MHz80},{5520, MHz20},{5540, MHz20|MHz40}, {5560, MHz20},
{5580, MHz20|MHz40|MHz80},{5600, MHz20},{5620, MHz20|MHz40},{5640, MHz20},{5660, MHz20|MHz40|MHz80},{5680, MHz20},{5700, MHz20|MHz40},{5720, MHz20},{5745, MHz20|MHz40|MHz80},{5765, MHz20},{5785, MHz20|MHz40},{5805, MHz20},{5825, MHz20}};
#define REQ_BW(htmode) (!strcmp(htmode, "HT20") ? MHz20 : !strcmp(htmode, "HT40") ? MHz40 : !strcmp(htmode, "HT80") ? MHz80 : !strcmp(htmode, "HT160") ? MHz160 : MHz20)
#define REQ_MODE(bw) (bw==MHz20 ? "HT20": bw==MHz40 ? "HT40" : bw==MHz80 ? "HT80" : bw==MHz160 ? "HT160" : "HT20")
char * get_max_channel_bw_channel(int channel_freq, const char* htmode)
{
unsigned int i;
bm_AllowedBw requestedBw;
requestedBw = REQ_BW(htmode);
for ( i = 0; i < ARRAY_SIZE(freqBwList); i++) {
if(freqBwList[i].freq == channel_freq) {
while (requestedBw) {
if (freqBwList[i].bw & requestedBw) {
return REQ_MODE(requestedBw);
}
requestedBw >>= 1;
}
}
}
return "HT20";
}
struct mode_map *mode_map_get_uci(const char *band, const char *htmode, const char *hwmode)
{
unsigned int i;
@@ -624,3 +662,22 @@ bool vif_get_security(struct schema_Wifi_VIF_State *vstate, char *mode, char *
return true;
}
bool vif_get_key_for_key_distr(const char *secret, char *key_str)
{
bool err = false;
FILE *fp;
char cmd_buf[256] = "openssl aes-128-cbc -nosalt -k ";
strcat(cmd_buf, secret);
strcat(cmd_buf, " -P 2>/dev/null | grep key | cut -d = -f2");
fp = popen(cmd_buf, "r");
if (fp && fscanf(fp, "%s", key_str)) {
err = true;
}
fclose(fp);
return err;
}

View File

@@ -32,6 +32,7 @@
extern ovsdb_table_t table_Wifi_VIF_Config;
extern ovsdb_table_t table_Hotspot20_Icon_Config;
extern ovsdb_table_t table_Radius_Proxy_Config;
extern struct blob_buf b;
extern struct blob_buf del;
@@ -94,6 +95,7 @@ enum {
WIF_ATTR_VENUE_URL,
WIF_ATTR_NETWORK_AUTH_TYPE,
WIF_ATTR_IPADDR_TYPE_AVAILABILITY,
WIF_ATTR_CONNECTION_CAPABILITY,
WIF_ATTR_DOMAIN_NAME,
WIF_ATTR_MCC_MNC,
WIF_ATTR_NAI_REALM,
@@ -129,6 +131,11 @@ enum {
WIF_ATTR_DVLAN_NAMING,
WIF_ATTR_DVLAN_BRIDGE,
WIF_ATTR_MIN_HW_MODE,
WIF_ATTR_11R_R0KH,
WIF_ATTR_11R_R1KH,
WIF_ATTR_RADPROXY,
WIF_ATTR_PROXY_ARP,
WIF_ATTR_MCAST_TO_UCAST,
__WIF_ATTR_MAX,
};
@@ -184,7 +191,8 @@ static const struct blobmsg_policy wifi_iface_policy[__WIF_ATTR_MAX] = {
[WIF_ATTR_VENUE_TYPE] = { .name = "venue_type", BLOBMSG_TYPE_INT32 },
[WIF_ATTR_VENUE_URL] = { .name = "venue_url", BLOBMSG_TYPE_ARRAY },
[WIF_ATTR_NETWORK_AUTH_TYPE] = { .name = "network_auth_type", BLOBMSG_TYPE_STRING },
[WIF_ATTR_IPADDR_TYPE_AVAILABILITY] = { .name = "ipaddr_type_availability", BLOBMSG_TYPE_INT32 },
[WIF_ATTR_IPADDR_TYPE_AVAILABILITY] = { .name = "ipaddr_type_availability", BLOBMSG_TYPE_STRING },
[WIF_ATTR_CONNECTION_CAPABILITY] = { .name = "hs20_conn_capab", BLOBMSG_TYPE_ARRAY },
[WIF_ATTR_DOMAIN_NAME] = { .name = "domain_name", BLOBMSG_TYPE_STRING },
[WIF_ATTR_MCC_MNC] = { .name = "anqp_3gpp_cell_net", BLOBMSG_TYPE_STRING },
[WIF_ATTR_NAI_REALM] = { .name = "nai_realm", BLOBMSG_TYPE_ARRAY },
@@ -220,6 +228,11 @@ static const struct blobmsg_policy wifi_iface_policy[__WIF_ATTR_MAX] = {
[WIF_ATTR_DVLAN_NAMING] = { .name = "vlan_naming", BLOBMSG_TYPE_STRING },
[WIF_ATTR_DVLAN_BRIDGE] = { .name = "vlan_bridge", BLOBMSG_TYPE_STRING },
[WIF_ATTR_MIN_HW_MODE] = { .name = "min_hw_mode", BLOBMSG_TYPE_STRING },
[WIF_ATTR_11R_R0KH] = { .name = "r0kh", BLOBMSG_TYPE_STRING },
[WIF_ATTR_11R_R1KH] = { .name = "r1kh", BLOBMSG_TYPE_STRING },
[WIF_ATTR_RADPROXY] = { .name = "radproxy", BLOBMSG_TYPE_STRING },
[WIF_ATTR_PROXY_ARP] = { .name = "proxy_arp", BLOBMSG_TYPE_BOOL },
[WIF_ATTR_MCAST_TO_UCAST] = { .name = "multicast_to_unicast", BLOBMSG_TYPE_BOOL },
};
const struct uci_blob_param_list wifi_iface_param = {
@@ -307,10 +320,67 @@ static struct vif_crypto {
{ "wpa-mixed", OVSDB_SECURITY_ENCRYPTION_WPA_EAP, OVSDB_SECURITY_MODE_MIXED, 1 },
{ "sae", OVSDB_SECURITY_ENCRYPTION_WPA_SAE, OVSDB_SECURITY_MODE_WPA3, 0 },
{ "sae-mixed", OVSDB_SECURITY_ENCRYPTION_WPA_SAE, OVSDB_SECURITY_MODE_MIXED, 0 },
{ "wpa3", OVSDB_SECURITY_ENCRYPTION_WPA3_EAP, OVSDB_SECURITY_MODE_WPA3, 1 },
{ "wpa3-only", OVSDB_SECURITY_ENCRYPTION_WPA3_EAP, OVSDB_SECURITY_MODE_WPA3, 1 },
{ "wpa3-mixed", OVSDB_SECURITY_ENCRYPTION_WPA3_EAP, OVSDB_SECURITY_MODE_MIXED, 1 },
};
extern ovsdb_table_t table_APC_State;
extern json_t* ovsdb_table_where(ovsdb_table_t *table, void *record);
extern unsigned int radproxy_apc;
/* Custom options table */
#define SCHEMA_CUSTOM_OPT_SZ 20
#define SCHEMA_CUSTOM_OPTS_MAX 15
const char custom_options_table[SCHEMA_CUSTOM_OPTS_MAX][SCHEMA_CUSTOM_OPT_SZ] =
{
SCHEMA_CONSTS_RATE_LIMIT,
SCHEMA_CONSTS_RATE_DL,
SCHEMA_CONSTS_RATE_UL,
SCHEMA_CONSTS_CLIENT_RATE_DL,
SCHEMA_CONSTS_CLIENT_RATE_UL,
SCHEMA_CONSTS_IEEE80211k,
SCHEMA_CONSTS_RTS_THRESHOLD,
SCHEMA_CONSTS_DTIM_PERIOD,
SCHEMA_CONSTS_RADIUS_OPER_NAME,
SCHEMA_CONSTS_RADIUS_NAS_ID,
SCHEMA_CONSTS_RADIUS_NAS_IP,
SCHEMA_CONSTS_DYNAMIC_VLAN,
SCHEMA_CONSTS_RADPROXY,
SCHEMA_CONSTS_PROXY_ARP,
SCHEMA_CONSTS_MCAST_TO_UCAST,
};
static bool vif_config_custom_opt_get_proxy(
const struct schema_Wifi_VIF_Config *vconf)
{
int i;
const char *opt;
const char *val;
char value[20];
for (i = 0; i < SCHEMA_CUSTOM_OPTS_MAX; i++) {
opt = custom_options_table[i];
val = SCHEMA_KEY_VAL(vconf->custom_options, opt);
if (!val)
strncpy(value, "0", 20);
else
strncpy(value, val, 20);
if (strcmp(opt, "radproxy") == 0) {
if (strcmp(value, "1") == 0) {
radproxy_apc |= 1;
return true;
}
else {
radproxy_apc |= 0;
return false;
}
}
}
return false;
}
static int vif_config_security_set(struct blob_buf *b,
const struct schema_Wifi_VIF_Config *vconf)
{
@@ -318,7 +388,10 @@ static int vif_config_security_set(struct blob_buf *b,
const char *mode = SCHEMA_KEY_VAL(vconf->security, SCHEMA_CONSTS_SECURITY_MODE);
unsigned int i;
unsigned int acct_interval;
const char *auth_server, *auth_port, *auth_secret, *security_key;
const char *auth_server, *auth_port, *auth_secret, *security_key, *acct_server;
char key_str[64], key_holder_str[128];
struct schema_APC_State apc_conf;
const char *local_server = "127.0.0.1";
if (!strcmp(encryption, OVSDB_SECURITY_ENCRYPTION_OPEN) || !mode)
goto open;
@@ -336,20 +409,48 @@ static int vif_config_security_set(struct blob_buf *b,
}
if (vif_crypto[i].enterprise) {
if (vif_config_custom_opt_get_proxy(vconf)) {
LOGN("%s: Apply Proxy Security Settings", vconf->if_name);
json_t *where = ovsdb_table_where(&table_APC_State, &apc_conf);
if (false == ovsdb_table_select_one_where(&table_APC_State,
where, &apc_conf)) {
LOG(INFO, "APC_State read failed");
return -1;
}
if (!strncmp(apc_conf.mode, "DR", 2)) {
auth_server = local_server;
acct_server = local_server;
} else if (!strncmp(apc_conf.mode, "OR", 2) ||
!strncmp(apc_conf.mode, "BDR", 2)) {
auth_server = apc_conf.dr_addr;
acct_server = apc_conf.dr_addr;
}
else {
auth_server = local_server;
acct_server = local_server;
}
}
else
{
auth_server = SCHEMA_KEY_VAL(vconf->security, SCHEMA_CONSTS_SECURITY_RADIUS_IP);
acct_server = SCHEMA_KEY_VAL(vconf->security, OVSDB_SECURITY_RADIUS_ACCT_IP);
}
acct_interval = 0;
auth_server = SCHEMA_KEY_VAL(vconf->security, SCHEMA_CONSTS_SECURITY_RADIUS_IP);
auth_port = SCHEMA_KEY_VAL(vconf->security, SCHEMA_CONSTS_SECURITY_RADIUS_PORT);
auth_secret = SCHEMA_KEY_VAL(vconf->security, SCHEMA_CONSTS_SECURITY_RADIUS_SECRET);
LOGT("%s: Server IP %s port %s secret %s", vconf->if_name, auth_server, auth_port, auth_secret);
if (!auth_server[0] || !auth_port[0] || !auth_secret[0]) {
LOGI("%s: Incomplete RADIUS security config - SSID not created", vconf->if_name);
return -1;
}
blobmsg_add_string(b, "auth_server", auth_server);
blobmsg_add_string(b, "auth_port", auth_port );
blobmsg_add_string(b, "auth_secret", auth_secret );
blobmsg_add_string(b, "acct_server",
SCHEMA_KEY_VAL(vconf->security, OVSDB_SECURITY_RADIUS_ACCT_IP));
blobmsg_add_string(b, "acct_server", acct_server);
blobmsg_add_string(b, "acct_port",
SCHEMA_KEY_VAL(vconf->security, OVSDB_SECURITY_RADIUS_ACCT_PORT));
blobmsg_add_string(b, "acct_secret",
@@ -361,6 +462,26 @@ static int vif_config_security_set(struct blob_buf *b,
{
blobmsg_add_u32(b, "acct_interval", acct_interval);
}
/*
* If Radius is configured and Roaming is enabled,
* - disable ft_psk_generate_local. This is required for hostapd to populate R0/R1.
* - populate r0KH and r1KH with broadcast addressing so that the corresponding
* Key Holders are auto-generated
*/
if (vconf->ft_mobility_domain) {
blobmsg_add_bool(b, "ft_psk_generate_local", 0);
vif_get_key_for_key_distr(auth_secret, key_str);
strcpy(key_holder_str, "ff:ff:ff:ff:ff:ff,*,");
strcat(key_holder_str, key_str);
blobmsg_add_string(b, "r0kh", key_holder_str);
strcpy(key_holder_str, "00:00:00:00:00:00,00:00:00:00:00:00,");
strcat(key_holder_str, key_str);
blobmsg_add_string(b, "r1kh", key_holder_str);
}
} else {
security_key = SCHEMA_KEY_VAL(vconf->security, SCHEMA_CONSTS_SECURITY_KEY);
if (security_key == NULL) {
@@ -368,6 +489,8 @@ static int vif_config_security_set(struct blob_buf *b,
return -1;
}
blobmsg_add_string(b, "key", security_key);
if (vconf->ft_mobility_domain)
blobmsg_add_bool(b, "ft_psk_generate_local", vconf->ft_psk);
}
}
return 0;
@@ -454,25 +577,6 @@ out_none:
OVSDB_SECURITY_ENCRYPTION_OPEN);
}
/* Custom options table */
#define SCHEMA_CUSTOM_OPT_SZ 20
#define SCHEMA_CUSTOM_OPTS_MAX 12
const char custom_options_table[SCHEMA_CUSTOM_OPTS_MAX][SCHEMA_CUSTOM_OPT_SZ] =
{
SCHEMA_CONSTS_RATE_LIMIT,
SCHEMA_CONSTS_RATE_DL,
SCHEMA_CONSTS_RATE_UL,
SCHEMA_CONSTS_CLIENT_RATE_DL,
SCHEMA_CONSTS_CLIENT_RATE_UL,
SCHEMA_CONSTS_IEEE80211k,
SCHEMA_CONSTS_RTS_THRESHOLD,
SCHEMA_CONSTS_DTIM_PERIOD,
SCHEMA_CONSTS_RADIUS_OPER_NAME,
SCHEMA_CONSTS_RADIUS_NAS_ID,
SCHEMA_CONSTS_RADIUS_NAS_IP,
SCHEMA_CONSTS_DYNAMIC_VLAN,
};
static void vif_config_custom_opt_set(struct blob_buf *b, struct blob_buf *del,
const struct schema_Wifi_VIF_Config *vconf)
@@ -483,6 +587,9 @@ static void vif_config_custom_opt_set(struct blob_buf *b, struct blob_buf *del,
const char *opt;
const char *val;
struct blob_attr *n;
bool found_nasid = false;
char mac[ETH_ALEN * 3];
struct blob_attr *tb[__WIF_ATTR_MAX] = { };
for (i = 0; i < SCHEMA_CUSTOM_OPTS_MAX; i++) {
opt = custom_options_table[i];
@@ -517,8 +624,12 @@ static void vif_config_custom_opt_set(struct blob_buf *b, struct blob_buf *del,
blobmsg_add_string(b, "rts_threshold", value);
else if (strcmp(opt, "dtim_period") == 0)
blobmsg_add_string(b, "dtim_period", value);
else if (strcmp(opt, "radius_nas_id") == 0)
blobmsg_add_string(b, "nasid", value);
else if (strcmp(opt, "radius_nas_id") == 0) {
if (strcmp(value, "\0") != 0) {
blobmsg_add_string(b, "nasid", value);
found_nasid = true;
}
}
else if (strcmp(opt, "radius_nas_ip") == 0)
blobmsg_add_string(b, "ownip", value);
else if (strcmp(opt, "radius_oper_name") == 0 && strlen(value) > 0)
@@ -552,8 +663,29 @@ static void vif_config_custom_opt_set(struct blob_buf *b, struct blob_buf *del,
strncpy(value, "br-wan.", 20);
blobmsg_add_string(del, "vlan_bridge", value);
}
} else if (strcmp(opt, "radproxy") == 0) {
blobmsg_add_string(b, "radproxy", value);
} else if (strcmp(opt, "proxy_arp") == 0) {
if (strcmp(value, "1") == 0)
blobmsg_add_bool(b, "proxy_arp", 1);
else if (strcmp(value, "0") == 0)
blobmsg_add_bool(del, "proxy_arp", 1);
} else if (strcmp(opt, "mcast_to_ucast") == 0) {
if (strcmp(value, "1") == 0)
blobmsg_add_bool(b, "multicast_to_unicast", 1);
else if (strcmp(value, "0") == 0)
blobmsg_add_bool(del, "multicast_to_unicast", 1);
}
}
/* No NASID was found from blob, so use BSSID as NASID */
if (found_nasid == false) {
blobmsg_parse(wifi_iface_policy, __WIF_ATTR_MAX, tb, blob_data(b->head), blob_len(b->head));
if (tb[WIF_ATTR_IFNAME] && !vif_get_mac(blobmsg_get_string(tb[WIF_ATTR_IFNAME]), mac))
blobmsg_add_string(b, "nasid", mac);
else
LOGE("Failed to get base BSSID (mac)\n");
}
}
static void set_custom_option_state(struct schema_Wifi_VIF_State *vstate,
@@ -686,6 +818,39 @@ static void vif_state_custom_options_get(struct schema_Wifi_VIF_State *vstate,
custom_options_table[i],
buf);
}
} else if (strcmp(opt, "radproxy") == 0) {
if (tb[WIF_ATTR_RADPROXY]) {
buf = blobmsg_get_string(tb[WIF_ATTR_RADPROXY]);
set_custom_option_state(vstate, &index,
custom_options_table[i],
buf);
}
} else if (strcmp(opt, "proxy_arp") == 0) {
if (tb[WIF_ATTR_PROXY_ARP]) {
if (blobmsg_get_bool(tb[WIF_ATTR_PROXY_ARP])) {
set_custom_option_state(vstate, &index,
custom_options_table[i],
"1");
} else {
set_custom_option_state(vstate, &index,
custom_options_table[i],
"0");
}
}
} else if (strcmp(opt, "mcast_to_ucast") == 0) {
if (tb[WIF_ATTR_MCAST_TO_UCAST]) {
if (blobmsg_get_bool(tb[WIF_ATTR_MCAST_TO_UCAST])) {
set_custom_option_state(vstate, &index,
custom_options_table[i],
"1");
} else {
set_custom_option_state(vstate, &index,
custom_options_table[i],
"0");
}
}
}
}
}
@@ -856,30 +1021,70 @@ size_t write_file(void *ptr, size_t size, size_t nmemb, FILE *stream) {
void vif_section_del(char *section_name)
{
struct uci_package *wireless;
struct uci_context *sec_ctx;
struct uci_element *e = NULL, *tmp = NULL;
int ret=0;
ret= uci_load(uci, "wireless", &wireless);
sec_ctx = uci_alloc_context();
ret= uci_load(sec_ctx, "wireless", &wireless);
if (ret) {
LOGD("%s: uci_load() failed with rc %d", section_name, ret);
LOGE("%s: %s uci_load() failed with rc %d", section_name, __func__, ret);
uci_free_context(sec_ctx);
return;
}
uci_foreach_element_safe(&wireless->sections, tmp, e) {
struct uci_section *s = uci_to_section(e);
if ((s == NULL) || (s->type == NULL)) continue;
if (!strcmp(s->type, section_name)) {
uci_section_del(uci, "vif", "wireless", (char *)s->e.name, section_name);
uci_section_del(sec_ctx, "vif", "wireless", (char *)s->e.name, section_name);
}
else {
continue;
}
}
uci_commit(uci, &wireless, false);
uci_unload(uci, wireless);
uci_commit(sec_ctx, &wireless, false);
uci_unload(sec_ctx, wireless);
uci_free_context(sec_ctx);
reload_config = 1;
}
void vif_check_radius_proxy()
{
struct schema_APC_State apc_conf;
int n = 0;
void *buf = NULL;
json_t *where = ovsdb_table_where(&table_APC_State, &apc_conf);
if (false == ovsdb_table_select_one_where(&table_APC_State, where, &apc_conf))
{
LOGI("APC_State read failed");
return;
}
buf = ovsdb_table_select_where(&table_Radius_Proxy_Config, NULL, &n);
if (!buf)
{
LOGI("Radius_Proxy_Config table doesn't exist. Stop radsecproxy service.");
system("/etc/init.d/radsecproxy stop");
return;
}
else if (!strcmp(apc_conf.mode, "DR"))
{
if (!system("pidof radsecproxy"))
goto out;
LOGI("Start radsecproxy service.");
system("/etc/init.d/radsecproxy start");
}
else
{
LOGI("Not DR. Stop radsecproxy service.");
system("/etc/init.d/radsecproxy stop");
}
out:
free(buf);
return;
}
static bool hs20_download_icon(char *icon_name, char *icon_url)
@@ -936,6 +1141,7 @@ static void hs20_vif_config(struct blob_buf *b,
int i = 0;
unsigned int len = 0;
char domain_name[256];
char str[3] = {};
if (hs2conf->enable) {
blobmsg_add_bool(b, "interworking", 1);
@@ -1048,6 +1254,20 @@ static void hs20_vif_config(struct blob_buf *b,
if (strlen(hs2conf->wan_metrics))
blobmsg_add_string(b, "hs20_wan_metrics", hs2conf->wan_metrics);
len = strlen(hs2conf->ipaddr_type_availability);
if (len)
{
if (len == 1)
{
snprintf(str, sizeof(str), "0%s", hs2conf->ipaddr_type_availability);
blobmsg_add_string(b, "ipaddr_type_availability", str);
}
else
{
blobmsg_add_string(b, "ipaddr_type_availability", hs2conf->ipaddr_type_availability);
}
}
n = blobmsg_open_array(b, "hs20_oper_friendly_name");
for (i = 0; i < hs2conf->operator_friendly_name_len; i++)
{
@@ -1064,6 +1284,13 @@ static void hs20_vif_config(struct blob_buf *b,
blobmsg_add_u32(b, "venue_type", venue_type);
}
n = blobmsg_open_array(b, "hs20_conn_capab");
for (i = 0; i < hs2conf->connection_capability_len; i++)
{
blobmsg_add_string(b, NULL, hs2conf->connection_capability[i]);
}
blobmsg_close_array(b, n);
if (hs2conf->operator_icons_len)
{
n = blobmsg_open_array(b, "operator_icon");
@@ -1084,14 +1311,17 @@ static void hs20_vif_config(struct blob_buf *b,
bool target_vif_config_del(const struct schema_Wifi_VIF_Config *vconf)
{
struct uci_package *wireless;
struct uci_context *vif_ctx;
struct uci_element *e = NULL, *tmp = NULL;
const char *ifname;
int ret=0;
int ret = 0;
vlan_del((char *)vconf->if_name);
ret= uci_load(uci, "wireless", &wireless);
vif_ctx = uci_alloc_context();
ret= uci_load(vif_ctx, "wireless", &wireless);
if (ret) {
LOGD("%s: uci_load() failed with rc %d", vconf->if_name, ret);
LOGE("%s: %s uci_load() failed with rc %d", vconf->if_name, __func__, ret);
uci_free_context(vif_ctx);
return false;
}
uci_foreach_element_safe(&wireless->sections, tmp, e) {
@@ -1099,14 +1329,15 @@ bool target_vif_config_del(const struct schema_Wifi_VIF_Config *vconf)
if ((s == NULL) || (s->type == NULL)) continue;
if (strcmp(s->type, "wifi-iface")) continue;
ifname = uci_lookup_option_string( uci, s, "ifname" );
ifname = uci_lookup_option_string( vif_ctx, s, "ifname" );
if (!strcmp(ifname,vconf->if_name)) {
uci_section_del(uci, "vif", "wireless", (char *)s->e.name, "wifi-iface");
uci_section_del(vif_ctx, "vif", "wireless", (char *)s->e.name, "wifi-iface");
break;
}
}
uci_commit(uci, &wireless, false);
uci_unload(uci, wireless);
uci_commit(vif_ctx, &wireless, false);
uci_unload(vif_ctx, wireless);
uci_free_context(vif_ctx);
reload_config = 1;
return true;
}
@@ -1299,7 +1530,6 @@ static int ap_vif_config_set(const struct schema_Wifi_Radio_Config *rconf,
blob_buf_init(&b, 0);
blob_buf_init(&del,0);
blobmsg_add_string(&b, "ifname", vconf->if_name);
blobmsg_add_string(&b, "device", rconf->if_name);
blobmsg_add_string(&b, "mode", "ap");
@@ -1335,10 +1565,9 @@ static int ap_vif_config_set(const struct schema_Wifi_Radio_Config *rconf,
blobmsg_add_string(&b, "min_hw_mode", vconf->min_hw_mode);
if (changed->ft_psk || changed->ft_mobility_domain) {
if (vconf->ft_psk && vconf->ft_mobility_domain) {
if (vconf->ft_mobility_domain) {
blobmsg_add_bool(&b, "ieee80211r", 1);
blobmsg_add_hex16(&b, "mobility_domain", vconf->ft_mobility_domain);
blobmsg_add_bool(&b, "ft_psk_generate_local", vconf->ft_psk);
blobmsg_add_bool(&b, "ft_over_ds", 0);
blobmsg_add_bool(&b, "reassociation_deadline", 1);
} else {
@@ -1385,9 +1614,8 @@ static int ap_vif_config_set(const struct schema_Wifi_Radio_Config *rconf,
blobmsg_add_bool(&b, "wpa_disable_eapol_key_retries", 1);
blobmsg_add_u32(&b, "channel", rconf->channel);
if (vif_config_security_set(&b, vconf)) {
return -1;
}
if (vif_config_security_set(&b, vconf))
return -1;
if (changed->custom_options)
vif_config_custom_opt_set(&b, &del, vconf);

View File

@@ -75,7 +75,7 @@ int rrm_setup_monitor(void);
void rrm_channel_init(void);
int rrm_ubus_init(struct ev_loop *loop);
int ubus_get_noise(const char *if_name, uint32_t *noise);
int ubus_set_channel_switch(const char *if_name, uint32_t frequency);
int ubus_set_channel_switch(const char *if_name, uint32_t frequency, int channel_bandwidth, int sec_chan_offset);
void set_rrm_parameters(rrm_entry_t *rrm_data);
ds_tree_t* rrm_get_rrm_config_list(void);
ds_tree_t* rrm_get_radio_list(void);

View File

@@ -94,6 +94,15 @@ radio_entry_t* rrm_get_radio_config(radio_type_t band)
}
return NULL;
}
void get_channel_bandwidth(const char* htmode, int *channel_bandwidth)
{
if(!strcmp(htmode, "HT20"))
*channel_bandwidth=20;
else if (!strcmp(htmode, "HT40"))
*channel_bandwidth=40;
else if(!strcmp(htmode, "HT80"))
*channel_bandwidth=80;
}
void rrm_nf_timer_handler(struct ev_loop *loop, ev_timer *timer, int revents)
{
@@ -154,16 +163,26 @@ void rrm_nf_timer_handler(struct ev_loop *loop, ev_timer *timer, int revents)
if (nf > nf_drop_threshold)
{
LOGD("[%s] backup=%d nf=%d nf_lwm=%d drop=%d thresh=%d",
LOGI("Interference detected on [%s], switching to backup_channel=%d nf=%d nf_lwm=%d drop=%d thresh=%d",
radio->config.if_name,
rrm_config->rrm_data.backup_channel,
nf,
rrm_config->rrm_data.noise_lwm,
rrm_config->rrm_data.snr_percentage_drop,
nf_drop_threshold);
int channel_bandwidth;
int sec_chan_offset=0;
struct mode_map *m = mode_map_get_uci(radio->schema.freq_band, get_max_channel_bw_channel(ieee80211_channel_to_frequency(rrm_config->rrm_data.backup_channel),
radio->schema.ht_mode), radio->schema.hw_mode);
if (m) {
sec_chan_offset = m->sec_channel_offset;
} else
LOGE("failed to get channel offset");
get_channel_bandwidth(get_max_channel_bw_channel(ieee80211_channel_to_frequency(rrm_config->rrm_data.backup_channel),
radio->schema.ht_mode), &channel_bandwidth);
ubus_set_channel_switch(radio->config.if_name,
ieee80211_channel_to_frequency(rrm_config->rrm_data.backup_channel));
ieee80211_channel_to_frequency(rrm_config->rrm_data.backup_channel), channel_bandwidth, sec_chan_offset);
}
}
}

View File

@@ -51,7 +51,7 @@ int ubus_get_noise(const char *if_name, uint32_t *noise)
}
int ubus_set_channel_switch(const char *if_name, uint32_t frequency)
int ubus_set_channel_switch(const char *if_name, uint32_t frequency, int channel_bandwidth, int sec_chan_offset)
{
uint32_t id;
static struct blob_buf b;
@@ -61,10 +61,21 @@ int ubus_set_channel_switch(const char *if_name, uint32_t frequency)
if (ubus_lookup_id(ubus, path, &id))
return -1;
blob_buf_init(&b, 0);
if (channel_bandwidth == 20 || channel_bandwidth == 40) {
blobmsg_add_bool(&b, "ht", 1);
} else if (channel_bandwidth == 80) {
blobmsg_add_bool(&b, "vht", 1);
}
if (channel_bandwidth == 40 || channel_bandwidth == 80) {
blobmsg_add_u32(&b, "center_freq1", frequency+30);
}
blobmsg_add_u32(&b, "freq", frequency);
blobmsg_add_u32(&b, "bcn_count", 1);
blobmsg_add_u32(&b, "bcn_count", 5);
blobmsg_add_u32(&b, "bandwidth", channel_bandwidth);
blobmsg_add_u32(&b, "sec_channel_offset", sec_chan_offset);
return ubus_invoke(ubus, id, "switch_chan", b.head, NULL, NULL, 1000);
}

View File

@@ -130,6 +130,7 @@ static int rx_msg(struct nl_msg *msg, void* arg)
struct nlattr *attr[GENL_UCC_ATTR_MAX+1];
struct voip_session *data;
char dst_ip[16];
genlmsg_parse(nlmsg_hdr(msg), 0, attr,
GENL_UCC_ATTR_MAX, genl_ucc_policy);
@@ -140,7 +141,6 @@ static int rx_msg(struct nl_msg *msg, void* arg)
return NL_OK;
}
char *dst_ip = malloc(16);
memset(dst_ip, 0, 16);
if((get_current_ip(dst_ip, IAC_IFACE)) < 0) {
LOGI("Error: Cannot get IP for %s", IAC_IFACE);
@@ -249,48 +249,31 @@ int main(int argc, char ** argv)
backtrace_init();
json_memdbg_init(loop);
#if 0
if (!dpp_init())
{
LOG(ERR,
"Initializing SM "
"(Failed to init DPP library)");
return -1;
}
if (!uccm_mqtt_init())
{
LOG(ERR,
"Initializing SM "
"(Failed to start MQTT)");
return -1;
}
#endif
if (!ovsdb_init_loop(loop, "UCCM")) {
LOGEM("Initializing UCCM (Failed to initialize OVSDB)");
return -1;
}
evsched_init(loop);
callback cb = recv_process;
LOGI("Call interap_recv");
if( interap_recv(IAC_VOIP_PORT, cb, sizeof(struct voip_session),
loop, &iac_io) < 0)
loop, &iac_io) < 0) {
interap_rcv_close();
LOGI("Error: Failed InterAP receive");
return 1;
}
// task_init();
evsched_init(loop);
netlink_listen(loop);
// command_ubus_init(loop);
ev_run(loop, 0);
if (!ovsdb_stop_loop(loop))
LOGE("Stopping UCCM (Failed to stop OVSDB");
#if 0
uccm_mqtt_stop();
#endif
ev_default_destroy();
interap_rcv_close();
LOGN("Exiting UCCM");
return 0;

View File

@@ -463,6 +463,19 @@ dpp_event_record_alloc()
return record;
}
static inline dpp_event_channel_switch_t *
dpp_event_channel_switch_alloc()
{
dpp_event_channel_switch_t *record = NULL;
record = calloc(1, sizeof(dpp_event_channel_switch_t));
if (record) {
memset(record, 0, sizeof(dpp_event_channel_switch_t));
}
return record;
}
static inline void
dpp_event_channel_record_free(dpp_event_channel_switch_t *record)
{

View File

@@ -105,7 +105,6 @@ static void sm_events_report_clear_client(ds_dlist_t *report_list)
static void sm_events_report_clear_channel(ds_dlist_t *report_list)
{
if (!ds_dlist_is_empty(report_list)) {
dpp_event_channel_switch_t *record = NULL;
ds_dlist_iter_t record_iter;
@@ -129,6 +128,8 @@ static void sm_events_report(EV_P_ ev_timer *w, int revents)
/* Event Record */
dpp_event_record_t *dpp_record = NULL;
dpp_event_record_t *sm_record = NULL;
dpp_event_channel_switch_t *dpp_record_cs = NULL;
dpp_event_channel_switch_t *sm_record_cs = NULL;
ds_dlist_iter_t record_iter;
dpp_events_report_timer_restart(report_timer);
@@ -153,8 +154,23 @@ static void sm_events_report(EV_P_ ev_timer *w, int revents)
ds_dlist_insert_tail(&report_ctx->client_event_list, dpp_record);
}
if(!ds_dlist_is_empty(&g_event_report.channel_switch_list))
report_ctx->channel_switch_list = g_event_report.channel_switch_list;
for (sm_record_cs = ds_dlist_ifirst(&record_iter, &g_event_report.channel_switch_list); sm_record_cs != NULL; sm_record_cs = ds_dlist_inext(&record_iter)) {
dpp_record_cs = dpp_event_channel_switch_alloc();
dpp_record_cs->channel_event.band = sm_record_cs->channel_event.band;
dpp_record_cs->channel_event.reason = sm_record_cs->channel_event.reason;
dpp_record_cs->channel_event.freq = sm_record_cs->channel_event.freq;
dpp_record_cs->channel_event.timestamp = sm_record_cs->channel_event.timestamp;
ds_dlist_iremove(&record_iter);
dpp_event_channel_record_free(sm_record_cs);
sm_record_cs = NULL;
if (ds_dlist_is_empty(&report_ctx->channel_switch_list)) {
ds_dlist_init(&report_ctx->channel_switch_list, dpp_event_channel_switch_t, node);
}
ds_dlist_insert_tail(&report_ctx->channel_switch_list, dpp_record_cs);
}
if (!ds_dlist_is_empty(&report_ctx->client_event_list) || !ds_dlist_is_empty(&report_ctx->channel_switch_list)) {
LOG(DEBUG, "Sending events report...");

View File

@@ -19,6 +19,16 @@ enum {
SYSTEM_ATTR_FIRMWARE,
SYSTEM_ATTR_REDIRECTOR,
SYSTEM_ATTR_INACTIVEFW,
SYSTEM_ATTR_SKU,
SYSTEM_ATTR_MODEL_REV,
SYSTEM_ATTR_MODEL_DESCR,
SYSTEM_ATTR_MANUFACT_NAME,
SYSTEM_ATTR_MANUFACT_DATE,
SYSTEM_ATTR_MANUFACT_URL,
SYSTEM_ATTR_MANUF_ABBR,
SYSTEM_ATTR_REF_DESIGN,
SYSTEM_ATTR_CERT_REGION,
SYSTEM_ATTR_MAC_ADDR,
__SYSTEM_ATTR_MAX,
};
@@ -29,6 +39,16 @@ static const struct blobmsg_policy system_policy[__SYSTEM_ATTR_MAX] = {
[SYSTEM_ATTR_FIRMWARE] = { .name = "firmware", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_REDIRECTOR] = { .name = "redirector", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_INACTIVEFW] = { .name = "inactivefw", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_SKU] = { .name = "sku_number", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_MODEL_REV] = { .name = "revision", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_MODEL_DESCR] = { .name = "model_description", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_MANUFACT_NAME] = { .name = "manufacturer_name", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_MANUFACT_DATE] = { .name = "manufacturer_date", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_MANUFACT_URL] = { .name = "manufacturer_url", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_MANUF_ABBR] = { .name = "manuf_abbr", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_REF_DESIGN] = { .name = "reference_design", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_CERT_REGION] = { .name = "certification_region", .type = BLOBMSG_TYPE_STRING },
[SYSTEM_ATTR_MAC_ADDR] = { .name = "id", .type = BLOBMSG_TYPE_STRING },
};
const struct uci_blob_param_list system_param = {
@@ -110,6 +130,56 @@ bool target_platform_version_get(void *buf, size_t len)
return copy_data(SYSTEM_ATTR_PLATFORM, buf, len);
}
bool target_sku_get(void *buf, size_t len)
{
return copy_data(SYSTEM_ATTR_SKU, buf, len);
}
bool target_model_revision_get(void *buf, size_t len)
{
return copy_data(SYSTEM_ATTR_MODEL_REV, buf, len);
}
bool target_model_description_get(void *buf, size_t len)
{
return copy_data(SYSTEM_ATTR_MODEL_DESCR, buf, len);
}
bool target_manuf_name_get(void *buf, size_t len)
{
return copy_data(SYSTEM_ATTR_MANUFACT_NAME, buf, len);
}
bool target_manuf_date_get(void *buf, size_t len)
{
return copy_data(SYSTEM_ATTR_MANUFACT_DATE, buf, len);
}
bool target_manuf_url_get(void *buf, size_t len)
{
return copy_data(SYSTEM_ATTR_MANUFACT_URL, buf, len);
}
bool target_manuf_abbr_get(void *buf, size_t len)
{
return copy_data(SYSTEM_ATTR_MANUF_ABBR, buf, len);
}
bool target_ref_design_get(void *buf, size_t len)
{
return copy_data(SYSTEM_ATTR_REF_DESIGN, buf, len);
}
bool target_cert_region_get(void *buf, size_t len)
{
return copy_data(SYSTEM_ATTR_CERT_REGION, buf, len);
}
bool target_mac_addr_get(void *buf, size_t len)
{
return copy_data(SYSTEM_ATTR_MAC_ADDR, buf, len);
}
bool target_device_config_register(void *awlan_cb)
{
struct schema_AWLAN_Node awlan;

View File

@@ -0,0 +1,25 @@
#!/bin/sh
[ "$ACTION" = ifup -o "$ACTION" = ifupdate ] || exit 0
[ "$INTERFACE" = wan ] || exit 0
conflict=0
wan_ipaddr="$(ubus call network.interface.wan status | grep \"address\" | grep -oE '[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}')"
lan_ipaddr="$(ubus call network.interface.lan status | grep \"address\" | grep -oE '[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}')"
logger -t hotplug "$ACTION of $INTERFACE ($DEVICE) $wan_ipaddr"
[ "$wan_ipaddr" = "192.168.1" ] && [ "$lan_ipaddr" = "192.168.1" ] && {
conflict=1
dest_ip="192.168.0.1"
}
[ "$wan_ipaddr" = "192.168.0" ] && [ "$lan_ipaddr" = "192.168.0" ] && {
conflict=1
dest_ip="192.168.1.1"
}
[ $conflict = 1 ] && {
logger -t hotplug "IP conflict with br-wan. Switch br-lan to $dest_ip"
uci set network.lan.ipaddr="$dest_ip"
uci_commit
reload_config
}
exit 0

View File

@@ -2,22 +2,120 @@
. /lib/functions.sh
SKU="unknown"
MODEL=""
PLATFORM="unknown"
SERIAL=""
MODEL_REV="unknown"
MODEL_DESCR="unknown"
MANUF_NAME="unknown"
MANUF_DATE="unknown"
MANUF_URL="unknown"
MANUF_DESIGN="unknown"
REF_DESIGN="unknown"
CERT_REGION="unknown"
ID=""
case "$(board_name)" in
edgecore,ecw5211|\
edgecore,ecw5410)
MODEL=$(cat /tmp/sysinfo/board_name | sed "s/edgecore,//" | tr [a-z] [A-Z])
SERIAL=$(cat /sys/class/net/eth0/address | tr -d :)
PLATFORM=$(cat /tmp/sysinfo/model)
SERIAL=$(cat /dev/mtd5 | grep serial_number | cut -d "=" -f2)
MODEL=$(cat /dev/mtd5 | grep "model=" | cut -d "=" -f2)
if [ ! $MODEL ]; then
MODEL=$(cat /tmp/sysinfo/board_name | sed "s/edgecore,//" | tr [a-z] [A-Z])
fi
SKU=$(cat /dev/mtd5 | grep sku | cut -d "=" -f2)
CERT_REGION=$(cat /dev/mtd5 | grep certification_region | cut -d "=" -f2)
ID=$(cat /dev/mtd5 | grep mac_address | cut -d "=" -f2)
MANUF_DATE=$(cat /dev/mtd5 | grep manufacturer_date | cut -d "=" -f2)
MANUF_NAME=$(cat /dev/mtd5 | grep manufacturer_name | cut -d "=" -f2)
if [ ! $MANUF_NAME ]; then
MANUF_NAME="Edge-Core"
fi
MANUF_ABBR="EC"
MANUF_URL=$(cat /dev/mtd5 | grep manufacturer_url | cut -d "=" -f2)
MODEL_DESCR=$(cat /dev/mtd5 | grep model_description | cut -d "=" -f2)
MODEL_REV=$(cat /dev/mtd5 | grep model_revision | cut -d "=" -f2)
REF_DESIGN=$(cat /dev/mtd5 | grep reference_design | cut -d "=" -f2)
;;
cig,wf194c)
MODEL=$(cat /tmp/sysinfo/board_name)
SERIAL=$(cat cat /dev/mtd14 | grep BaseMacAddress | cut -dx -f2 | tr -d '\r\n')
PLATFORM=$(cat /tmp/sysinfo/model)
SERIAL=$(cat /dev/mtd14 | grep serial_number | cut -d "=" -f2)
if [ ! $SERIAL ]; then
SERIAL=$(cat /dev/mtd14 | grep BaseMacAddress | cut -dx -f2)
fi
MODEL=$(cat /dev/mtd14 | grep "model=" | cut -d "=" -f2)
SKU=$(cat /dev/mtd14 | grep sku | cut -d "=" -f2)
CERT_REGION=$(cat /dev/mtd14 | grep certification_region | cut -d "=" -f2)
ID=$(cat /dev/mtd14 | grep mac_address | cut -d "=" -f2)
MANUF_DATE=$(cat /dev/mtd14 | grep manufacturer_date | cut -d "=" -f2)
MANUF_NAME=$(cat /dev/mtd14 | grep manufacturer_name | cut -d "=" -f2)
if [ ! $MANUF_NAME ]; then
MANUF_NAME="CIG"
fi
MANUF_ABBR="CIG"
MANUF_URL=$(cat /dev/mtd14 | grep manufacturer_url | cut -d "=" -f2)
MODEL_DESCR=$(cat /dev/mtd14 | grep model_description | cut -d "=" -f2)
MODEL_REV=$(cat /dev/mtd14 | grep model_revision | cut -d "=" -f2)
REF_DESIGN=$(cat /dev/mtd14 | grep reference_design | cut -d "=" -f2)
;;
cig,wf188n)
PLATFORM=$(cat /tmp/sysinfo/model)
SERIAL=$(cat /dev/mtd12 | grep serial_number | cut -d "=" -f2)
MODEL=$(cat /dev/mtd12 | grep "model=" | cut -d "=" -f2)
SKU=$(cat /dev/mtd12 | grep sku | cut -d "=" -f2)
CERT_REGION=$(cat /dev/mtd12 | grep certification_region | cut -d "=" -f2)
ID=$(cat /dev/mtd12 | grep mac_address | cut -d "=" -f2)
MANUF_DATE=$(cat /dev/mtd12 | grep manufacturer_date | cut -d "=" -f2)
MANUF_NAME=$(cat /dev/mtd12 | grep manufacturer_name | cut -d "=" -f2)
if [ ! $MANUF_NAME ]; then
MANUF_NAME="CIG"
fi
MANUF_ABBR="CIG"
MANUF_URL=$(cat /dev/mtd12 | grep manufacturer_url | cut -d "=" -f2)
MODEL_DESCR=$(cat /dev/mtd12 | grep model_description | cut -d "=" -f2)
MODEL_REV=$(cat /dev/mtd12 | grep model_revision | cut -d "=" -f2)
REF_DESIGN=$(cat /dev/mtd12 | grep reference_design | cut -d "=" -f2)
;;
linksys,ea8300)
MODEL=$(grep modelNumber= /dev/mtd9 | tr -d '\r\n' | sed "s/modelNumber=//")
SERIAL=$(grep serial_number= /dev/mtd9 | tr -d '\r\n' | sed "s/serial_number=//")
PLATFORM=OPENWRT_EA8300
PLATFORM="OPENWRT_EA8300"
MODEL_REV=$(cat /dev/mtd9 | grep hw_revision | cut -d "=" -f2 | tr -d '\r\n')
MODEL_DESCR=$(cat /dev/mtd9 | grep modelDescription | cut -d "=" -f2 | tr -d '\r\n')
MANUF_URL=$(cat /dev/mtd9 | grep manufacturerURL | cut -d "=" -f2 | tr -d '\r\n')
CERT_REGION=$(cat /dev/mtd9 | grep cert_region | cut -d "=" -f2 | tr -d '\r\n')
ID=$(cat /dev/mtd9 | grep hw_mac_addr | cut -d "=" -f2 | tr -d '\r\n')
MANUF_NAME=$(cat /dev/mtd9 | grep "manufacturer=" | cut -d "=" -f2 | tr -d '\r\n')
if [ ! $MANUF_NAME ]; then
MANUF_NAME="Linksys"
fi
MANUF_ABBR="LS"
MANUF_DATE=$(cat /dev/mtd9 | grep manufacturer_date | cut -d "=" -f2 | tr -d '\r\n')
YEAR=$(echo "$MANUF_DATE" | cut -d "/" -f1)
MONTH=$(echo "$MANUF_DATE" | cut -d "/" -f2)
DAY=$(echo "$MANUF_DATE" | cut -d "/" -f3)
MANUF_DATE="$DAY-$MONTH-$YEAR"
;;
tp-link,ec420-g1)
PLATFORM=$(cat /tmp/sysinfo/model)
SERIAL=$(cat /dev/mtd9 | grep serial_number | cut -d "=" -f2)
MODEL=$(cat /dev/mtd9 | grep "model=" | cut -d "=" -f2)
SKU=$(cat /dev/mtd9 | grep sku | cut -d "=" -f2)
CERT_REGION=$(cat /dev/mtd9 | grep certification_region | cut -d "=" -f2)
ID=$(cat /dev/mtd9 | grep mac_address | cut -d "=" -f2)
MANUF_DATE=$(cat /dev/mtd9 | grep manufacturer_date | cut -d "=" -f2)
MANUF_NAME=$(cat /dev/mtd9 | grep manufacturer_name | cut -d "=" -f2)
if [ ! $MANUF_NAME ]; then
MANUF_NAME="Proware (TP-Link)"
fi
MANUF_ABBR="PW"
MANUF_URL=$(cat /dev/mtd9 | grep manufacturer_url | cut -d "=" -f2)
MODEL_DESCR=$(cat /dev/mtd9 | grep model_description | cut -d "=" -f2)
MODEL_REV=$(cat /dev/mtd9 | grep model_revision | cut -d "=" -f2)
REF_DESIGN=$(cat /dev/mtd9 | grep reference_design | cut -d "=" -f2)
;;
*)
MODEL=$(cat /tmp/sysinfo/board_name)
@@ -28,9 +126,41 @@ esac
MODEL=$(echo $MODEL | sed "s/.*,//" | tr [a-z] [A-Z])
# fallback check to get the serial number from mac address if flash does not contain this info.
if [ ! $SERIAL ]; then
SERIAL=$(cat /sys/class/net/eth0/address | tr -d :)
fi
# fallback check to get the id from mac address if flash does not contain this info.
if [ ! $ID ]; then
ID=$(cat /sys/class/net/eth0/address)
fi
# fallback check to get the model if flash does not contain this info.
if [ ! $MODEL ]; then
MODEL=$(cat /tmp/sysinfo/board_name)
fi
# Read the active firmware version info
FIRMWARE=$(cat /usr/opensync/.versions | grep FW_IMAGE_ACTIVE | grep -o '[^-]*$')
if [ ! $FIRMWARE ]; then
FIRMWARE=$(cat /usr/opensync/.versions | grep FW_VERSION | cut -d ":" -f2)
fi
uci set system.tip=tip
uci set system.tip.serial="${SERIAL}"
uci set system.tip.model="${MODEL}"
uci set system.tip.platform="${PLATFORM}"
uci set system.tip.firmware='0.1.0'
uci set system.tip.firmware="${FIRMWARE}"
uci set system.tip.sku_number="${SKU}"
uci set system.tip.revision="${MODEL_REV}"
uci set system.tip.model_description="${MODEL_DESCR}"
uci set system.tip.manufacturer_name="${MANUF_NAME}"
uci set system.tip.manufacturer_date="${MANUF_DATE}"
uci set system.tip.manufacturer_url="${MANUF_URL}"
uci set system.tip.reference_design="${REF_DESIGN}"
uci set system.tip.certification_region="${CERT_REGION}"
uci set system.tip.id="${ID}"
uci set system.tip.manuf_abbr="${MANUF_ABBR}"
uci commit

View File

@@ -2,6 +2,8 @@
uci set network.wan.type=bridge
uci set network.wan6.ifname=@wan
uci set network.wan.metric=1
uci set network.lan.metric=10
uci set network.wan.vlan_filtering=1
uci set network.lan.vlan_filtering=1
exit 0

View File

@@ -12281,14 +12281,14 @@ index 0000000000..6b0eb2f831
++ pinctrl-names = "default";
++
++ led@25 {
++ label = "wifi5g";
++ gpios = <&tlmm 35 GPIO_ACTIVE_HIGH>;
++ label = "green:wifi5";
++ gpios = <&tlmm 35 GPIO_ACTIVE_LOW>;
++ linux,default-trigger = "wf188:green:5g";
++ default-state = "off";
++ };
++ led@24 {
++ label = "wifi2g";
++ gpios = <&tlmm 37 GPIO_ACTIVE_HIGH>;
++ label = "green:wifi2";
++ gpios = <&tlmm 37 GPIO_ACTIVE_LOW>;
++ linux,default-trigger = "wf188:green:2g";
++ default-state = "off";
++ };

View File

@@ -0,0 +1,81 @@
From 1f9978564420818d4ce4bdbb08fce2eca7c13d8e Mon Sep 17 00:00:00 2001
From: Rick Sommerville <rick.sommerville@netexperience.com>
Date: Sun, 23 May 2021 14:36:03 -0400
Subject: [PATCH] Preserve certificates and redirector over factory-reset
---
package/base-files/files/etc/rc.button/reset | 2 +-
.../patches/001-jffs2reset-keep-option | 48 +++++++++++++++++++
2 files changed, 49 insertions(+), 1 deletion(-)
create mode 100644 package/system/fstools/patches/001-jffs2reset-keep-option
diff --git a/package/base-files/files/etc/rc.button/reset b/package/base-files/files/etc/rc.button/reset
index 2403122ad2..56c0548ec9 100755
--- a/package/base-files/files/etc/rc.button/reset
+++ b/package/base-files/files/etc/rc.button/reset
@@ -23,7 +23,7 @@ released)
elif [ "$SEEN" -ge 5 -a -n "$OVERLAY" ]
then
echo "FACTORY RESET" > /dev/console
- jffs2reset -y && reboot &
+ wlan_ap_factory_reset.sh
fi
;;
esac
diff --git a/package/system/fstools/patches/001-jffs2reset-keep-option b/package/system/fstools/patches/001-jffs2reset-keep-option
new file mode 100644
index 0000000000..50209ea276
--- /dev/null
+++ b/package/system/fstools/patches/001-jffs2reset-keep-option
@@ -0,0 +1,48 @@
+--- a/jffs2reset.c
++++ b/jffs2reset.c
+@@ -40,7 +40,7 @@ ask_user(void)
+ return 0;
+ }
+
+-static int jffs2_reset(struct volume *v, int reset)
++static int jffs2_reset(struct volume *v, int reset, int keep)
+ {
+ char *mp;
+
+@@ -48,7 +48,7 @@ static int jffs2_reset(struct volume *v,
+ if (mp) {
+ ULOG_INFO("%s is mounted as %s, only erasing files\n", v->blk, mp);
+ fs_state_set("/overlay", FS_STATE_PENDING);
+- overlay_delete(mp, false);
++ overlay_delete(mp, keep);
+ mount(mp, "/", NULL, MS_REMOUNT, 0);
+ } else {
+ ULOG_INFO("%s is not mounted\n", v->blk);
+@@ -93,8 +93,8 @@ static int jffs2_mark(struct volume *v)
+ int main(int argc, char **argv)
+ {
+ struct volume *v;
+- int ch, yes = 0, reset = 0;
+- while ((ch = getopt(argc, argv, "yr")) != -1) {
++ int ch, yes = 0, reset = 0, keep = 0;
++ while ((ch = getopt(argc, argv, "yrk")) != -1) {
+ switch(ch) {
+ case 'y':
+ yes = 1;
+@@ -102,6 +102,9 @@ int main(int argc, char **argv)
+ case 'r':
+ reset = 1;
+ break;
++ case 'k':
++ keep = 1;
++ break;
+ }
+
+ }
+@@ -128,5 +131,5 @@ int main(int argc, char **argv)
+ volume_init(v);
+ if (!strcmp(*argv, "jffs2mark"))
+ return jffs2_mark(v);
+- return jffs2_reset(v, reset);
++ return jffs2_reset(v, reset, keep);
+ }
--
2.17.1

View File

@@ -0,0 +1,46 @@
From 5380b0204d97a79669243b46a8750e038e6a0a19 Mon Sep 17 00:00:00 2001
From: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
Date: Wed, 14 Apr 2021 11:14:45 -0400
Subject: [PATCH] netifd: Dont renew dhcp on bridge topo change
Do not renew the dhcp on bridge topology change
as this causes some of the dhcp servers to fail.
This occurs when many interfaces are added on to
a bridge and for every interface there is a dhcp
renew. The server considers receiving renew many
times in a quick succession as a DOS attack. So for
now we disable dhcp lease renew when a new interface
is added.
Signed-off-by: Chaitanya Godavarthi <chaitanya.kiran@netexperience.com>
---
.../netifd/patches/0104-fix-dhcp-issue.patch | 17 +++++++++++++++++
1 file changed, 17 insertions(+)
create mode 100644 package/network/config/netifd/patches/0104-fix-dhcp-issue.patch
diff --git a/package/network/config/netifd/patches/0104-fix-dhcp-issue.patch b/package/network/config/netifd/patches/0104-fix-dhcp-issue.patch
new file mode 100644
index 0000000000..6f1d2e708e
--- /dev/null
+++ b/package/network/config/netifd/patches/0104-fix-dhcp-issue.patch
@@ -0,0 +1,17 @@
+Index: netifd-2019-08-05-5e02f944/interface.c
+===================================================================
+--- netifd-2019-08-05-5e02f944.orig/interface.c
++++ netifd-2019-08-05-5e02f944/interface.c
+@@ -424,7 +424,11 @@ interface_main_dev_cb(struct device_user
+ interface_set_link_state(iface, false);
+ break;
+ case DEV_EVENT_TOPO_CHANGE:
+- interface_proto_event(iface->proto, PROTO_CMD_RENEW, false);
++ /* This renews the dhcp lease when the bridge adds/deletes a
++ * new interface. It causes some dhcp servers to fail in
++ * case where there are many interfaces being added to the
++ * bridge frequently. Disabling this for now. */
++ /* interface_proto_event(iface->proto, PROTO_CMD_RENEW, false); */
+ return;
+ default:
+ break;
--
2.25.1

View File

@@ -0,0 +1,31 @@
From 4a85624a667c4027bf09f6155fbb046ac588a20a Mon Sep 17 00:00:00 2001
From: ravi vaishnav <ravi.vaishnav@netexperience.com>
Date: Thu, 22 Apr 2021 16:36:52 -0400
Subject: [PATCH] base-files: Increase Socket buffer memory size
When configuring 16 VLAN, we see hostapd complaining
about No buffer space available while handling receive
events. Hence, increasing the socket buffer memory size
to 512KB.
Signed-off-by: ravi vaishnav <ravi.vaishnav@netexperience.com>
---
package/base-files/files/etc/sysctl.d/10-default.conf | 5 +++++
1 file changed, 5 insertions(+)
diff --git a/package/base-files/files/etc/sysctl.d/10-default.conf b/package/base-files/files/etc/sysctl.d/10-default.conf
index bc8c579695..aeda9153a8 100644
--- a/package/base-files/files/etc/sysctl.d/10-default.conf
+++ b/package/base-files/files/etc/sysctl.d/10-default.conf
@@ -25,3 +25,8 @@ net.ipv4.tcp_dsack=1
net.ipv6.conf.default.forwarding=1
net.ipv6.conf.all.forwarding=1
+
+net.core.wmem_default = 524288
+net.core.rmem_default = 524288
+net.core.wmem_max = 524288
+net.core.rmem_max = 524288
--
2.25.1

View File

@@ -0,0 +1,39 @@
From dc2e1e24e5a69face7d154fea6d3ecbee6c90e45 Mon Sep 17 00:00:00 2001
From: Arif Alam <arif.alam@netexperience.com>
Date: Wed, 28 Apr 2021 19:29:23 -0400
Subject: [PATCH] netifd: Add WPA3 Enterprise modes
Add configuration options for:
- WPA3 Enterprise Only mode
- WPA3 Enterprise Transition mode
Signed-off-by: Arif Alam <arif.alam@netexperience.com>
---
.../patches/0105-add-wpa3-enterprise-modes.patch | 15 +++++++++++++++
1 file changed, 15 insertions(+)
create mode 100644 package/network/config/netifd/patches/0105-add-wpa3-enterprise-modes.patch
diff --git a/package/network/config/netifd/patches/0105-add-wpa3-enterprise-modes.patch b/package/network/config/netifd/patches/0105-add-wpa3-enterprise-modes.patch
new file mode 100644
index 0000000000..9018365807
--- /dev/null
+++ b/package/network/config/netifd/patches/0105-add-wpa3-enterprise-modes.patch
@@ -0,0 +1,15 @@
+--- a/scripts/netifd-wireless.sh
++++ b/scripts/netifd-wireless.sh
+@@ -244,8 +244,11 @@ wireless_vif_parse_encryption() {
+ owe*)
+ auth_type=owe
+ ;;
++ wpa3-only*)
++ auth_type=eap-only
++ ;;
+ wpa3-mixed*)
+- auth_type=eap-eap192
++ auth_type=eap-transition
+ ;;
+ wpa3*)
+ auth_type=eap192
--
2.25.1

View File

@@ -0,0 +1,156 @@
From 4a5ac0aa04a5e6cf9316ce7c16843f0f4a4128ce Mon Sep 17 00:00:00 2001
From: John Crispin <john@phrozen.org>
Date: Wed, 12 May 2021 07:00:18 +0200
Subject: [PATCH] ipq807x: fix edgecore eap102
* import the fixes for the update hardware revision
Signed-off-by: John Crispin <john@phrozen.org>
---
target/linux/ipq807x/base-files/etc/board.d/02_network | 5 +----
target/linux/ipq807x/base-files/etc/init.d/bootcount | 3 ++-
target/linux/ipq807x/base-files/lib/upgrade/platform.sh | 4 ++--
.../arch/arm64/boot/dts/qcom/qcom-ipq807x-eap102.dts | 8 ++++----
target/linux/ipq807x/image/ipq60xx.mk | 6 +++---
target/linux/ipq807x/image/ipq807x.mk | 2 +-
6 files changed, 13 insertions(+), 15 deletions(-)
diff --git a/target/linux/ipq807x/base-files/etc/board.d/02_network b/target/linux/ipq807x/base-files/etc/board.d/02_network
index f23a9f3eac..e90a73f7bf 100755
--- a/target/linux/ipq807x/base-files/etc/board.d/02_network
+++ b/target/linux/ipq807x/base-files/etc/board.d/02_network
@@ -28,6 +28,7 @@ qcom_setup_interfaces()
ucidef_set_interface_wan "eth0"
;;
cig,wf194c|\
+ edgecore,eap102|\
sercomm,wallaby)
ucidef_set_interface_lan "eth0"
ucidef_set_interface_wan "eth1"
@@ -36,10 +37,6 @@ qcom_setup_interfaces()
ucidef_set_interface_lan "eth1 eth2"
ucidef_set_interface_wan "eth0"
;;
- edgecore,eap102)
- ucidef_set_interface_lan "eth1"
- ucidef_set_interface_wan "eth0"
- ;;
esac
}
diff --git a/target/linux/ipq807x/base-files/etc/init.d/bootcount b/target/linux/ipq807x/base-files/etc/init.d/bootcount
index ac345d6d4a..a24f27353e 100755
--- a/target/linux/ipq807x/base-files/etc/init.d/bootcount
+++ b/target/linux/ipq807x/base-files/etc/init.d/bootcount
@@ -4,7 +4,8 @@ START=99
boot() {
case "$(board_name)" in
- edgecore,eap101)
+ edgecore,eap101|\
+ edgecore,eap102)
fw_setenv bootcount 0
;;
esac
diff --git a/target/linux/ipq807x/base-files/lib/upgrade/platform.sh b/target/linux/ipq807x/base-files/lib/upgrade/platform.sh
index 59d1578925..a520df40d7 100755
--- a/target/linux/ipq807x/base-files/lib/upgrade/platform.sh
+++ b/target/linux/ipq807x/base-files/lib/upgrade/platform.sh
@@ -48,7 +48,6 @@ platform_do_upgrade() {
;;
cig,wf188n|\
cig,wf194c|\
- edgecore,eap102|\
qcom,ipq6018-cp01|\
qcom,ipq807x-hk01|\
sercomm,wallaby|\
@@ -56,7 +55,8 @@ platform_do_upgrade() {
tplink,ex227)
nand_upgrade_tar "$1"
;;
- edgecore,eap101)
+ edgecore,eap101|\
+ edgecore,eap102)
CI_UBIPART="rootfs1"
nand_upgrade_tar "$1"
;;
diff --git a/target/linux/ipq807x/files/arch/arm64/boot/dts/qcom/qcom-ipq807x-eap102.dts b/target/linux/ipq807x/files/arch/arm64/boot/dts/qcom/qcom-ipq807x-eap102.dts
index e8157f5514..cf822c246e 100755
--- a/target/linux/ipq807x/files/arch/arm64/boot/dts/qcom/qcom-ipq807x-eap102.dts
+++ b/target/linux/ipq807x/files/arch/arm64/boot/dts/qcom/qcom-ipq807x-eap102.dts
@@ -32,8 +32,8 @@
* Aliases as required by u-boot
* to patch MAC addresses
*/
- ethernet0 = "/soc/dp5";
- ethernet1 = "/soc/dp6";
+ ethernet0 = "/soc/dp6";
+ ethernet1 = "/soc/dp5";
led-boot = &led_power;
led-failsafe = &led_power;
@@ -593,7 +593,7 @@
};
};
- dp1 {
+/* dp1 {
device_type = "network";
compatible = "qcom,nss-dp";
qcom,id = <1>;
@@ -639,7 +639,7 @@
qcom,link-poll = <1>;
qcom,phy-mdio-addr = <3>;
phy-mode = "sgmii";
- };
+ };*/
dp5 {
device_type = "network";
diff --git a/target/linux/ipq807x/image/ipq60xx.mk b/target/linux/ipq807x/image/ipq60xx.mk
index c536a174f8..201885a760 100644
--- a/target/linux/ipq807x/image/ipq60xx.mk
+++ b/target/linux/ipq807x/image/ipq60xx.mk
@@ -7,7 +7,7 @@ define Device/cig_wf188
SUPPORTED_DEVICES := cig,wf188
IMAGES := sysupgrade.tar
IMAGE/sysupgrade.tar/squashfs := append-rootfs | pad-rootfs | sysupgrade-tar rootfs=$$$$@ | append-metadata
- DEVICE_PACKAGES := ath11k-wifi-cig-wf188 uboot-env
+ DEVICE_PACKAGES := ath11k-wifi-cig-wf188 uboot-envtools
endef
TARGET_DEVICES += cig_wf188
@@ -16,7 +16,7 @@ define Device/cig_wf188n
DEVICE_DTS := qcom-ipq6018-cig-wf188n
DEVICE_DTS_CONFIG := config@cp03-c1
SUPPORTED_DEVICES := cig,wf188n
- DEVICE_PACKAGES := ath11k-wifi-cig-wf188n uboot-env
+ DEVICE_PACKAGES := ath11k-wifi-cig-wf188n uboot-envtools
endef
TARGET_DEVICES += cig_wf188n
@@ -25,7 +25,7 @@ define Device/edgecore_eap101
DEVICE_DTS := qcom-ipq6018-edgecore-eap101
DEVICE_DTS_CONFIG := config@cp01-c1
SUPPORTED_DEVICES := edgecore,eap101
- DEVICE_PACKAGES := ath11k-wifi-edgecore-eap101 uboot-env
+ DEVICE_PACKAGES := ath11k-wifi-edgecore-eap101 uboot-envtools
endef
TARGET_DEVICES += edgecore_eap101
diff --git a/target/linux/ipq807x/image/ipq807x.mk b/target/linux/ipq807x/image/ipq807x.mk
index 7081769407..000d2793c9 100644
--- a/target/linux/ipq807x/image/ipq807x.mk
+++ b/target/linux/ipq807x/image/ipq807x.mk
@@ -41,7 +41,7 @@ define Device/edgecore_eap102
DEVICE_DTS := qcom-ipq807x-eap102
DEVICE_DTS_CONFIG=config@ac02
SUPPORTED_DEVICES := edgecore,eap102
- DEVICE_PACKAGES := ath11k-wifi-edgecore-eap102 kmod-usb3 kmod-usb2
+ DEVICE_PACKAGES := ath11k-wifi-edgecore-eap102 kmod-usb2 uboot-envtools
endef
TARGET_DEVICES += edgecore_eap102
define Device/tplink_ex227
--
2.25.1

View File

@@ -60,6 +60,7 @@ packages:
- kmod-ip6-tunnel
- kmod-iptunnel
- kmod-iptunnel6
- logrotate
diffconfig: |
CONFIG_OPENSSL_ENGINE=y

View File

@@ -39,6 +39,7 @@ packages:
- luci-mod-simple
- luci-theme-tip
- nft-qos
- openssl-util
- openvswitch
- openvswitch-common
- openvswitch-libofproto
@@ -77,6 +78,9 @@ packages:
- kmod-iptunnel
- kmod-iptunnel6
- eapol-test
- apc
- radsecproxy
- logrotate
diffconfig: |
CONFIG_OPENSSL_ENGINE=y