Skip to content

Commit

Permalink
Merge pull request #21 from nefarius/nefarius/feature/bluetooth
Browse files Browse the repository at this point in the history
Added Bluetooth utility commands
  • Loading branch information
nefarius authored Feb 21, 2025
2 parents 8c6bdf5 + 322dfd7 commit e990e2b
Show file tree
Hide file tree
Showing 11 changed files with 170 additions and 7 deletions.
3 changes: 3 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
[submodule "vcpkg"]
path = vcpkg
url = https://github.com/microsoft/vcpkg.git
3 changes: 3 additions & 0 deletions Directory.Build.props
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
<Project>
<Import Project="$(MSBuildThisFileDirectory)vcpkg\scripts\buildsystems\msbuild\vcpkg.props" Condition="'$(CI)' != 'true'" />
</Project>
9 changes: 9 additions & 0 deletions Directory.Build.targets
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<Project>
<Import Project="$(MSBuildThisFileDirectory)vcpkg\scripts\buildsystems\msbuild\vcpkg.targets" Condition="'$(CI)' != 'true'" />
<ItemDefinitionGroup Condition="'$(CI)' != 'true' AND !Exists('$(MSBuildThisFileDirectory)/vcpkg/vcpkg.exe')">
<PreBuildEvent>
<Command>$(MSBuildThisFileDirectory)vcpkg\bootstrap-vcpkg.bat</Command>
<Message>Bootstrap vcpkg</Message>
</PreBuildEvent>
</ItemDefinitionGroup>
</Project>
1 change: 1 addition & 0 deletions NefConUtil.sln.DotSettings
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
<wpf:ResourceDictionary xml:space="preserve" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:ss="urn:shemas-jetbrains-com:settings-storage-xaml" xmlns:wpf="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
<s:Boolean x:Key="/Default/UserDictionary/Words/=attribs/@EntryIndexedValue">True</s:Boolean>
<s:Boolean x:Key="/Default/UserDictionary/Words/=Bthprops/@EntryIndexedValue">True</s:Boolean>
<s:Boolean x:Key="/Default/UserDictionary/Words/=Bugprone/@EntryIndexedValue">True</s:Boolean>
<s:Boolean x:Key="/Default/UserDictionary/Words/=cmdl/@EntryIndexedValue">True</s:Boolean>
<s:Boolean x:Key="/Default/UserDictionary/Words/=cppcoreguidelines/@EntryIndexedValue">True</s:Boolean>
Expand Down
1 change: 1 addition & 0 deletions NefConUtil.vcxproj
Original file line number Diff line number Diff line change
Expand Up @@ -540,6 +540,7 @@
<ClInclude Include=".\src\colorwin.hpp" />
<ClInclude Include=".\src\resource.h" />
<ClInclude Include="src\ColorLogging.hpp" />
<ClInclude Include="src\LibraryHelper.hpp" />
</ItemGroup>
<ItemGroup>
<ResourceCompile Include=".\src\NefConUtil.rc" />
Expand Down
3 changes: 3 additions & 0 deletions NefConUtil.vcxproj.filters
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,9 @@
<ClInclude Include="src\ColorLogging.hpp">
<Filter>Header Files</Filter>
</ClInclude>
<ClInclude Include="src\LibraryHelper.hpp">
<Filter>Header Files</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<ResourceCompile Include=".\src\NefConUtil.rc">
Expand Down
55 changes: 55 additions & 0 deletions src/LibraryHelper.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
#pragma once

#include <bluetoothapis.h>
#include <newdev.h>

#include <type_traits>

class ProcPtr {
public:
explicit ProcPtr(FARPROC ptr) : _ptr(ptr) {}

template <typename T, typename = std::enable_if_t<std::is_function_v<T>>>
operator T* () const {
return reinterpret_cast<T*>(_ptr);
}

private:
FARPROC _ptr;
};

class DllHelper {
public:
explicit DllHelper(LPCTSTR filename) : _module(LoadLibrary(filename)) {}

~DllHelper() { FreeLibrary(_module); }

ProcPtr operator[](LPCSTR proc_name) const {
return ProcPtr(GetProcAddress(_module, proc_name));
}

static HMODULE _parent_module;

private:
HMODULE _module;
};


class Bthprops {
DllHelper _dll{ L"BluetoothApis.dll" };

public:
decltype(BluetoothFindFirstRadio)* pBluetoothFindFirstRadio = _dll["BluetoothFindFirstRadio"];
decltype(BluetoothFindRadioClose)* pBluetoothFindRadioClose = _dll["BluetoothFindRadioClose"];
decltype(BluetoothSetLocalServiceInfo)* pBluetoothSetLocalServiceInfo = _dll["BluetoothSetLocalServiceInfo"];
};

class Newdev {
DllHelper _dll{ L"Newdev.dll" };

public:
decltype(DiUninstallDriverW)* pDiUninstallDriverW = _dll["DiUninstallDriverW"];
decltype(DiInstallDriverW)* pDiInstallDriverW = _dll["DiInstallDriverW"];
decltype(DiUninstallDevice)* pDiUninstallDevice = _dll["DiUninstallDevice"];
};

89 changes: 87 additions & 2 deletions src/NefConUtil.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -49,10 +49,10 @@ int main(int argc, char* argv[])
"--class-guid",
"--service-name",
"--position",
"--service-name",
"--display-name",
"--bin-path",
"--file-path"
"--file-path",
"--service-guid"
});

