Request for feature - Scan while AP
by KeithG
I mentioned this a while ago and am wondering if this is on the list
of features to add. Currently, we start as connman/iwd, but if we do
not get an IP address, we stop iwd then start hostapd and advertise as
an AP for initial setup. When a user connects, he/she can scan for
availabel SSIDS and set then up.
I know iwd can run in AP mode, but it cannot scan while in AP mode. As
it is, hostapd does this for us, so we have a work around. I was
wondering if this functionality is in the works.
Regards,
Keith
4 months
[PATCH v3 1/4] scan: add support for scanning on AP interface type
by James Prestwood
This adds a new flag, force_ap to the scan parameters. When enabled
this will set NL80211_SCAN_FLAG_AP.
---
src/scan.c | 3 +++
src/scan.h | 1 +
2 files changed, 4 insertions(+)
v3:
* Removed the feature check.
diff --git a/src/scan.c b/src/scan.c
index 12b7a3fd..b0824e72 100644
--- a/src/scan.c
+++ b/src/scan.c
@@ -391,6 +391,9 @@ static struct l_genl_msg *scan_build_cmd(struct scan_context *sc,
NL80211_EXT_FEATURE_SCAN_RANDOM_SN))
flags |= NL80211_SCAN_FLAG_RANDOM_SN;
+ if (params->ap_scan)
+ flags |= NL80211_SCAN_FLAG_AP;
+
if (flags)
l_genl_msg_append_attr(msg, NL80211_ATTR_SCAN_FLAGS, 4, &flags);
diff --git a/src/scan.h b/src/scan.h
index 2c401df6..ba11a508 100644
--- a/src/scan.h
+++ b/src/scan.h
@@ -98,6 +98,7 @@ struct scan_parameters {
bool randomize_mac_addr_hint : 1;
bool no_cck_rates : 1;
bool duration_mandatory : 1;
+ bool ap_scan : 1;
const uint8_t *ssid; /* Used for direct probe request */
size_t ssid_len;
const uint8_t *source_mac;
--
2.34.1
4 months
[PATCH v2 1/7] scan: add scan_bss_get_security
by James Prestwood
This was already implemented in station but with no dependency on
that module at all. AP will need this for a scanning API so its
being moved into scan.c.
---
src/scan.c | 17 +++++++++++++++++
src/scan.h | 2 ++
2 files changed, 19 insertions(+)
diff --git a/src/scan.c b/src/scan.c
index 1ab6420b..7c510df8 100644
--- a/src/scan.c
+++ b/src/scan.c
@@ -1680,6 +1680,23 @@ int scan_bss_get_rsn_info(const struct scan_bss *bss, struct ie_rsn_info *info)
return 0;
}
+int scan_bss_get_security(const struct scan_bss *bss, enum security *security)
+{
+ int ret;
+ struct ie_rsn_info info;
+
+ ret = scan_bss_get_rsn_info(bss, &info);
+ if (ret < 0) {
+ if (ret != -ENOENT)
+ return ret;
+
+ *security = security_determine(bss->capability, NULL);
+ } else
+ *security = security_determine(bss->capability, &info);
+
+ return 0;
+}
+
int scan_bss_rank_compare(const void *a, const void *b, void *user_data)
{
const struct scan_bss *new_bss = a, *bss = b;
diff --git a/src/scan.h b/src/scan.h
index 81cb9e46..2c401df6 100644
--- a/src/scan.h
+++ b/src/scan.h
@@ -28,6 +28,7 @@ struct p2p_probe_req;
struct p2p_beacon;
struct mmpdu_header;
struct wiphy;
+enum security;
enum scan_state {
SCAN_STATE_NOT_RUNNING,
@@ -161,6 +162,7 @@ void scan_bss_free(struct scan_bss *bss);
int scan_bss_rank_compare(const void *a, const void *b, void *user);
int scan_bss_get_rsn_info(const struct scan_bss *bss, struct ie_rsn_info *info);
+int scan_bss_get_security(const struct scan_bss *bss, enum security *security);
struct scan_bss *scan_bss_new_from_probe_req(const struct mmpdu_header *mpdu,
const uint8_t *body,
--
2.34.1
4 months
[PATCH v4] network: add 6GHz restrictions to network_can_connect_bss
by James Prestwood
The 802.11ax standards adds some restrictions for the 6GHz band. In short
stations must use SAE, OWE, or 8021x on this band and frame protection is
required.
---
src/network.c | 58 +++++++++++++++++++++++++++++++++++++++------------
1 file changed, 45 insertions(+), 13 deletions(-)
v4:
* Renamed label to mfp_no_tkip
* Fixed missing parentheses after IS_SAE
diff --git a/src/network.c b/src/network.c
index 4e7af27c..7330126e 100644
--- a/src/network.c
+++ b/src/network.c
@@ -55,6 +55,7 @@
#include "src/util.h"
#include "src/erp.h"
#include "src/handshake.h"
+#include "src/band.h"
#define SAE_PT_SETTING "SAE-PT-Group%u"
@@ -774,6 +775,7 @@ int network_can_connect_bss(struct network *network, const struct scan_bss *bss)
struct network_config *config = info ? &info->config : NULL;
bool can_transition_disable = wiphy_can_transition_disable(wiphy);
struct ie_rsn_info rsn;
+ enum band_freq band;
int ret;
switch (security) {
@@ -785,6 +787,9 @@ int network_can_connect_bss(struct network *network, const struct scan_bss *bss)
return -ENOSYS;
}
+ if (!band_freq_to_channel(bss->frequency, &band))
+ return -ENOTSUP;
+
memset(&rsn, 0, sizeof(rsn));
ret = scan_bss_get_rsn_info(bss, &rsn);
if (ret < 0) {
@@ -797,6 +802,13 @@ int network_can_connect_bss(struct network *network, const struct scan_bss *bss)
* We assume the spec means us to check bit 3 here
*/
if (ret == -ENOENT && security == SECURITY_NONE) {
+ /*
+ * 802.11ax 12.12.2 - STA shall not use Open System
+ * authentication without encryption
+ */
+ if (band == BAND_FREQ_6_GHZ)
+ return -EPERM;
+
if (!config)
return 0;
@@ -814,26 +826,21 @@ int network_can_connect_bss(struct network *network, const struct scan_bss *bss)
return ret;
}
- if (!config || !config->have_transition_disable)
+ if (!config || !config->have_transition_disable) {
+ if (band == BAND_FREQ_6_GHZ)
+ goto mfp_no_tkip;
+
goto no_transition_disable;
+ }
if (!can_transition_disable) {
+ if (band == BAND_FREQ_6_GHZ)
+ return -EPERM;
+
l_debug("HW not capable of Transition Disable, skip");
goto no_transition_disable;
}
- /*
- * WPA3 Specification, v3, Section 8:
- * - Disable use of WEP and TKIP
- * - Disallow association without negotiation of PMF
- */
- rsn.pairwise_ciphers &= ~IE_RSN_CIPHER_SUITE_TKIP;
-
- if (!rsn.group_management_cipher)
- return -EPERM;
-
- rsn.mfpr = true;
-
/* WPA3-Personal */
if (test_bit(&config->transition_disable, 0)) {
rsn.akm_suites &= ~IE_RSN_AKM_SUITE_PSK;
@@ -851,6 +858,31 @@ int network_can_connect_bss(struct network *network, const struct scan_bss *bss)
return -EPERM;
}
+mfp_no_tkip:
+ /*
+ * WPA3 Specification, v3, Section 8:
+ * - Disable use of WEP and TKIP
+ * - Disallow association without negotiation of PMF
+ */
+ rsn.pairwise_ciphers &= ~IE_RSN_CIPHER_SUITE_TKIP;
+
+ if (!rsn.group_management_cipher)
+ return -EPERM;
+
+ rsn.mfpr = true;
+
+ /* 802.11ax Section 12.12.2 */
+ if (band == BAND_FREQ_6_GHZ) {
+ /* STA shall not use the following cipher suite selectors */
+ rsn.pairwise_ciphers &= ~IE_RSN_CIPHER_SUITE_USE_GROUP_CIPHER;
+
+ /* Basically the STA must use OWE, SAE, or 8021x */
+ if (!IE_AKM_IS_SAE(rsn.akm_suites) &&
+ !IE_AKM_IS_8021X(rsn.akm_suites) &&
+ (!(rsn.akm_suites | IE_RSN_AKM_SUITE_OWE)))
+ return -EPERM;
+ }
+
no_transition_disable:
if (!wiphy_select_cipher(wiphy, rsn.pairwise_ciphers))
return -ENOTSUP;
--
2.34.1
4 months
[PATCH v3 1/7] ie: update IE_AKM_IS_SAE to bitwise comparison
by James Prestwood
All uses of this macro will work with a bitwise comparison which is
needed for 6GHz checks and somewhat more flexible since it can be
used to compare RSN info, not only single AKM values.
---
src/ie.h | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/src/ie.h b/src/ie.h
index 302cda70..9b57cf66 100644
--- a/src/ie.h
+++ b/src/ie.h
@@ -337,8 +337,8 @@ enum ie_rsn_akm_suite {
};
#define IE_AKM_IS_SAE(akm) \
- ((akm == IE_RSN_AKM_SUITE_SAE_SHA256) || \
- (akm == IE_RSN_AKM_SUITE_FT_OVER_SAE_SHA256))
+ (akm & (IE_RSN_AKM_SUITE_SAE_SHA256 | \
+ IE_RSN_AKM_SUITE_FT_OVER_SAE_SHA256))
#define IE_AKM_IS_FT(akm) \
(akm & (IE_RSN_AKM_SUITE_FT_OVER_8021X | \
--
2.34.1
4 months, 1 week
[PATCH v2 1/3] network: add 6GHz restrictions to network_can_connect_bss
by James Prestwood
The 802.11ax standards adds some restrictions for the 6GHz band. In short
stations must use SAE, OWE, or 8021x on this band and frame protection is
required.
---
src/network.c | 34 ++++++++++++++++++++++++++++++++++
1 file changed, 34 insertions(+)
v2:
* Removed mfpr setting since this is enforced in station.c
diff --git a/src/network.c b/src/network.c
index 4e7af27c..0aa2d3af 100644
--- a/src/network.c
+++ b/src/network.c
@@ -55,6 +55,7 @@
#include "src/util.h"
#include "src/erp.h"
#include "src/handshake.h"
+#include "src/band.h"
#define SAE_PT_SETTING "SAE-PT-Group%u"
@@ -774,6 +775,7 @@ int network_can_connect_bss(struct network *network, const struct scan_bss *bss)
struct network_config *config = info ? &info->config : NULL;
bool can_transition_disable = wiphy_can_transition_disable(wiphy);
struct ie_rsn_info rsn;
+ enum band_freq band;
int ret;
switch (security) {
@@ -785,6 +787,9 @@ int network_can_connect_bss(struct network *network, const struct scan_bss *bss)
return -ENOSYS;
}
+ if (!band_freq_to_channel(bss->frequency, &band))
+ return -ENOTSUP;
+
memset(&rsn, 0, sizeof(rsn));
ret = scan_bss_get_rsn_info(bss, &rsn);
if (ret < 0) {
@@ -797,6 +802,13 @@ int network_can_connect_bss(struct network *network, const struct scan_bss *bss)
* We assume the spec means us to check bit 3 here
*/
if (ret == -ENOENT && security == SECURITY_NONE) {
+ /*
+ * 802.11ax 12.12.2 - STA shall not use Open System
+ * authentication without encryption
+ */
+ if (band == BAND_FREQ_6_GHZ)
+ return -EPERM;
+
if (!config)
return 0;
@@ -852,6 +864,28 @@ int network_can_connect_bss(struct network *network, const struct scan_bss *bss)
}
no_transition_disable:
+ /* 802.11ax Section 12.12.2 */
+ if (band == BAND_FREQ_6_GHZ) {
+ /* STA shall not use the following cipher suite selectors */
+ rsn.pairwise_ciphers &= ~IE_RSN_CIPHER_SUITE_USE_GROUP_CIPHER;
+ rsn.pairwise_ciphers &= ~IE_RSN_CIPHER_SUITE_TKIP;
+
+ /* STA shall not use the following AKM suite selectors */
+ rsn.akm_suites &= ~IE_RSN_AKM_SUITE_PSK;
+ rsn.akm_suites &= ~IE_RSN_AKM_SUITE_PSK_SHA256;
+ rsn.akm_suites &= ~IE_RSN_AKM_SUITE_FT_USING_PSK;
+
+ /* Basically the STA must use OWE, SAE, or 8021x */
+ if (!(rsn.akm_suites & (IE_RSN_AKM_SUITE_8021X |
+ IE_RSN_AKM_SUITE_FT_OVER_8021X |
+ IE_RSN_AKM_SUITE_8021X_SHA256 |
+ IE_RSN_AKM_SUITE_SAE_SHA256 |
+ IE_RSN_AKM_SUITE_FT_OVER_SAE_SHA256 |
+ IE_RSN_AKM_SUITE_FT_OVER_8021X_SHA384 |
+ IE_RSN_AKM_SUITE_OWE)))
+ return -EPERM;
+ }
+
if (!wiphy_select_cipher(wiphy, rsn.pairwise_ciphers))
return -ENOTSUP;
--
2.34.1
4 months, 1 week
[PATCH 01/11] band: add operating clases for 802.11ax
by James Prestwood
Obtained from the IEEE 802.11ax amendment, Table E-4
---
src/band.c | 63 +++++++++++++++++++++++++++++++++++++++++++++++-------
1 file changed, 55 insertions(+), 8 deletions(-)
diff --git a/src/band.c b/src/band.c
index 9024d186..28ba6a62 100644
--- a/src/band.c
+++ b/src/band.c
@@ -489,8 +489,8 @@ static int band_channel_info_get_bandwidth(const struct band_chandef *info)
struct operating_class_info {
uint32_t starting_frequency;
uint32_t flags;
- uint8_t channel_set[20];
- uint8_t center_frequencies[8];
+ uint8_t channel_set[60];
+ uint8_t center_frequencies[30];
uint16_t channel_spacing;
uint8_t operating_class;
};
@@ -598,20 +598,20 @@ static const struct operating_class_info e4_operating_classes[] = {
{
.operating_class = 125,
.starting_frequency = 5000,
- .channel_set = { 149, 153, 157, 161, 165, 169, 173},
+ .channel_set = { 149, 153, 157, 161, 165, 169, 173, 177 },
.channel_spacing = 20,
},
{
.operating_class = 126,
.starting_frequency = 5000,
- .channel_set = { 149, 157, 165},
+ .channel_set = { 149, 157, 165, 173 },
.channel_spacing = 40,
.flags = PRIMARY_CHANNEL_LOWER,
},
{
.operating_class = 127,
.starting_frequency = 5000,
- .channel_set = { 153, 161, 169 },
+ .channel_set = { 153, 161, 169, 177 },
.channel_spacing = 40,
.flags = PRIMARY_CHANNEL_UPPER,
},
@@ -619,21 +619,68 @@ static const struct operating_class_info e4_operating_classes[] = {
.operating_class = 128,
.starting_frequency = 5000,
.channel_spacing = 80,
- .center_frequencies = { 42, 58, 106, 122, 138, 155 },
+ .center_frequencies = { 42, 58, 106, 122, 138, 155, 171 },
},
{
.operating_class = 129,
.starting_frequency = 5000,
.channel_spacing = 160,
- .center_frequencies = { 50, 114 },
+ .center_frequencies = { 50, 114, 163 },
},
{
.operating_class = 130,
.starting_frequency = 5000,
.channel_spacing = 80,
- .center_frequencies = { 42, 58, 106, 122, 138, 155 },
+ .center_frequencies = { 42, 58, 106, 122, 138, 155, 171 },
.flags = PLUS80,
},
+ {
+ .operating_class = 131,
+ .starting_frequency = 5950,
+ .channel_spacing = 20,
+ .channel_set = { 1, 5, 9, 13, 17, 21, 25, 29, 33, 37, 41, 45,
+ 49, 53, 57, 61, 65, 69, 73, 77, 81, 85, 89, 93,
+ 97, 101, 105, 109, 113, 117, 121, 125, 129, 133,
+ 137, 141, 145, 149, 153, 157, 161, 165, 169,
+ 173, 177, 181, 185, 189, 193, 197, 201, 205,
+ 209, 213, 217, 221, 225, 229, 233 },
+ },
+ {
+ .operating_class = 132,
+ .starting_frequency = 5950,
+ .channel_spacing = 40,
+ .center_frequencies = { 3, 11, 19, 27, 35, 43, 51, 59, 67, 75,
+ 83, 91, 99, 107, 115, 123, 131, 139,
+ 147, 155, 163, 171, 179, 187, 195, 203,
+ 211, 219, 227 },
+ },
+ {
+ .operating_class = 133,
+ .starting_frequency = 5950,
+ .channel_spacing = 80,
+ .center_frequencies = { 7, 23, 39, 55, 71, 87, 103, 119, 135,
+ 151, 167, 183, 199, 215 },
+ },
+ {
+ .operating_class = 134,
+ .starting_frequency = 5950,
+ .channel_spacing = 160,
+ .center_frequencies = { 15, 47, 79, 111, 143, 175, 207 },
+ },
+ {
+ .operating_class = 135,
+ .starting_frequency = 5950,
+ .channel_spacing = 80,
+ .center_frequencies = { 7, 23, 39, 55, 71, 87, 102, 119, 135,
+ 151, 167, 183, 199, 215 },
+ .flags = PLUS80,
+ },
+ {
+ .operating_class = 136,
+ .starting_frequency = 5950,
+ .channel_spacing = 20,
+ .center_frequencies = { 2 },
+ }
};
static const struct operating_class_info *e4_find_opclass(uint32_t opclass)
--
2.34.1
4 months, 1 week
lib to iwd
by Joakim Lotsengård
Hi,
TL;DR:
Is there any lib for iwd/iwctl (like libnm for NetworkManager) written
in C that will scan + GetOrderNetworks + configure a SSID+passphrase.
Goal is to configure an IoT device using a side-channel, typically
bluetooth. If not, would iwd-project accept that we contributed such a
work? How would you want that in such a case?
Longer:
I am new to iwd but I have long experience developing IoT products
using embedded Linux with WiFi. My background and understanding of
WiFi, routing and IP in general is rather high.
Today we have a rather ordinary IoT Linux-based product. It has one
ethernet port and a WiFi-card. It's based on a DiGi module. We are
using Bluetooth (BLE) and an app (for both Android and iPhone) to
configure the SSID the first time. We are using wpa_supplicant +
NetworkManager today. We have our own written daemon that talks
bluetooth with our app, and configures the SSID+any pass via libnm for
NetworkManager.
Our problem:
WiFi works badly and we had to hack a 'wifi watchdog' to kick
wpa_supplicant (via rfkill or even restart NetworkManager). The nmlib
usage we have suffers from bad threading and general mischief. It got
worse with the rewrite of the backend in libnm in 1.22. We want to
remove both NetworkManager and wpa_supplicant and only use iwd.
Problem is that there seems to be no corresponding "libnm" towards
iwd. One has to implement the DBUS API, rather than just use a lib. We
only need:
- Scan
- GetOrderedNetworks -> Present to user over bluetooth in an app.
- Configure user selected SSID and passphrase (only supporting
WPA2-PSK and possibly Open is fine).
With iwd this is simple compared to many other solutions, but still
not just straight forward. DBUS is "complicated". I think this is a
very common operation many IoT devices want to do. You configure the
single SSID over a side-channel (bluetooth typically). You want a
single SSID configured. A lib that helps with this very exact
operation would benefit many projects.
We can't use Python. Target does not have Python. It must be in C (or
C++) to match the other half of the daemon we have to configure WiFi
over Bluetooth.
I know DPP, but:
We really want to use our current app and solution which is a protocol
over bluetooth we developed ourselves. Also, iPhone does not support
DPP. In general the DPP support out there seems poor and not really
ready for the big masses. Please correct me if I am wrong.
We only want a minor "libiwd" or "libiwctl" just like libnm that can
configure an IoT device's SSID via a side channel. How can we do this
the easiest and most standard way?
(QR-code: If you go to our web-site you might figure out that we do
have a display on our device. A QR-code way if DPP might be possible.
However, we rather do it the bluetooth way due to legacy and for
security reasons. The device is installed in Hotels where guests have
access. With bluetooth we can add a check of "overship".)
Contribution:
If there is no such lib the company I work for (Orbital Systems) might
be willing to contribute such a work. Under any applicable license
(LGPL?). Basically take code from iwctl and make a lib. A small lib
focused on only getting that (single?) SSID configured. I would guess
the lib can be expanded to cover the full DBUS API of iwd, but that is
not our goal currently. I think there are many
projects/devices/products out there that want to configure the SSID
via a side-channel by code and not via iwctl. How would iwd community
recommend this be done?
(I also asked on the IRC channel, but there wasn't much traffic there
so I moved it to the mailing-list.)
--
Thanks, keeping being Awesome
Joakim Lotsengård - Orbital Systems AB - www.orbital-systems.com
4 months, 1 week
[PATCH] sae: define _GNU_SOURCE for reallocarray definition
by James Prestwood
sae.c was failing to build on some platforms:
error: implicit declaration of function 'reallocarray'; did you mean 'realloc'?
[-Werror=implicit-function-declaration]
---
src/sae.c | 1 +
1 file changed, 1 insertion(+)
diff --git a/src/sae.c b/src/sae.c
index a4150628..859ec94b 100644
--- a/src/sae.c
+++ b/src/sae.c
@@ -24,6 +24,7 @@
#include <config.h>
#endif
+#define _GNU_SOURCE
#include <stdlib.h>
#include <ell/ell.h>
--
2.34.1
4 months, 1 week
[PATCH] tools: change print to %zd for ssize_t
by James Prestwood
iwd-decrypt-profile was using %ld which isn't portable.
---
tools/iwd-decrypt-profile.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/tools/iwd-decrypt-profile.c b/tools/iwd-decrypt-profile.c
index e660c346..e71b56b4 100644
--- a/tools/iwd-decrypt-profile.c
+++ b/tools/iwd-decrypt-profile.c
@@ -196,7 +196,7 @@ int main(int argc, char *argv[])
close(fd);
if (len < 0) {
- printf("Unable to write to %s (%ld)\n", outfile, len);
+ printf("Unable to write to %s (%zd)\n", outfile, len);
goto failed;
}
}
--
2.34.1
4 months, 1 week