Skip to content

Commit

Permalink
[ncp] implement dbus server for NCP mode
Browse files Browse the repository at this point in the history
  • Loading branch information
Irving-cl committed Jun 26, 2024
1 parent 3edc59f commit c3fa90c
Show file tree
Hide file tree
Showing 21 changed files with 723 additions and 369 deletions.
38 changes: 33 additions & 5 deletions src/agent/application.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,9 @@ Application::Application(const std::string &aInterfaceName,
#if OTBR_ENABLE_MDNS
, mPublisher(Mdns::Publisher::Create([this](Mdns::Publisher::State aState) { this->HandleMdnsState(aState); }))
#endif
#if OTBR_ENABLE_DBUS_SERVER && OTBR_ENABLE_BORDER_AGENT
, mDBusAgent(MakeUnique<DBus::DBusAgent>(*mHost, *mPublisher))
#endif
#if OTBR_ENABLE_VENDOR_SERVER
, mVendorServer(vendor::VendorServer::newInstance(*this))
#endif
Expand All @@ -82,19 +85,35 @@ void Application::Init(void)
{
mHost->Init();

if (mHost->GetCoprocessorType() == OT_COPROCESSOR_RCP)
switch (mHost->GetCoprocessorType())
{
case OT_COPROCESSOR_RCP:
InitRcpMode();
break;
case OT_COPROCESSOR_NCP:
InitNcpMode();
break;
default:
DieNow("Unknown coprocessor type!");
break;
}

otbrLogInfo("Co-processor version: %s", mHost->GetCoprocessorVersion());
}

void Application::Deinit(void)
{
if (mHost->GetCoprocessorType() == OT_COPROCESSOR_RCP)
switch (mHost->GetCoprocessorType())
{
case OT_COPROCESSOR_RCP:
DeinitRcpMode();
break;
case OT_COPROCESSOR_NCP:
DeinitNcpMode();
break;
default:
DieNow("Unknown coprocessor type!");
break;
}

mHost->Deinit();
Expand Down Expand Up @@ -223,9 +242,6 @@ void Application::CreateRcpMode(const std::string &aRestListenAddress, int aRest
#if OTBR_ENABLE_REST_SERVER
mRestWebServer = MakeUnique<rest::RestWebServer>(rcpHost, aRestListenAddress, aRestListenPort);
#endif
#if OTBR_ENABLE_DBUS_SERVER && OTBR_ENABLE_BORDER_AGENT
mDBusAgent = MakeUnique<DBus::DBusAgent>(rcpHost, *mPublisher);
#endif

OT_UNUSED_VARIABLE(aRestListenAddress);
OT_UNUSED_VARIABLE(aRestListenPort);
Expand Down Expand Up @@ -284,4 +300,16 @@ void Application::DeinitRcpMode(void)
#endif
}

void Application::InitNcpMode(void)
{
#if OTBR_ENABLE_DBUS_SERVER
mDBusAgent->Init();
#endif
}

void Application::DeinitNcpMode(void)
{
/* empty */
}

} // namespace otbr
3 changes: 3 additions & 0 deletions src/agent/application.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -260,6 +260,9 @@ class Application : private NonCopyable
void InitRcpMode(void);
void DeinitRcpMode(void);

void InitNcpMode(void);
void DeinitNcpMode(void);

std::string mInterfaceName;
#if __linux__
otbr::Utils::InfraLinkSelector mInfraLinkSelector;
Expand Down
42 changes: 42 additions & 0 deletions src/common/types.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -159,4 +159,46 @@ std::string MacAddress::ToString(void) const
return std::string(strbuf);
}

otError OtbrErrorToOtError(otbrError aError)
{
otError error;

switch (aError)
{
case OTBR_ERROR_NONE:
error = OT_ERROR_NONE;
break;

case OTBR_ERROR_NOT_FOUND:
error = OT_ERROR_NOT_FOUND;
break;

case OTBR_ERROR_PARSE:
error = OT_ERROR_PARSE;
break;

case OTBR_ERROR_NOT_IMPLEMENTED:
error = OT_ERROR_NOT_IMPLEMENTED;
break;

case OTBR_ERROR_INVALID_ARGS:
error = OT_ERROR_INVALID_ARGS;
break;

case OTBR_ERROR_DUPLICATED:
error = OT_ERROR_DUPLICATED;
break;

case OTBR_ERROR_INVALID_STATE:
error = OT_ERROR_INVALID_STATE;
break;

default:
error = OT_ERROR_FAILED;
break;
}

return error;
}

} // namespace otbr
12 changes: 12 additions & 0 deletions src/common/types.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,8 @@
#include <string>
#include <vector>

#include <openthread/error.h>

#include "common/byteswap.hpp"

#ifndef IN6ADDR_ANY
Expand Down Expand Up @@ -469,6 +471,16 @@ static constexpr size_t kVendorOuiLength = 3;
static constexpr size_t kMaxVendorNameLength = 24;
static constexpr size_t kMaxProductNameLength = 24;

