summaryrefslogtreecommitdiffhomepage
path: root/windows/driverlogic/src/driverlogic.cpp
diff options
context:
space:
mode:
authorDavid Lönnhager <david.l@mullvad.net>2020-02-13 10:57:54 +0100
committerDavid Lönnhager <david.l@mullvad.net>2020-02-13 10:57:54 +0100
commitb7c2a1d6c6d14846591a30625bf3b05d069ca637 (patch)
tree189d2154031620fc8524a64bad9cd959079e1e07 /windows/driverlogic/src/driverlogic.cpp
parent6ab2a7767bc3e8ed63f436e93ec8b2eda5205752 (diff)
parent3368555bd0b81f13c7419860915bd06c40505df9 (diff)
downloadmullvadvpn-b7c2a1d6c6d14846591a30625bf3b05d069ca637.tar.xz
mullvadvpn-b7c2a1d6c6d14846591a30625bf3b05d069ca637.zip
Merge branch 'driverlogic-update'
Diffstat (limited to 'windows/driverlogic/src/driverlogic.cpp')
-rw-r--r--windows/driverlogic/src/driverlogic.cpp128
1 files changed, 91 insertions, 37 deletions
diff --git a/windows/driverlogic/src/driverlogic.cpp b/windows/driverlogic/src/driverlogic.cpp
index e426cc2243..f57ffc209b 100644
--- a/windows/driverlogic/src/driverlogic.cpp
+++ b/windows/driverlogic/src/driverlogic.cpp
@@ -15,6 +15,8 @@
#include <devpkey.h>
#include <newdev.h>
#include <cfgmgr32.h>
+#include <io.h>
+#include <fcntl.h>
namespace
@@ -288,7 +290,7 @@ bool DeleteDevice(HDEVINFO devInfo, const SP_DEVINFO_DATA &devInfoData)
return true;
}
-void ForEachDevice(const std::wstring &tapHardwareId, std::function<void(HDEVINFO, const SP_DEVINFO_DATA &)> func)
+void ForEachNetworkDevice(const std::optional<std::wstring> hwId, std::function<bool(HDEVINFO, const SP_DEVINFO_DATA &)> func)
{
HDEVINFO devInfo = SetupDiGetClassDevsW(
&GUID_DEVCLASS_NET,
@@ -325,37 +327,43 @@ void ForEachDevice(const std::wstring &tapHardwareId, std::function<void(HDEVINF
THROW_WINDOWS_ERROR(lastError, "Enumerating network adapters");
}
- try
+ if (hwId.has_value())
{
- const auto hardwareId = GetDeviceRegistryStringProperty(devInfo, devInfoData, SPDRP_HARDWAREID);
+ try
+ {
+ const auto hardwareId = GetDeviceRegistryStringProperty(devInfo, devInfoData, SPDRP_HARDWAREID);
- if (!hardwareId.has_value() ||
- 0 != tapHardwareId.compare(hardwareId.value()))
+ if (!hardwareId.has_value() ||
+ 0 != hwId->compare(hardwareId.value()))
+ {
+ continue;
+ }
+ }
+ catch (const std::exception & e)
{
+ //
+ // Skip this adapter
+ //
+
+ std::wcerr << L"Skipping TAP adapter due to exception caught while iterating: "
+ << common::string::ToWide(e.what()) << std::endl;
continue;
}
}
- catch (const std::exception & e)
- {
- //
- // Skip this adapter
- //
- std::cerr << "Skipping TAP adapter due to exception caught while iterating: "
- << e.what() << std::endl;
- continue;
+ if (!func(devInfo, devInfoData))
+ {
+ break;
}
-
- func(devInfo, devInfoData);
}
}
-std::set<NetworkAdapter> GetTapAdapters(const std::wstring &tapHardwareId)
+std::set<NetworkAdapter> GetNetworkAdapters(const std::optional<std::wstring> hardwareId)
{
std::set<NetworkAdapter> adapters;
common::network::Nci nci;
- ForEachDevice(tapHardwareId, [&](HDEVINFO devInfo, const SP_DEVINFO_DATA &devInfoData) {
+ ForEachNetworkDevice(hardwareId, [&](HDEVINFO devInfo, const SP_DEVINFO_DATA &devInfoData) {
try
{
//
@@ -378,9 +386,10 @@ std::set<NetworkAdapter> GetTapAdapters(const std::wstring &tapHardwareId)
// Skip this adapter
//
- std::cerr << "Skipping TAP adapter due to exception caught while iterating: "
- << e.what() << std::endl;
+ std::wcerr << L"Skipping adapter due to exception caught while iterating: "
+ << common::string::ToWide(e.what()) << std::endl;
}
+ return true;
});
return adapters;
@@ -491,6 +500,42 @@ ATTEMPT_UPDATE:
<< rebootRequired;
}
+//
+// Broken adapters may use our "Mullvad" name, so find one that is not in use.
+// NOTE: Enumerating adapters first and picking the next free name is not sufficient,
+// because the broken TAP may not be included.
+//
+void RenameAdapterToMullvad(const NetworkAdapter &adapter)
+{
+ common::network::Nci nci;
+
+ try
+ {
+ nci.setConnectionName(common::Guid::FromString(adapter.guid), TAP_BASE_ALIAS);
+ return;
+ }
+ catch (...)
+ {
+ }
+
+ for (int i = 1; i < 10; i++)
+ {
+ std::wstringstream ss;
+ ss << TAP_BASE_ALIAS << L"-" << i;
+
+ try
+ {
+ nci.setConnectionName(common::Guid::FromString(adapter.guid), ss.str().c_str());
+ return;
+ }
+ catch (...)
+ {
+ }
+ }
+
+ THROW_ERROR("Exhausted TAP adapter namespace");
+}
+
std::optional<NetworkAdapter> FindMullvadAdapter(const std::set<NetworkAdapter> &tapAdapters)
{
if (tapAdapters.empty())
@@ -523,7 +568,7 @@ std::optional<NetworkAdapter> FindMullvadAdapter(const std::set<NetworkAdapter>
// Look for TAP adapter with alias "Mullvad-1", "Mullvad-2", etc.
//
- for (auto i = 0; i < 10; ++i)
+ for (auto i = 1; i < 10; ++i)
{
std::wstringstream ss;
@@ -544,7 +589,7 @@ std::optional<NetworkAdapter> FindMullvadAdapter(const std::set<NetworkAdapter>
NetworkAdapter FindBrandedTap()
{
- std::set<NetworkAdapter> added = GetTapAdapters(TAP_HARDWARE_ID);
+ std::set<NetworkAdapter> added = GetNetworkAdapters(TAP_HARDWARE_ID);
if (added.empty())
{
@@ -562,7 +607,7 @@ NetworkAdapter FindBrandedTap()
void RemoveTapDriver(const std::wstring &tapHardwareId)
{
- ForEachDevice(tapHardwareId, [](HDEVINFO devInfo, const SP_DEVINFO_DATA &devInfoData) {
+ ForEachNetworkDevice(tapHardwareId, [](HDEVINFO devInfo, const SP_DEVINFO_DATA &devInfoData) {
try
{
DeleteDevice(devInfo, devInfoData);
@@ -573,31 +618,38 @@ void RemoveTapDriver(const std::wstring &tapHardwareId)
// Skip this adapter
//
- std::cerr << "Skipping TAP adapter due to exception caught while iterating: "
- << e.what() << std::endl;
+ std::wcerr << L"Skipping TAP adapter due to exception caught while iterating: "
+ << common::string::ToWide(e.what()) << std::endl;
}
+ return true;
});
}
void DeleteVanillaMullvadAdapter()
{
- auto tapAdapters = GetTapAdapters(DEPRECATED_TAP_HARDWARE_ID);
+ auto tapAdapters = GetNetworkAdapters(DEPRECATED_TAP_HARDWARE_ID);
std::optional<NetworkAdapter> mullvadAdapter = FindMullvadAdapter(tapAdapters);
if (!mullvadAdapter.has_value())
{
- THROW_ERROR("Mullvad TAP adapter not found");
+ return;
}
const auto mullvadGuid = mullvadAdapter.value().guid;
bool deletedAdapter = false;
- ForEachDevice(DEPRECATED_TAP_HARDWARE_ID, [&](HDEVINFO devInfo, const SP_DEVINFO_DATA &devInfoData) {
+ //
+ // Enumerate over all network devices with the hardware ID DEPRECATED_TAP_HARDWARE_ID,
+ // and delete any adapter whose GUID matches that of the "Mullvad" adapter.
+ //
+
+ ForEachNetworkDevice(DEPRECATED_TAP_HARDWARE_ID, [&](HDEVINFO devInfo, const SP_DEVINFO_DATA &devInfoData) {
try
{
if (0 == GetNetCfgInstanceId(devInfo, devInfoData).compare(mullvadGuid))
{
- deletedAdapter = DeleteDevice(devInfo, devInfoData) || deletedAdapter;
+ deletedAdapter = DeleteDevice(devInfo, devInfoData);
+ return false;
}
}
catch (const std::exception & e)
@@ -606,10 +658,10 @@ void DeleteVanillaMullvadAdapter()
// Skip this adapter
//
- std::cerr << "Skipping TAP adapter due to exception caught while iterating: "
- << e.what() << std::endl;
- return;
+ std::wcerr << L"Skipping TAP adapter due to exception caught while iterating: "
+ << common::string::ToWide(e.what()) << std::endl;
}
+ return true;
});
if (!deletedAdapter)
@@ -622,6 +674,12 @@ void DeleteVanillaMullvadAdapter()
int wmain(int argc, const wchar_t * argv[], const wchar_t * [])
{
+ if (-1 == _setmode(_fileno(stdout), _O_U16TEXT)
+ || -1 == _setmode(_fileno(stderr), _O_U16TEXT))
+ {
+ std::wcerr << L"Failed to set translation mode" << std::endl;
+ }
+
if (2 > argc)
{
goto INVALID_ARGUMENTS;
@@ -638,6 +696,7 @@ int wmain(int argc, const wchar_t * argv[], const wchar_t * [])
CreateTapDevice();
UpdateTapDriver(argv[2]);
+ RenameAdapterToMullvad(FindBrandedTap());
}
else if (0 == _wcsicmp(argv[1], L"update"))
{
@@ -661,11 +720,6 @@ int wmain(int argc, const wchar_t * argv[], const wchar_t * [])
{
DeleteVanillaMullvadAdapter();
}
- else if (0 == _wcsicmp(argv[1], L"find-tap"))
- {
- const auto tap = FindBrandedTap();
- std::wcout << tap.alias;
- }
else
{
goto INVALID_ARGUMENTS;
@@ -673,7 +727,7 @@ int wmain(int argc, const wchar_t * argv[], const wchar_t * [])
}
catch (const std::exception &e)
{
- std::cerr << e.what();
+ std::wcerr << common::string::ToWide(e.what());
return GENERAL_ERROR;
}
catch (...)