wireless-ap: Enable ACS only for ath* devices
authorMichael Tremer <michael.tremer@ipfire.org>
Thu, 21 Mar 2019 19:22:56 +0000 (20:22 +0100)
committerMichael Tremer <michael.tremer@ipfire.org>
Thu, 21 Mar 2019 19:22:56 +0000 (20:22 +0100)
Signed-off-by: Michael Tremer <michael.tremer@ipfire.org>
src/functions/functions.hostapd
src/functions/functions.phy
src/functions/functions.wireless
src/hooks/ports/wireless-ap

index 57f8c1e..9024ab2 100644 (file)
@@ -111,6 +111,12 @@ hostapd_config_write() {
                assert isset key
        fi
 
+       # With channel 0, ACS must be supported
+       if [ ${channel} -eq 0 ] && ! wireless_supports_acs "${device}"; then
+               error "ACS requested, but not supported by ${device}"
+               return ${EXIT_ERROR}
+       fi
+
        # Check channel bandwidth for validity
        if isset channel_bandwidth && ! wireless_channel_bandwidth_is_valid "${mode}" "${channel_bandwidth}"; then
                error "Invalid channel bandwidth for ${mode}: ${channel_bandwidth}"
index 064ca7b..ee0f2a2 100644 (file)
@@ -189,6 +189,28 @@ phy_supports_ht_capability() {
        list_match "${capability}" $(__phy_list_ht_capabilities "${phy}")
 }
 
+# Returns TRUE if the PHY supports ACS
+phy_supports_acs() {
+       local phy="${1}"
+       assert isset phy
+
+       local driver="$(phy_get_driver "${phy}")"
+       if ! isset driver; then
+               return ${EXIT_ERROR}
+       fi
+
+       # This is basically a whilelist of drivers which support this
+       # There is no better detection
+       case "${driver}" in
+               ath10k_*|ath9k|ath5k)
+                       return ${EXIT_TRUE}
+                       ;;
+               *)
+                       return ${EXIT_FALSE}
+                       ;;
+       esac
+}
+
 # Returns TRUE if the PHY supports DFS
 phy_supports_dfs() {
        local phy="${1}"
index 0437d27..9e72fe0 100644 (file)
@@ -536,6 +536,19 @@ wireless_get_vht_caps() {
        network-phy-list-vht-caps "${phy}"
 }
 
+wireless_supports_acs() {
+       local device="${1}"
+       assert isset device
+
+       local phy="$(device_get_phy "${device}")"
+       if ! isset phy; then
+               log ERROR "Could not determine PHY for ${device}"
+               return ${EXIT_ERROR}
+       fi
+
+       phy_supports_acs "${phy}"
+}
+
 wireless_supports_dfs() {
        local device="${1}"
        assert isset device
index 983f0f9..0c42b61 100644 (file)
@@ -28,7 +28,7 @@ HOOK_SETTINGS="${HOOK_SETTINGS} ENCRYPTION KEY SSID"
 
 ADDRESS=$(mac_generate)
 BROADCAST_SSID=on
-CHANNEL=0
+CHANNEL=
 CHANNEL_BANDWIDTH=
 ENCRYPTION=""
 KEY=""
@@ -125,6 +125,13 @@ hook_parse_cmdline() {
                return ${EXIT_ERROR}
        fi
 
+       # Automatically enable ACS if no channel is set and ACS is available
+       if ! isset CHANNEL && phy_supports_acs "${PHY}"; then
+               CHANNEL="0"
+
+               log INFO "Automatic Channel Selection (ACS) enabled"
+       fi
+
        # Channel bandwidth must match the mode
        if isset CHANNEL_BANDWIDTH && ! wireless_channel_bandwidth_is_valid "${MODE}" "${CHANNEL_BANDWIDTH}"; then
                error "Channel Bandwidth '${CHANNEL_BANDWIDTH}' is not supported for ${MODE}"