forked from Kistler-Group/sdbus-cpp
Add support for Unix fd D-Bus type
This commit is contained in:
committed by
Stanislav Angelovič
parent
efe799ef3f
commit
57c840637c
@ -43,6 +43,7 @@ namespace sdbus {
|
||||
class ObjectPath;
|
||||
class Signature;
|
||||
template <typename... _ValueTypes> class Struct;
|
||||
struct UnixFd;
|
||||
class MethodReply;
|
||||
namespace internal {
|
||||
class ISdBus;
|
||||
@ -100,6 +101,7 @@ namespace sdbus {
|
||||
Message& operator<<(const Variant &item);
|
||||
Message& operator<<(const ObjectPath &item);
|
||||
Message& operator<<(const Signature &item);
|
||||
Message& operator<<(const UnixFd &item);
|
||||
|
||||
Message& operator>>(bool& item);
|
||||
Message& operator>>(int16_t& item);
|
||||
@ -115,6 +117,7 @@ namespace sdbus {
|
||||
Message& operator>>(Variant &item);
|
||||
Message& operator>>(ObjectPath &item);
|
||||
Message& operator>>(Signature &item);
|
||||
Message& operator>>(UnixFd &item);
|
||||
|
||||
Message& openContainer(const std::string& signature);
|
||||
Message& closeContainer();
|
||||
|
@ -40,6 +40,7 @@ namespace sdbus {
|
||||
template <typename... _ValueTypes> class Struct;
|
||||
class ObjectPath;
|
||||
class Signature;
|
||||
struct UnixFd;
|
||||
class Message;
|
||||
class MethodCall;
|
||||
class MethodReply;
|
||||
@ -285,6 +286,17 @@ namespace sdbus {
|
||||
}
|
||||
};
|
||||
|
||||
template <>
|
||||
struct signature_of<UnixFd>
|
||||
{
|
||||
static constexpr bool is_valid = true;
|
||||
|
||||
static const std::string str()
|
||||
{
|
||||
return "h";
|
||||
}
|
||||
};
|
||||
|
||||
template <typename _Element>
|
||||
struct signature_of<std::vector<_Element>>
|
||||
{
|
||||
|
@ -97,6 +97,12 @@ namespace sdbus {
|
||||
mutable Message msg_{};
|
||||
};
|
||||
|
||||
/********************************************//**
|
||||
* @class Struct
|
||||
*
|
||||
* Representation of struct D-Bus type
|
||||
*
|
||||
***********************************************/
|
||||
template <typename... _ValueTypes>
|
||||
class Struct
|
||||
: public std::tuple<_ValueTypes...>
|
||||
@ -135,6 +141,12 @@ namespace sdbus {
|
||||
return result_type(std::forward<_Elements>(args)...);
|
||||
}
|
||||
|
||||
/********************************************//**
|
||||
* @class ObjectPath
|
||||
*
|
||||
* Representation of object path D-Bus type
|
||||
*
|
||||
***********************************************/
|
||||
class ObjectPath : public std::string
|
||||
{
|
||||
public:
|
||||
@ -146,6 +158,12 @@ namespace sdbus {
|
||||
using std::string::operator=;
|
||||
};
|
||||
|
||||
/********************************************//**
|
||||
* @class Signature
|
||||
*
|
||||
* Representation of Signature D-Bus type
|
||||
*
|
||||
***********************************************/
|
||||
class Signature : public std::string
|
||||
{
|
||||
public:
|
||||
@ -157,6 +175,27 @@ namespace sdbus {
|
||||
using std::string::operator=;
|
||||
};
|
||||
|
||||
/********************************************//**
|
||||
* @struct UnixFd
|
||||
*
|
||||
* Representation of Unix file descriptor D-Bus type
|
||||
*
|
||||
***********************************************/
|
||||
struct UnixFd
|
||||
{
|
||||
int fd_ = -1;
|
||||
|
||||
UnixFd() = default;
|
||||
UnixFd(int fd)
|
||||
: fd_(fd)
|
||||
{}
|
||||
|
||||
operator int() const
|
||||
{
|
||||
return fd_;
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif /* SDBUS_CXX_TYPES_H_ */
|
||||
|
@ -210,7 +210,15 @@ Message& Message::operator<<(const ObjectPath &item)
|
||||
Message& Message::operator<<(const Signature &item)
|
||||
{
|
||||
auto r = sd_bus_message_append_basic((sd_bus_message*)msg_, SD_BUS_TYPE_SIGNATURE, item.c_str());
|
||||
SDBUS_THROW_ERROR_IF(r < 0, "Failed to serialize an Signature value", -r);
|
||||
SDBUS_THROW_ERROR_IF(r < 0, "Failed to serialize a Signature value", -r);
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
Message& Message::operator<<(const UnixFd &item)
|
||||
{
|
||||
auto r = sd_bus_message_append_basic((sd_bus_message*)msg_, SD_BUS_TYPE_UNIX_FD, &item.fd_);
|
||||
SDBUS_THROW_ERROR_IF(r < 0, "Failed to serialize a UnixFd value", -r);
|
||||
|
||||
return *this;
|
||||
}
|
||||
@ -383,6 +391,17 @@ Message& Message::operator>>(Signature &item)
|
||||
return *this;
|
||||
}
|
||||
|
||||
Message& Message::operator>>(UnixFd &item)
|
||||
{
|
||||
auto r = sd_bus_message_read_basic((sd_bus_message*)msg_, SD_BUS_TYPE_UNIX_FD, &item.fd_);
|
||||
if (r == 0)
|
||||
ok_ = false;
|
||||
|
||||
SDBUS_THROW_ERROR_IF(r < 0, "Failed to deserialize a UnixFd value", -r);
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
Message& Message::openContainer(const std::string& signature)
|
||||
{
|
||||
|
@ -209,6 +209,12 @@ TEST_F(SdbusTestObject, CallsMethodWithObjectPathSuccesfully)
|
||||
ASSERT_THAT(resObjectPath, Eq(OBJECT_PATH_VALUE));
|
||||
}
|
||||
|
||||
TEST_F(SdbusTestObject, CallsMethodWithUnixFdSuccesfully)
|
||||
{
|
||||
auto resUnixFd = m_proxy->getUnixFd();
|
||||
ASSERT_THAT(resUnixFd, Gt(UNIX_FD_VALUE));
|
||||
}
|
||||
|
||||
TEST_F(SdbusTestObject, CallsMethodWithComplexTypeSuccesfully)
|
||||
{
|
||||
auto resComplex = m_proxy->getComplex();
|
||||
|
@ -157,6 +157,10 @@ protected:
|
||||
{
|
||||
return OBJECT_PATH_VALUE;
|
||||
}
|
||||
sdbus::UnixFd getUnixFd() const
|
||||
{
|
||||
return UNIX_FD_VALUE;
|
||||
}
|
||||
|
||||
ComplexType getComplex() const
|
||||
{
|
||||
|
@ -97,6 +97,7 @@ protected:
|
||||
|
||||
object_.registerMethod("getSignature").onInterface(INTERFACE_NAME).implementedAs([this](){ return this->getSignature(); });
|
||||
object_.registerMethod("getObjectPath").onInterface(INTERFACE_NAME).implementedAs([this](){ return this->getObjectPath(); });
|
||||
object_.registerMethod("getUnixFd").onInterface(INTERFACE_NAME).implementedAs([this](){ return this->getUnixFd(); });
|
||||
|
||||
object_.registerMethod("getComplex").onInterface(INTERFACE_NAME).implementedAs([this](){ return this->getComplex(); }).markAsDeprecated();
|
||||
|
||||
@ -163,6 +164,7 @@ protected:
|
||||
virtual void doOperationAsync(uint32_t param, sdbus::Result<uint32_t> result) = 0;
|
||||
virtual sdbus::Signature getSignature() const = 0;
|
||||
virtual sdbus::ObjectPath getObjectPath() const = 0;
|
||||
virtual sdbus::UnixFd getUnixFd() const = 0;
|
||||
virtual ComplexType getComplex() const = 0;
|
||||
virtual void throwError() const = 0;
|
||||
|
||||
@ -266,6 +268,9 @@ R"delimiter(<!DOCTYPE node PUBLIC "-//freedesktop//DTD D-BUS Object Introspectio
|
||||
<arg type="u" direction="out"/>
|
||||
<arg type="s" direction="out"/>
|
||||
</method>
|
||||
<method name="getUnixFd">
|
||||
<arg type="h" direction="out"/>
|
||||
</method>
|
||||
<method name="multiply">
|
||||
<arg type="x" direction="in"/>
|
||||
<arg type="d" direction="in"/>
|
||||
|
@ -40,6 +40,7 @@ constexpr const int32_t INT64_VALUE{-1024};
|
||||
const std::string STRING_VALUE{"sdbus-c++-testing"};
|
||||
const sdbus::Signature SIGNATURE_VALUE{"a{is}"};
|
||||
const sdbus::ObjectPath OBJECT_PATH_VALUE{"/"};
|
||||
const int UNIX_FD_VALUE = 0;
|
||||
|
||||
const std::string DEFAULT_STATE_VALUE{"default-state-value"};
|
||||
const uint32_t DEFAULT_ACTION_VALUE{999};
|
||||
|
@ -175,6 +175,13 @@ public:
|
||||
return result;
|
||||
}
|
||||
|
||||
sdbus::UnixFd getUnixFd()
|
||||
{
|
||||
sdbus::UnixFd result;
|
||||
object_.callMethod("getUnixFd").onInterface(INTERFACE_NAME).storeResultsTo(result);
|
||||
return result;
|
||||
}
|
||||
|
||||
ComplexType getComplex()
|
||||
{
|
||||
ComplexType result;
|
||||
|
@ -30,6 +30,7 @@
|
||||
#include <cstdint>
|
||||
|
||||
using ::testing::Eq;
|
||||
using ::testing::Gt;
|
||||
using ::testing::DoubleEq;
|
||||
using namespace std::string_literals;
|
||||
|
||||
@ -125,6 +126,21 @@ TEST(AMessage, CanCarryASimpleInteger)
|
||||
ASSERT_THAT(dataRead, Eq(dataWritten));
|
||||
}
|
||||
|
||||
TEST(AMessage, CanCarryAUnixFd)
|
||||
{
|
||||
sdbus::Message msg{sdbus::createPlainMessage()};
|
||||
|
||||
sdbus::UnixFd dataWritten = 0;
|
||||
msg << dataWritten;
|
||||
|
||||
msg.seal();
|
||||
|
||||
sdbus::UnixFd dataRead;
|
||||
msg >> dataRead;
|
||||
|
||||
ASSERT_THAT(dataRead, Gt(dataWritten));
|
||||
}
|
||||
|
||||
TEST(AMessage, CanCarryAVariant)
|
||||
{
|
||||
sdbus::Message msg{sdbus::createPlainMessage()};
|
||||
|
@ -72,6 +72,7 @@ namespace
|
||||
TYPE(sdbus::ObjectPath)HAS_DBUS_TYPE_SIGNATURE("o")
|
||||
TYPE(sdbus::Signature)HAS_DBUS_TYPE_SIGNATURE("g")
|
||||
TYPE(sdbus::Variant)HAS_DBUS_TYPE_SIGNATURE("v")
|
||||
TYPE(sdbus::UnixFd)HAS_DBUS_TYPE_SIGNATURE("h")
|
||||
TYPE(sdbus::Struct<bool>)HAS_DBUS_TYPE_SIGNATURE("(b)")
|
||||
TYPE(sdbus::Struct<uint16_t, double, std::string, sdbus::Variant>)HAS_DBUS_TYPE_SIGNATURE("(qdsv)")
|
||||
TYPE(std::vector<int16_t>)HAS_DBUS_TYPE_SIGNATURE("an")
|
||||
@ -91,10 +92,11 @@ namespace
|
||||
>
|
||||
>,
|
||||
sdbus::Signature,
|
||||
sdbus::UnixFd,
|
||||
const char*
|
||||
>
|
||||
>;
|
||||
TYPE(ComplexType)HAS_DBUS_TYPE_SIGNATURE("a{t(a{ya(obva{is})}gs)}")
|
||||
TYPE(ComplexType)HAS_DBUS_TYPE_SIGNATURE("a{t(a{ya(obva{is})}ghs)}")
|
||||
|
||||
typedef ::testing::Types< bool
|
||||
, uint8_t
|
||||
@ -110,6 +112,7 @@ namespace
|
||||
, sdbus::ObjectPath
|
||||
, sdbus::Signature
|
||||
, sdbus::Variant
|
||||
, sdbus::UnixFd
|
||||
, sdbus::Struct<bool>
|
||||
, sdbus::Struct<uint16_t, double, std::string, sdbus::Variant>
|
||||
, std::vector<int16_t>
|
||||
|
@ -240,3 +240,10 @@ TEST(ASignature, CanBeConstructedFromStdString)
|
||||
|
||||
ASSERT_THAT(sdbus::Signature{aSignature}, Eq(aSignature));
|
||||
}
|
||||
|
||||
TEST(AUnixFd, CanBeConstructedFromInt)
|
||||
{
|
||||
int fd{2};
|
||||
|
||||
ASSERT_THAT((int)sdbus::UnixFd{fd}, Eq(fd));
|
||||
}
|
||||
|
@ -44,6 +44,7 @@ const char *atomic_type_to_string(char t)
|
||||
{ 'o', "sdbus::ObjectPath" },
|
||||
{ 'g', "sdbus::Signature" },
|
||||
{ 'v', "sdbus::Variant" },
|
||||
{ 'h', "sdbus::UnixFd" },
|
||||
{ '\0', "" }
|
||||
};
|
||||
|
||||
|
Reference in New Issue
Block a user