Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Partially implement WifiEnumerateAccessPoints to expose access point ids #113

Merged
merged 12 commits into from
Jan 18, 2024
13 changes: 10 additions & 3 deletions src/common/server/NetRemoteServer.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,9 @@

using namespace Microsoft::Net::Remote;

NetRemoteServer::NetRemoteServer(std::string_view serverAddress) :
m_serverAddress{ serverAddress }
NetRemoteServer::NetRemoteServer(NetRemoteServerConfiguration configuration) :
m_serverAddress(configuration.ServerAddress),
m_service(configuration.AccessPointManager)
{}

NetRemoteServer::~NetRemoteServer()
Expand All @@ -24,6 +25,12 @@ NetRemoteServer::GetGrpcServer() noexcept
return m_server;
}

Service::NetRemoteService&
NetRemoteServer::GetService() noexcept
{
return m_service;
}

void
NetRemoteServer::Run()
{
Expand All @@ -36,7 +43,7 @@ NetRemoteServer::Run()
builder.RegisterService(&m_service);

m_server = builder.BuildAndStart();
LOG_INFO << std::format("netremote server started listening on {}", m_serverAddress);
LOG_INFO << std::format("Netremote server started listening on {}", m_serverAddress);
}

void
Expand Down
6 changes: 3 additions & 3 deletions src/common/server/NetRemoteServerConfiguration.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -19,12 +19,12 @@ ConfigureCliAppOptions(CLI::App& app, NetRemoteServerConfiguration& config)
app.add_option(
"-a,--address",
config.ServerAddress,
"The address to listen on for incoming connections.");
"The address to listen on for incoming connections");

app.add_option(
app.add_flag(
"-v,--verbosity",
config.LogVerbosity,
"The log verbosity level. Supply multiple times to increase verbosity (0=warnings, errors, and fatal messages, 1=info messages, 2=debug messages, 3=verbose messages).");
"The log verbosity level. Supply multiple times to increase verbosity (0=warnings, errors, and fatal messages, 1=info messages, 2=debug messages, 3=verbose messages)");

return app;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,9 @@
#include <string_view>

#include <grpcpp/server.h>
#include <microsoft/net/remote/NetRemoteServerConfiguration.hxx>
#include <microsoft/net/remote/NetRemoteService.hxx>
#include <microsoft/net/wifi/AccessPointManager.hxx>

namespace Microsoft::Net::Remote
{
Expand All @@ -19,11 +21,11 @@ struct NetRemoteServer
virtual ~NetRemoteServer();

/**
* @brief Construct a new NetRemoteServer object.
* @brief Construct a new NetRemoteServer object with the specified configuration.
*
* @param serverAddress
* @param configuration
*/
NetRemoteServer(std::string_view serverAddress);
NetRemoteServer(NetRemoteServerConfiguration configuration);

/**
* @brief Get the GrpcServer object.
Expand All @@ -33,6 +35,14 @@ struct NetRemoteServer
std::unique_ptr<grpc::Server>&
GetGrpcServer() noexcept;

/**
* @brief Get the NetRemoteService object instance.
*
* @return Service::NetRemoteService&
*/
Service::NetRemoteService&
GetService() noexcept;

/**
* @brief Start the server if not already started.
*/
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,20 @@
#define NET_REMOTE_SERVER_CONFIGURATION_HXX

#include <cstdint>
#include <memory>
#include <string>
#include <vector>

namespace Microsoft::Net::Wifi
{
class AccessPointManager;
} // namespace Microsoft::Net::Wifi

namespace Microsoft::Net::Remote
{
/**
* @brief Collects configuration options for the NetRemoteServer class.
*/
struct NetRemoteServerConfiguration
{
/**
Expand Down Expand Up @@ -54,7 +63,12 @@ struct NetRemoteServerConfiguration
* show all info messages, and a level of 2 will show all debug messages,
* and a level of 3 or above will show all verbose messages.
*/
uint8_t LogVerbosity{ 0 };
uint32_t LogVerbosity{ 0 };

/**
* @brief Access point manager instance.
*/
std::shared_ptr<Microsoft::Net::Wifi::AccessPointManager> AccessPointManager;
};

} // namespace Microsoft::Net::Remote
Expand Down
19 changes: 14 additions & 5 deletions src/common/service/NetRemoteService.cxx
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@

#include <format>
#include <iostream>
#include <iterator>
#include <string>
#include <vector>
Expand All @@ -13,15 +12,25 @@ using namespace Microsoft::Net::Remote::Service;
using Microsoft::Net::Wifi::AccessPointManager;

NetRemoteService::NetRemoteService() :
m_accessPointManager(AccessPointManager::Create())
NetRemoteService(AccessPointManager::Create())
{}

NetRemoteService::NetRemoteService(std::shared_ptr<AccessPointManager> accessPointManager) :
m_accessPointManager(std::move(accessPointManager))
{}

std::shared_ptr<AccessPointManager>
NetRemoteService::GetAccessPointManager() noexcept
{
return m_accessPointManager;
}

::grpc::Status
NetRemoteService::WifiEnumerateAccessPoints([[maybe_unused]] ::grpc::ServerContext* context, [[maybe_unused]] const ::Microsoft::Net::Remote::Wifi::WifiEnumerateAccessPointsRequest* request, ::Microsoft::Net::Remote::Wifi::WifiEnumerateAccessPointsResult* response)
{
using Microsoft::Net::Remote::Wifi::WifiEnumerateAccessPointsResultItem;

LOG_VERBOSE << std::format("Received WifiEnumerateAccessPoints request\n");
LOGD << std::format("Received WifiEnumerateAccessPoints request");

auto accessPoints = m_accessPointManager->GetAllAccessPoints();
std::vector<WifiEnumerateAccessPointsResultItem> accessPointResultItems(std::size(accessPoints));
Expand Down Expand Up @@ -53,7 +62,7 @@ using Microsoft::Net::Wifi::Dot11PhyType;
::grpc::Status
NetRemoteService::WifiAccessPointEnable([[maybe_unused]] ::grpc::ServerContext* context, const ::Microsoft::Net::Remote::Wifi::WifiAccessPointEnableRequest* request, ::Microsoft::Net::Remote::Wifi::WifiAccessPointEnableResult* response)
{
LOG_VERBOSE << std::format("Received WifiAccessPointEnable request for access point id {}\n", request->accesspointid());
LOGD << std::format("Received WifiAccessPointEnable request for access point id {}", request->accesspointid());

WifiAccessPointOperationStatus status{};

Expand All @@ -72,7 +81,7 @@ NetRemoteService::WifiAccessPointEnable([[maybe_unused]] ::grpc::ServerContext*
::grpc::Status
NetRemoteService::WifiAccessPointDisable([[maybe_unused]] ::grpc::ServerContext* context, const ::Microsoft::Net::Remote::Wifi::WifiAccessPointDisableRequest* request, ::Microsoft::Net::Remote::Wifi::WifiAccessPointDisableResult* response)
{
LOG_VERBOSE << std::format("Received WifiAccessPointDisable request for access point id {}\n", request->accesspointid());
LOGD << std::format("Received WifiAccessPointDisable request for access point id {}", request->accesspointid());

WifiAccessPointOperationStatus status{};
// TODO: Disable the access point.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,12 +9,33 @@

namespace Microsoft::Net::Remote::Service
{
/**
* @brief Implementation of the NetRemote::Service gRPC service.
*/
class NetRemoteService :
public NetRemote::Service
{
public:
/**
* @brief Construct a new NetRemoteService object.
*/
NetRemoteService();

/**
* @brief Construct a new NetRemoteService object with the specified access point manager.
*
* @param accessPointManager The access point manager to use.
*/
NetRemoteService(std::shared_ptr<Microsoft::Net::Wifi::AccessPointManager> accessPointManager);

/**
* @brief Get the AccessPointManager object for this service.
*
* @return std::shared_ptr<Microsoft::Net::Wifi::AccessPointManager>
*/
std::shared_ptr<Microsoft::Net::Wifi::AccessPointManager>
GetAccessPointManager() noexcept;

private:
virtual ::grpc::Status
WifiEnumerateAccessPoints(::grpc::ServerContext* context, const ::Microsoft::Net::Remote::Wifi::WifiEnumerateAccessPointsRequest* request, ::Microsoft::Net::Remote::Wifi::WifiEnumerateAccessPointsResult* response) override;
Expand Down
2 changes: 1 addition & 1 deletion src/common/shared/logging/LogUtils.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ logging::GetLogName(std::string_view componentName)
}

plog::Severity
logging::LogVerbosityToPlogSeverity(uint8_t verbosity) noexcept
logging::LogVerbosityToPlogSeverity(uint32_t verbosity) noexcept
{
switch (verbosity) {
case 0:
Expand Down
2 changes: 1 addition & 1 deletion src/common/shared/logging/include/logging/LogUtils.hxx
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ GetLogName(std::string_view componentName);
* @return plog::Severity
*/
plog::Severity
LogVerbosityToPlogSeverity(uint8_t verbosity) noexcept;
LogVerbosityToPlogSeverity(uint32_t verbosity) noexcept;

} // namespace logging

Expand Down
6 changes: 6 additions & 0 deletions src/common/tools/cli/NetRemoteCliHandlerOperations.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,12 @@ NetRemoteCliHandlerOperations::WifiEnumerateAccessPoints()
LOGE << std::format("Failed to enumerate WiFi access points, error={} details={} message={}", magic_enum::enum_name(status.error_code()), status.error_details(), status.error_message());
return;
}

LOGI << std::format("{} access points discovered", result.accesspoints_size());

for (const auto& accessPoint : result.accesspoints()) {
LOGI << std::format(" - [{}]", accessPoint.accesspointid());
}
}

std::unique_ptr<INetRemoteCliHandlerOperations>
Expand Down
5 changes: 5 additions & 0 deletions src/common/wifi/apmanager/AccessPointDiscoveryAgent.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
#include <microsoft/net/wifi/AccessPointDiscoveryAgent.hxx>
#include <microsoft/net/wifi/IAccessPoint.hxx>
#include <notstd/Memory.hxx>
#include <plog/Log.h>

using namespace Microsoft::Net::Wifi;

Expand Down Expand Up @@ -39,6 +40,7 @@ AccessPointDiscoveryAgent::DevicePresenceChanged(AccessPointPresenceEvent presen
{
std::shared_lock<std::shared_mutex> onDevicePresenceChangedLock{ m_onDevicePresenceChangedGate };
if (m_onDevicePresenceChanged) {
LOGD << "Access point discovery agent detected a device presence change";
m_onDevicePresenceChanged(presence, std::move(interfaceName));
}
}
Expand All @@ -54,6 +56,7 @@ AccessPointDiscoveryAgent::Start()
{
bool expected = false;
if (m_started.compare_exchange_weak(expected, true)) {
LOGD << "Access point discovery agent starting";
m_operations->Start([weakThis = std::weak_ptr<AccessPointDiscoveryAgent>(GetInstance())](auto&& presence, auto&& interfaceName) {
// Attempt to promote the weak pointer to a shared pointer to ensure this instance is still valid.
if (auto strongThis = weakThis.lock(); strongThis) {
Expand All @@ -68,12 +71,14 @@ AccessPointDiscoveryAgent::Stop()
{
bool expected = true;
if (m_started.compare_exchange_weak(expected, false)) {
LOGD << "Access point discovery agent stopping";
m_operations->Stop();
}
}

std::future<std::vector<std::string>>
AccessPointDiscoveryAgent::ProbeAsync()
{
LOGD << "Access point discovery agent probing for devices";
return m_operations->ProbeAsync();
}
21 changes: 10 additions & 11 deletions src/common/wifi/apmanager/AccessPointManager.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,8 @@ AccessPointManager::AddDiscoveryAgent(std::shared_ptr<AccessPointDiscoveryAgent>
{
using namespace std::chrono_literals;

// Register a discovery event callback.
//
// Use a weak_ptr below to ensure that the access point manager can
// be safely destroyed prior to the discovery agent. This allows the
// callback to be registered indefinitely, safely checking whether this
Expand All @@ -100,28 +102,25 @@ AccessPointManager::AddDiscoveryAgent(std::shared_ptr<AccessPointDiscoveryAgent>
}
});

// If this agent has already started, kick off a probe to ensure any access
// points already found will be added to this manager.
std::future<std::vector<std::string>> existingAccessPointInterfaceNamesProbe;
const bool isStarted = discoveryAgent->IsStarted();
if (isStarted) {
existingAccessPointInterfaceNamesProbe = discoveryAgent->ProbeAsync();
} else {
// Start the agent if not done already.
if (!discoveryAgent->IsStarted()) {
discoveryAgent->Start();
}

// If the agent hasn't yet been started, start it now, then probe for
// existing access points in case they've already been discovered.
// Kick off a probe to ensure any access points already present will be added to this manager.
auto existingAccessPointInterfaceNamesProbe = discoveryAgent->ProbeAsync();

// Add the agent.
{
std::unique_lock<std::shared_mutex> discoveryAgentLock{ m_discoveryAgentsGate };
m_discoveryAgents.push_back(std::move(discoveryAgent));
}

if (existingAccessPointInterfaceNamesProbe.valid()) {
static constexpr auto probeTimeout = 3s;
static constexpr auto ProbeTimeout = 3s;

// Wait for the operation to complete.
const auto waitResult = existingAccessPointInterfaceNamesProbe.wait_for(probeTimeout);
const auto waitResult = existingAccessPointInterfaceNamesProbe.wait_for(ProbeTimeout);

// If the operation completed, get the results and add those access points.
if (waitResult == std::future_status::ready) {
Expand Down
1 change: 1 addition & 0 deletions src/common/wifi/apmanager/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ target_sources(wifi-apmanager
target_link_libraries(wifi-apmanager
PRIVATE
notstd
plog::plog
PUBLIC
${PROJECT_NAME}-protocol
wifi-core
Expand Down
Loading
Loading