REST: Add method return support for basic types
Add support for returning the basic D-Bus types,
such as int, string, etc, from methods.
It does this by using the sd_bus_message_read_basic
API to pull the data out of the method response message,
and then converts it to JSON.
Future commits will add array/dict/variant support.
Change-Id: I937d22330a9c2df443942ea84e45d894244388ff
Signed-off-by: Matt Spinler <spinler@us.ibm.com>
diff --git a/include/openbmc_dbus_rest.hpp b/include/openbmc_dbus_rest.hpp
index 895f436..18b99dd 100644
--- a/include/openbmc_dbus_rest.hpp
+++ b/include/openbmc_dbus_rest.hpp
@@ -795,9 +795,153 @@
return r;
}
+template <typename T>
+int readMessageItem(const std::string &typeCode, sdbusplus::message::message &m,
+ nlohmann::json &data)
+{
+ T value;
+
+ int r = sd_bus_message_read_basic(m.get(), typeCode.front(), &value);
+ if (r < 0)
+ {
+ BMCWEB_LOG_ERROR << "sd_bus_message_read_basic on type " << typeCode
+ << " failed!";
+ return r;
+ }
+
+ data = value;
+ return 0;
+}
+
int convertDBusToJSON(const std::string &returnType,
sdbusplus::message::message &m, nlohmann::json &response)
{
+ int r = 0;
+ const std::vector<std::string> returnTypes = dbusArgSplit(returnType);
+
+ nlohmann::json &thisElement = response;
+ for (const std::string &typeCode : returnTypes)
+ {
+ if (returnType.size() > 1)
+ {
+ response.push_back(nlohmann::json{});
+ thisElement = response.back();
+ }
+
+ if (typeCode == "s")
+ {
+ r = readMessageItem<char *>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "g")
+ {
+ r = readMessageItem<char *>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "o")
+ {
+ r = readMessageItem<char *>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "b")
+ {
+ r = readMessageItem<int>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+
+ thisElement = static_cast<bool>(thisElement.get<int>());
+ }
+ else if (typeCode == "u")
+ {
+ r = readMessageItem<uint32_t>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "i")
+ {
+ r = readMessageItem<int32_t>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "x")
+ {
+ r = readMessageItem<int64_t>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "t")
+ {
+ r = readMessageItem<uint64_t>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "n")
+ {
+ r = readMessageItem<int16_t>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "q")
+ {
+ r = readMessageItem<uint16_t>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "y")
+ {
+ r = readMessageItem<uint8_t>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "d")
+ {
+ r = readMessageItem<double>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else if (typeCode == "h")
+ {
+ r = readMessageItem<int>(typeCode, m, thisElement);
+ if (r < 0)
+ {
+ return r;
+ }
+ }
+ else
+ {
+ // TODO: add array, dict, variant support
+ BMCWEB_LOG_ERROR << "Invalid D-Bus signature type " << typeCode;
+ return -2;
+ }
+ }
+
return 0;
}