Possible Operator Usage/Deduction Error when Using REGISTER_STRUCT macros #458
-
|
Describe the bug To Reproduce Expected behavior Real (buggy) behavior Additional context // Type Helpers for std::optional
#include "sdbus-c++/sdbus-c++.h"
#include <optional>
template<typename T>
struct sdbus::signature_of<std::optional<T>> : public sdbus::signature_of<sdbus::Variant>{};
template<typename T>
inline sdbus::Message& operator<<(sdbus::Message& os, const std::optional<T> maybeValue){
static_assert(!std::is_same_v<T, bool>);
if(maybeValue){
os << sdbus::Variant(maybeValue.value());
}
else {
os << sdbus::Variant(false);
}
return os;
}
template<typename T>
inline sdbus::Message& operator>>(sdbus::Message& is, std::optional<T>& maybeValue){
static_assert(!std::is_same_v<T, bool>);
sdbus::Variant tmp;
is >> tmp;
if(tmp.containsValueOfType<T>()){
maybeValue = tmp.get<T>();
} else {
maybeValue = std::nullopt;
}
return is;
}
// This is working fine
struct Foo {
int member;
};
struct Bar {
std::optional<Foo> foo;
};
SDBUSCPP_REGISTER_STRUCT(Foo, member);
SDBUSCPP_REGISTER_STRUCT(Bar, foo);
// When using a type for which operators are already provided by the lib itself,
// it seems the template providers up top are not used/found by the compiler.
struct Foobar {
std::optional<int> foobar;
};
SDBUSCPP_REGISTER_STRUCT(Foobar, foobar);I'm basically looking for some guidance on this issue. Not really sure if its a bug with the lib or if I'm using it just wrong. Let me know if I can provide more info on this. |
Beta Was this translation helpful? Give feedback.
Replies: 4 comments
-
|
Hi, it's not dependent on a basic type defined by the lib -- you'll get the same error when you move The serialization and deserialization functions shall be placed in the Let me know if that helped. |
Beta Was this translation helpful? Give feedback.
-
|
@fwilmsh Here is the likely explanation to your issue: To find the correct
So the solution to this is as I said before: place the Alternatively, you can also place them in the namespace of your custom type (but extending |
Beta Was this translation helpful? Give feedback.
-
|
@fwilmsh Can we close the discussion thread? |
Beta Was this translation helpful? Give feedback.
-
|
It seems to work @sangelovic. Thanks for the detailed explanation. |
Beta Was this translation helpful? Give feedback.
@fwilmsh Here is the likely explanation to your issue:
To find the correct
operator<<implementation, the compiler involves unqualified name lookup (UNL) as well as argument dependent lookup (ADL) when building the set of candidates for overloaded operator resolution:In case of
Barregistration, theSDBUSCPP_REGISTER_STRUCTmacro callssdbus::detail::serialize_pack()method which callsoperator<<for all struct members. So from the context ofsdbus::detail::serialize_pack(), when resolvingoperator<<()forstd::optional<Foo>the compiler finds these candidates: