Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/platform/Linux/ConnectivityManagerImpl.h
Original file line number Diff line number Diff line change
Expand Up @@ -217,7 +217,7 @@ class ConnectivityManagerImpl final : public ConnectivityManager,
bool mPafChannelAvailable = true;
#endif

bool _GetBssInfo(const gchar * bssPath, NetworkCommissioning::WiFiScanResponse & result);
CHIP_ERROR _GetBssInfo(const char * bssPath, NetworkCommissioning::WiFiScanResponse & result);

CHIP_ERROR _StartWiFiManagement();
CHIP_ERROR _StopWiFiManagement();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1118,45 +1118,24 @@ CHIP_ERROR ConnectivityManagerImpl::CommitConfig()

CHIP_ERROR ConnectivityManagerImpl::GetWiFiBssId(MutableByteSpan & value)
{
constexpr size_t bssIdSize = 6;
static_assert(kMaxHardwareAddrSize >= bssIdSize, "We are assuming we can fit a BSSID in a buffer of size kMaxHardwareAddrSize");
VerifyOrReturnError(value.size() >= bssIdSize, CHIP_ERROR_BUFFER_TOO_SMALL);
WiFiScanResponse bssInfo;
static_assert(kMaxHardwareAddrSize >= sizeof(bssInfo.bssid),
"We are assuming we can fit a BSSID in a buffer of size kMaxHardwareAddrSize");
VerifyOrReturnError(value.size() >= sizeof(bssInfo.bssid), CHIP_ERROR_BUFFER_TOO_SMALL);

CHIP_ERROR err = CHIP_ERROR_READ_FAILED;
struct ifaddrs * ifaddr = nullptr;
std::lock_guard<std::mutex> lock(mWpaSupplicantMutex);

// On Linux simulation, we don't have the DBus API to get the BSSID of connected AP. Use mac address
// of local WiFi network card instead.
if (getifaddrs(&ifaddr) == -1)
{
ChipLogError(DeviceLayer, "Failed to get network interfaces");
}
else
{
// Walk through linked list, maintaining head pointer so we can free list later.
for (struct ifaddrs * ifa = ifaddr; ifa != nullptr; ifa = ifa->ifa_next)
{
if (ConnectivityUtils::GetInterfaceConnectionType(ifa->ifa_name) == InterfaceTypeEnum::kWiFi)
{
if (ConnectivityUtils::GetInterfaceHardwareAddrs(ifa->ifa_name, value.data(), kMaxHardwareAddrSize) !=
CHIP_NO_ERROR)
{
ChipLogError(DeviceLayer, "Failed to get WiFi network hardware address");
}
else
{
// Set 48-bit IEEE MAC Address
value.reduce_size(bssIdSize);
err = CHIP_NO_ERROR;
break;
}
}
}
VerifyOrReturnError(mWpaSupplicant.iface, CHIP_ERROR_INCORRECT_STATE);

freeifaddrs(ifaddr);
}
const char * bssPath = wpa_supplicant_1_interface_get_current_bss(mWpaSupplicant.iface.get());
VerifyOrReturnError(bssPath != nullptr, CHIP_ERROR_INCORRECT_STATE);
Comment thread
arkq marked this conversation as resolved.
Outdated

return err;
ReturnErrorOnFailure(_GetBssInfo(bssPath, bssInfo));

memcpy(value.data(), bssInfo.bssid, sizeof(bssInfo.bssid));
value.reduce_size(sizeof(bssInfo.bssid));

return CHIP_NO_ERROR;
}

CHIP_ERROR ConnectivityManagerImpl::GetWiFiSecurityType(SecurityTypeEnum & securityType)
Expand Down Expand Up @@ -1385,7 +1364,7 @@ std::pair<WiFiBand, uint16_t> GetBandAndChannelFromFrequency(uint32_t freq)

} // namespace