/**
* This method converts a otbrError to a otError.
*
* @param[in] aError a otbrError code.
*
* @returns a otError code.
*
*/
otError OtbrErrorToOtError(otbrError aError);

} // namespace otbr

#endif // OTBR_COMMON_TYPES_HPP_
5 changes: 3 additions & 2 deletions src/dbus/server/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,8 @@ add_custom_target(otbr-dbus-introspect-header ALL
add_library(otbr-dbus-server STATIC
dbus_agent.cpp
dbus_object.cpp
dbus_thread_object.cpp
dbus_thread_object_ncp.cpp
dbus_thread_object_rcp.cpp
error_helper.cpp
)

Expand All @@ -55,7 +56,7 @@ target_link_libraries(otbr-dbus-server PUBLIC

if(OTBR_DOC)
add_custom_target(otbr-dbus-server-doc ALL
COMMAND gdbus-codegen --generate-docbook generated-docs ${CMAKE_CURRENT_SOURCE_DIR}/introspect.xml
COMMAND gdbus-codegen --generate-docbook generated-docs ${CMAKE_CURRENT_SOURCE_DIR}/introspect.xml
COMMAND xmlto html generated-docs-io.openthread.BorderRouter.xml
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
VERBATIM
Expand Down
23 changes: 20 additions & 3 deletions src/dbus/server/dbus_agent.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,8 @@

#include "common/logging.hpp"
#include "dbus/common/constants.hpp"
#include "dbus/server/dbus_thread_object_ncp.hpp"
#include "dbus/server/dbus_thread_object_rcp.hpp"
#include "mdns/mdns.hpp"

namespace otbr {
Expand All @@ -44,7 +46,7 @@ namespace DBus {
const struct timeval DBusAgent::kPollTimeout = {0, 0};
constexpr std::chrono::seconds DBusAgent::kDBusWaitAllowance;

DBusAgent::DBusAgent(otbr::Ncp::RcpHost &aHost, Mdns::Publisher &aPublisher)
DBusAgent::DBusAgent(otbr::Ncp::ThreadHost &aHost, Mdns::Publisher &aPublisher)
: mInterfaceName(aHost.GetInterfaceName())
, mHost(aHost)
, mPublisher(aPublisher)
Expand All @@ -65,8 +67,23 @@ void DBusAgent::Init(void)

VerifyOrDie(mConnection != nullptr, "Failed to get DBus connection");

mThreadObject =
std::unique_ptr<DBusThreadObject>(new DBusThreadObject(mConnection.get(), mInterfaceName, &mHost, &mPublisher));
switch (mHost.GetCoprocessorType())
{
case OT_COPROCESSOR_RCP:
mThreadObject = MakeUnique<DBusThreadObjectRcp>(*mConnection, mInterfaceName,
static_cast<Ncp::RcpHost &>(mHost), &mPublisher);
break;

case OT_COPROCESSOR_NCP:
mThreadObject =
MakeUnique<DBusThreadObjectNcp>(*mConnection, mInterfaceName, static_cast<Ncp::NcpHost &>(mHost));
break;

default:
DieNow("Unknown coprocessor type!");
break;
}

error = mThreadObject->Init();
VerifyOrDie(error == OTBR_ERROR_NONE, "Failed to initialize DBus Agent");
}
Expand Down
21 changes: 11 additions & 10 deletions src/dbus/server/dbus_agent.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -46,9 +46,9 @@
#include "dbus/common/dbus_message_helper.hpp"
#include "dbus/common/dbus_resources.hpp"
#include "dbus/server/dbus_object.hpp"
#include "dbus/server/dbus_thread_object.hpp"

#include "ncp/rcp_host.hpp"
#include "dbus/server/dbus_thread_object_ncp.hpp"
#include "dbus/server/dbus_thread_object_rcp.hpp"
#include "ncp/thread_host.hpp"

namespace otbr {
namespace DBus {
Expand All @@ -59,10 +59,11 @@ class DBusAgent : public MainloopProcessor, private NonCopyable
/**
* The constructor of dbus agent.
*
* @param[in] aHost A reference to the Thread controller.
* @param[in] aHost A reference to the Thread host.
* @param[in] aPublisher A reference to the MDNS publisher.
*
*/
DBusAgent(otbr::Ncp::RcpHost &aHost, Mdns::Publisher &aPublisher);
DBusAgent(otbr::Ncp::ThreadHost &aHost, Mdns::Publisher &aPublisher);

/**
* This method initializes the dbus agent.
Expand All @@ -85,11 +86,11 @@ class DBusAgent : public MainloopProcessor, private NonCopyable

static const struct timeval kPollTimeout;

std::string mInterfaceName;
std::unique_ptr<DBusThreadObject> mThreadObject;
UniqueDBusConnection mConnection;
otbr::Ncp::RcpHost &mHost;
Mdns::Publisher &mPublisher;
std::string mInterfaceName;
std::unique_ptr<DBusObject> mThreadObject;
UniqueDBusConnection mConnection;
otbr::Ncp::ThreadHost &mHost;
Mdns::Publisher &mPublisher;

/**
* This map is used to track DBusWatch-es.
Expand Down
67 changes: 61 additions & 6 deletions src/dbus/server/dbus_object.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,11 @@ DBusObject::DBusObject(DBusConnection *aConnection, const std::string &aObjectPa
}

otbrError DBusObject::Init(void)
{
return Initialize(/* aIsAsyncPropertyHandler */ false);
}

otbrError DBusObject::Initialize(bool aIsAsyncPropertyHandler)
{
otbrError error = OTBR_ERROR_NONE;
DBusObjectPathVTable vTable;
Expand All @@ -60,12 +65,21 @@ otbrError DBusObject::Init(void)

VerifyOrExit(dbus_connection_register_object_path(mConnection, mObjectPath.c_str(), &vTable, this),
error = OTBR_ERROR_DBUS);
RegisterMethod(DBUS_INTERFACE_PROPERTIES, DBUS_PROPERTY_GET_METHOD,
std::bind(&DBusObject::GetPropertyMethodHandler, this, _1));
RegisterMethod(DBUS_INTERFACE_PROPERTIES, DBUS_PROPERTY_SET_METHOD,
std::bind(&DBusObject::SetPropertyMethodHandler, this, _1));
RegisterMethod(DBUS_INTERFACE_PROPERTIES, DBUS_PROPERTY_GET_ALL_METHOD,
std::bind(&DBusObject::GetAllPropertiesMethodHandler, this, _1));

if (aIsAsyncPropertyHandler)
{
RegisterMethod(DBUS_INTERFACE_PROPERTIES, DBUS_PROPERTY_GET_METHOD,
std::bind(&DBusObject::AsyncGetPropertyMethodHandler, this, _1));
}
else
{
RegisterMethod(DBUS_INTERFACE_PROPERTIES, DBUS_PROPERTY_GET_METHOD,
std::bind(&DBusObject::GetPropertyMethodHandler, this, _1));
RegisterMethod(DBUS_INTERFACE_PROPERTIES, DBUS_PROPERTY_SET_METHOD,
std::bind(&DBusObject::SetPropertyMethodHandler, this, _1));
RegisterMethod(DBUS_INTERFACE_PROPERTIES, DBUS_PROPERTY_GET_ALL_METHOD,
std::bind(&DBusObject::GetAllPropertiesMethodHandler, this, _1));
}

exit:
return error;
Expand Down Expand Up @@ -98,6 +112,13 @@ void DBusObject::RegisterSetPropertyHandler(const std::string &aInterfac
mSetPropertyHandlers.emplace(fullPath, aHandler);
}

void DBusObject::RegisterAsyncGetPropertyHandler(const std::string &aInterfaceName,
const std::string &aPropertyName,
const AsyncPropertyHandlerType &aHandler)
{
mAsyncGetPropertyHandlers[aInterfaceName].emplace(aPropertyName, aHandler);
}

DBusHandlerResult DBusObject::sMessageHandler(DBusConnection *aConnection, DBusMessage *aMessage, void *aData)
{
DBusObject *server = reinterpret_cast<DBusObject *>(aData);
Expand Down Expand Up @@ -252,6 +273,40 @@ void DBusObject::SetPropertyMethodHandler(DBusRequest &aRequest)
return;
}

void DBusObject::AsyncGetPropertyMethodHandler(DBusRequest &aRequest)
{
DBusMessageIter iter;
std::string interfaceName;
otError error = OT_ERROR_NONE;
std::string propertyName;

VerifyOrExit(dbus_message_iter_init(aRequest.GetMessage(), &iter), error = OT_ERROR_FAILED);
SuccessOrExit(error = OtbrErrorToOtError(DBusMessageExtract(&iter, interfaceName)));
SuccessOrExit(error = OtbrErrorToOtError(DBusMessageExtract(&iter, propertyName)));

{
auto propertyIter = mAsyncGetPropertyHandlers.find(interfaceName);

otbrLogDebug("AsyncGetProperty %s.%s", interfaceName.c_str(), propertyName.c_str());
VerifyOrExit(propertyIter != mAsyncGetPropertyHandlers.end(), error = OT_ERROR_NOT_FOUND);
{
auto &interfaceHandlers = propertyIter->second;
auto interfaceIter = interfaceHandlers.find(propertyName);

VerifyOrExit(interfaceIter != interfaceHandlers.end(), error = OT_ERROR_NOT_FOUND);
(interfaceIter->second)(aRequest);
}
}

exit:
if (error != OT_ERROR_NONE)
{
otbrLogWarning("GetProperty %s.%s error:%s", interfaceName.c_str(), propertyName.c_str(),
ConvertToDBusErrorName(error));
aRequest.ReplyOtResult(error);
}
}

DBusObject::~DBusObject(void)
{
}
Expand Down
Loading

0 comments on commit c3fa90c

Please sign in to comment.