auto cliArgs = nefarius::winapi::cli::GetCommandLineArgs();
Expand Down Expand Up @@ -719,6 +719,85 @@ int main(int argc, char* argv[])
return EXIT_SUCCESS;
}

constexpr PCSTR ENABLE_BLUETOOTH_SERVICE = "--enable-bluetooth-service";
constexpr PCSTR DISABLE_BLUETOOTH_SERVICE = "--disable-bluetooth-service";

if (cmdl[{ENABLE_BLUETOOTH_SERVICE}] || cmdl[{DISABLE_BLUETOOTH_SERVICE}])
{
//
// Sanity check
//
if (cmdl[{ENABLE_BLUETOOTH_SERVICE}] && cmdl[{DISABLE_BLUETOOTH_SERVICE}])
{
logger->error("You must either specify 'enable' or 'disable' action, not both together");
return EXIT_FAILURE;
}

const bool enable = cmdl[{ENABLE_BLUETOOTH_SERVICE}];

auto bthServiceName = cmdl({"--service-name"}).str();
auto bthServiceGuid = cmdl({"--service-guid"}).str();

if (bthServiceName.empty())
{
logger->error("Service name missing");
return EXIT_FAILURE;
}

if (bthServiceGuid.empty())
{
logger->error("Service GUID missing");
return EXIT_FAILURE;
}

const auto guid = nefarius::winapi::GUIDFromString(bthServiceGuid);

if (!guid)
{
logger->error(
"GUID format invalid, expected format (with or without brackets): xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx");
return EXIT_FAILURE;
}

int errorCode;
if (!IsAdmin(errorCode))
{
return errorCode;
}

if (auto ret = nefarius::winapi::security::AdjustProcessPrivileges(); !ret)
{
logger->error("Failed to modify process privileges, error: %v", ret.error().getErrorMessageA());
return ret.error().getErrorCode();
}

auto serviceNameWide = nefarius::utilities::ConvertAnsiToWide(bthServiceName);

BLUETOOTH_LOCAL_SERVICE_INFO svcInfo = {};
wcscpy_s(svcInfo.szName, sizeof(svcInfo.szName) / sizeof(WCHAR), serviceNameWide.c_str());

svcInfo.Enabled = enable ? TRUE : FALSE;
Bthprops bth;

if (DWORD err; ERROR_SUCCESS != (err = bth.pBluetoothSetLocalServiceInfo(
nullptr, //callee would select the first found radio
&guid.value(),
0,
&svcInfo
)))
{
auto error = nefarius::utilities::Win32Error(err);
logger->error("Failed to %v local service, error: %v",
enable ? "enable" : "disable",
error.getErrorMessageA());
return error.getErrorCode();
}

logger->info("Service %v successfully", enable ? "enabled" : "disabled");

return EXIT_SUCCESS;
}

#pragma endregion

#pragma region Version
Expand Down Expand Up @@ -778,6 +857,12 @@ int main(int argc, char* argv[])
std::cout << " --find-hwid Shows one or more devices matching a partial Hardware ID" << '\n';
std::cout << " ---hardware-id (Partial) Hardware ID of the device to match against (required)" <<
'\n';
std::cout << " --enable-bluetooth-service Enables a local Bluetooth service" << '\n';
std::cout << " --service-name The service name" << '\n';
std::cout << " --service-guid The service GUID" << '\n';
std::cout << " --disable-bluetooth-service Disables a local Bluetooth service" << '\n';
std::cout << " --service-name The service name" << '\n';
std::cout << " --service-guid The service GUID" << '\n';
std::cout << " -v, --version Display version of this utility" << '\n';
std::cout << '\n';
std::cout << " logging:" << '\n';
Expand Down
2 changes: 2 additions & 0 deletions src/NefConUtil.h
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
#include <rpc.h>
#include <shellapi.h>
#include <io.h>
#include <bluetoothapis.h>

//
// Device class interfaces
Expand Down Expand Up @@ -45,6 +46,7 @@
// Internal
//
#include "ColorLogging.hpp"
#include "LibraryHelper.hpp"

//
// neflib
Expand Down
10 changes: 5 additions & 5 deletions src/NefConUtil.rc
Original file line number Diff line number Diff line change
Expand Up @@ -51,8 +51,8 @@ END
//

VS_VERSION_INFO VERSIONINFO
FILEVERSION 1,11,1,0
PRODUCTVERSION 1,11,1,0
FILEVERSION 1,12,0,0
PRODUCTVERSION 1,12,0,0
FILEFLAGSMASK 0x3fL
#ifdef _DEBUG
FILEFLAGS 0x1L
Expand All @@ -69,12 +69,12 @@ BEGIN
BEGIN
VALUE "CompanyName", "Nefarius Software Solutions e.U."
VALUE "FileDescription", "Nefarius' Device Console Utility"
VALUE "FileVersion", "1.11.1.0"
VALUE "FileVersion", "1.12.0.0"
VALUE "InternalName", "nefcon.exe"
VALUE "LegalCopyright", "Copyright (C) 2022-2024 Nefarius Software Solutions e.U."
VALUE "LegalCopyright", "Copyright (C) 2022-2025 Nefarius Software Solutions e.U."
VALUE "OriginalFilename", "nefcon.exe"
VALUE "ProductName", "nefcon"
VALUE "ProductVersion", "1.11.1.0"
VALUE "ProductVersion", "1.12.0.0"
END
END
BLOCK "VarFileInfo"
Expand Down
1 change: 1 addition & 0 deletions vcpkg
Submodule vcpkg added at 8d88de

0 comments on commit e990e2b

Please sign in to comment.