bool ConnectivityManagerImpl::_GetBssInfo(const gchar * bssPath, NetworkCommissioning::WiFiScanResponse & result)
CHIP_ERROR ConnectivityManagerImpl::_GetBssInfo(const char * bssPath, NetworkCommissioning::WiFiScanResponse & result)
{
// This function can be called without g_main_context_get_thread_default() being set.
// The BSS proxy object is created in a synchronous manner, so the D-Bus call will be
Expand All @@ -1395,32 +1374,27 @@ bool ConnectivityManagerImpl::_GetBssInfo(const gchar * bssPath, NetworkCommissi
GAutoPtr<GError> err;
GAutoPtr<WpaSupplicant1BSS> bss(wpa_supplicant_1_bss_proxy_new_for_bus_sync(
G_BUS_TYPE_SYSTEM, G_DBUS_PROXY_FLAGS_NONE, kWpaSupplicantServiceName, bssPath, nullptr, &err.GetReceiver()));
VerifyOrReturnError(bss != nullptr, CHIP_ERROR_INCORRECT_STATE,
ChipLogError(DeviceLayer, WPA_SUPPLICANT_CLIENT_LOG_PREFIX "Failed to create BSS proxy: %s", err->message));

if (bss == nullptr)
{
return false;
}

WpaSupplicant1BSSProxy * bssProxy = WPA_SUPPLICANT_1_BSS_PROXY(bss.get());

GAutoPtr<GVariant> ssid(g_dbus_proxy_get_cached_property(G_DBUS_PROXY(bssProxy), "SSID"));
GAutoPtr<GVariant> bssid(g_dbus_proxy_get_cached_property(G_DBUS_PROXY(bssProxy), "BSSID"));
GVariant * ssid = wpa_supplicant_1_bss_get_ssid(bss.get());
GVariant * bssid = wpa_supplicant_1_bss_get_bssid(bss.get());

// Network scan is performed in the background, so the BSS
// may be gone when we try to get the properties.
if (ssid == nullptr || bssid == nullptr)
{
ChipLogDetail(DeviceLayer, WPA_SUPPLICANT_CLIENT_LOG_PREFIX "BSS not found: %s", StringOrNullMarker(bssPath));
return false;
return CHIP_ERROR_NOT_FOUND;
}

gsize ssidLen = 0;
gsize bssidLen = 0;
char bssidStr[2 * 6 + 5 + 1] = { 0 };
auto ssidStr = reinterpret_cast<const uint8_t *>(g_variant_get_fixed_array(ssid.get(), &ssidLen, sizeof(uint8_t)));
auto bssidBuf = reinterpret_cast<const uint8_t *>(g_variant_get_fixed_array(bssid.get(), &bssidLen, sizeof(uint8_t)));
gint16 signal = wpa_supplicant_1_bss_get_signal(bss.get());
guint16 frequency = wpa_supplicant_1_bss_get_frequency(bss.get());
auto ssidStr = reinterpret_cast<const uint8_t *>(g_variant_get_fixed_array(ssid, &ssidLen, sizeof(uint8_t)));
auto bssidBuf = reinterpret_cast<const uint8_t *>(g_variant_get_fixed_array(bssid, &bssidLen, sizeof(uint8_t)));
int16_t signal = wpa_supplicant_1_bss_get_signal(bss.get());
uint16_t frequency = wpa_supplicant_1_bss_get_frequency(bss.get());

if (bssidLen == 6)
{
Expand All @@ -1433,8 +1407,6 @@ bool ConnectivityManagerImpl::_GetBssInfo(const gchar * bssPath, NetworkCommissi
WPA_SUPPLICANT_CLIENT_LOG_PREFIX "Got a network with incorrect BSSID len: %" G_GSIZE_FORMAT " != 6", bssidLen);
bssidLen = 0;
}
ChipLogDetail(DeviceLayer, "Network Found: %s (%s) Signal:%d",
NullTerminated(StringOrNullMarker((const gchar *) ssidStr), ssidLen).c_str(), bssidStr, signal);

// Internal sentinel (bit 7). Not a real WiFiSecurityBitmap value; keeps an EAP-only
// network from being reported as Open. Masked off before the result is returned.
Expand Down Expand Up @@ -1515,25 +1487,10 @@ bool ConnectivityManagerImpl::_GetBssInfo(const gchar * bssPath, NetworkCommissi

return res;
};
auto GetNetworkSecurityType =
[IsNetworkWPAPSK, IsNetworkWPA2PSK](
WpaSupplicant1BSSProxy * proxy) -> chip::BitFlags<app::Clusters::NetworkCommissioning::WiFiSecurityBitmap> {
GAutoPtr<GVariant> wpa(g_dbus_proxy_get_cached_property(G_DBUS_PROXY(proxy), "WPA"));
GAutoPtr<GVariant> rsn(g_dbus_proxy_get_cached_property(G_DBUS_PROXY(proxy), "RSN"));

chip::BitFlags<app::Clusters::NetworkCommissioning::WiFiSecurityBitmap> res(IsNetworkWPAPSK(wpa.get()),
IsNetworkWPA2PSK(rsn.get()));
if (!res.HasAny())
{
res.Set(app::Clusters::NetworkCommissioning::WiFiSecurityBitmap::kUnencrypted);
}
res.Clear(kEAP);
return res;
};

// Drop the network if its SSID or BSSID is illegal.
VerifyOrReturnError(ssidLen <= kMaxWiFiSSIDLength, false);
VerifyOrReturnError(bssidLen == kWiFiBSSIDLength, false);
VerifyOrReturnError(ssidLen <= kMaxWiFiSSIDLength, CHIP_ERROR_INTERNAL);
VerifyOrReturnError(bssidLen == kWiFiBSSIDLength, CHIP_ERROR_INTERNAL);
memcpy(result.ssid, ssidStr, ssidLen);
memcpy(result.bssid, bssidBuf, bssidLen);
result.ssidLen = ssidLen;
Expand All @@ -1554,9 +1511,17 @@ bool ConnectivityManagerImpl::_GetBssInfo(const gchar * bssPath, NetworkCommissi
auto bandInfo = GetBandAndChannelFromFrequency(frequency);
result.wiFiBand = bandInfo.first;
result.channel = bandInfo.second;
result.security = GetNetworkSecurityType(bssProxy);

return true;
chip::BitFlags<app::Clusters::NetworkCommissioning::WiFiSecurityBitmap> networkSecurityType(
IsNetworkWPAPSK(wpa_supplicant_1_bss_get_wpa(bss.get())), IsNetworkWPA2PSK(wpa_supplicant_1_bss_get_rsn(bss.get())));
if (!networkSecurityType.HasAny())
{
networkSecurityType.Set(app::Clusters::NetworkCommissioning::WiFiSecurityBitmap::kUnencrypted);
}
networkSecurityType.Clear(kEAP);
result.security = networkSecurityType;

return CHIP_NO_ERROR;
}

void ConnectivityManagerImpl::_OnWpaInterfaceScanDone(WpaSupplicant1Interface * iface, gboolean success)
Expand All @@ -1576,8 +1541,12 @@ void ConnectivityManagerImpl::_OnWpaInterfaceScanDone(WpaSupplicant1Interface *
for (const char * bssPath = (bsss != nullptr ? *bsss : nullptr); bssPath != nullptr; bssPath = *(++bsss))
{
WiFiScanResponse network;
if (_GetBssInfo(bssPath, network))
if (_GetBssInfo(bssPath, network) == CHIP_NO_ERROR)
{
ChipLogDetail(DeviceLayer, "Network Found: %s (%02x:%02x:%02x:%02x:%02x:%02x) Signal: %d",
NullTerminated(StringOrNullMarker((const char *) network.ssid), network.ssidLen).c_str(),
network.bssid[0], network.bssid[1], network.bssid[2], network.bssid[3], network.bssid[4],
network.bssid[5], network.signal.strength);
Comment thread
arkq marked this conversation as resolved.
if (mInterestedSSID.empty() ||
(network.ssidLen == mInterestedSSID.size() &&
memcmp(network.ssid, mInterestedSSID.data(), mInterestedSSID.size()) == 0))
Expand Down
12 changes: 12 additions & 0 deletions src/platform/Linux/dbus/wpa/DBusWpaBss.xml
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,19 @@ limitations under the License.

<node>
<interface name="fi.w1.wpa_supplicant1.BSS">
<property name="SSID" type="ay" access="read">
<annotation name="org.gtk.GDBus.C.ForceGVariant" value="true" />
</property>
<property name="BSSID" type="ay" access="read">
<annotation name="org.gtk.GDBus.C.ForceGVariant" value="true" />
</property>
<property name="Signal" type="n" access="read" />
<property name="Frequency" type="q" access="read" />
<property name="WPA" type="a{sv}" access="read">
<annotation name="org.gtk.GDBus.C.ForceGVariant" value="true" />
</property>
<property name="RSN" type="a{sv}" access="read">
<annotation name="org.gtk.GDBus.C.ForceGVariant" value="true" />
</property>
</interface>
</node>
1 change: 1 addition & 0 deletions src/platform/Linux/dbus/wpa/DBusWpaInterface.xml
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,7 @@ the wpa_supplicant integration with the Matter SDK.
</signal>
<property name="State" type="s" access="read" />
<property name="Scanning" type="b" access="read" />
<property name="CurrentBSS" type="o" access="read" />
<property name="CurrentNetwork" type="o" access="read" />
<property name="CurrentAuthMode" type="s" access="read" />
<property name="BSSs" type="ao" access="read" />
Expand Down
Loading