Skip to content

Commit f4daf7f

Browse files
authored
LeakFix: Add StopWiFiManagement Method to clean-up WPA Supplicant's glib objects on glib main loop (project-chip#43755)
1 parent db5fe1b commit f4daf7f

3 files changed

Lines changed: 33 additions & 0 deletions

File tree

src/platform/Linux/ConnectivityManagerImpl.h

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -99,6 +99,15 @@ struct GDBusWpaSupplicant
9999
GAutoPtr<WpaSupplicant1Interface> iface;
100100
GAutoPtr<char> interfacePath;
101101
GAutoPtr<char> networkPath;
102+
103+
// Must be called synchronously on the GLib thread while the GLib main loop is still running.
104+
void Reset()
105+
{
106+
iface.reset();
107+
proxy.reset();
108+
interfacePath.reset();
109+
networkPath.reset();
110+
}
102111
};
103112
#endif
104113

@@ -163,6 +172,9 @@ class ConnectivityManagerImpl final : public ConnectivityManager,
163172
CHIP_ERROR CommitConfig();
164173

165174
void StartWiFiManagement();
175+
// Release GLib objects before the GLib main loop is quit.
176+
// Must be called from PlatformManagerImpl::_Shutdown() before g_main_loop_quit().
177+
void StopWiFiManagement();
166178
bool IsWiFiManagementStarted();
167179
void StartNonConcurrentWiFiManagement();
168180
int32_t GetDisconnectReason();
@@ -254,6 +266,7 @@ class ConnectivityManagerImpl final : public ConnectivityManager,
254266
bool _GetBssInfo(const gchar * bssPath, NetworkCommissioning::WiFiScanResponse & result);
255267

256268
CHIP_ERROR _StartWiFiManagement();
269+
CHIP_ERROR _StopWiFiManagement();
257270

258271
bool mAssociationStarted = false;
259272
unsigned int mAssociationRetriesLeft = 0;

src/platform/Linux/ConnectivityManagerImpl_NetworkManagementWpaSupplicant.cpp

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -599,6 +599,13 @@ void ConnectivityManagerImpl::StartWiFiManagement()
599599
VerifyOrReturn(err == CHIP_NO_ERROR, ChipLogError(DeviceLayer, "Failed to start WiFi management"));
600600
}
601601

602+
void ConnectivityManagerImpl::StopWiFiManagement()
603+
{
604+
CHIP_ERROR err = PlatformMgrImpl().GLibMatterContextInvokeSync(
605+
+[](ConnectivityManagerImpl * self) { return self->_StopWiFiManagement(); }, this);
606+
VerifyOrReturn(err == CHIP_NO_ERROR, ChipLogError(DeviceLayer, "Failed to stop WiFi management"));
607+
}
608+
602609
CHIP_ERROR ConnectivityManagerImpl::StartWiFiManagementSync()
603610
{
604611
if (IsWiFiManagementStarted())
@@ -1631,6 +1638,14 @@ CHIP_ERROR ConnectivityManagerImpl::_StartWiFiManagement()
16311638
return CHIP_NO_ERROR;
16321639
}
16331640

1641+
CHIP_ERROR ConnectivityManagerImpl::_StopWiFiManagement()
1642+
{
1643+
std::lock_guard<std::mutex> lock(mWpaSupplicantMutex);
1644+
1645+
mWpaSupplicant.Reset();
1646+
1647+
return CHIP_NO_ERROR;
1648+
}
16341649
#endif // CHIP_DEVICE_CONFIG_ENABLE_WPA
16351650

16361651
} // namespace DeviceLayer

src/platform/Linux/PlatformManagerImpl.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -282,6 +282,11 @@ void PlatformManagerImpl::_Shutdown()
282282
#if CHIP_DEVICE_CONFIG_WITH_GLIB_MAIN_LOOP
283283
if (mGLibMainLoop != nullptr)
284284
{
285+
#if CHIP_DEVICE_CONFIG_ENABLE_WPA
286+
// The wpa_supplicant GLib objects must be released while the GLib main loop is still running. Release them here, before
287+
// quitting the loop, otherwise they leak when ConnectivityManager is destructed.
288+
ConnectivityMgrImpl().StopWiFiManagement();
289+
#endif
285290
g_main_loop_quit(mGLibMainLoop);
286291
g_thread_join(mGLibMainLoopThread);
287292
g_main_loop_unref(mGLibMainLoop);

0 commit comments

Comments
 (0)