summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTom Joseph <tomjoseph@in.ibm.com>2018-09-14 10:02:20 +0530
committerBrad Bishop <bradleyb@fuzziesquirrel.com>2018-10-04 14:27:10 -0400
commit536ea32ddc61bc3f5ad34eada5788797e1771832 (patch)
tree184aa6f39ef50147245bed65254d614403998673
parent3618f443ceae49bbcbfd7d35563c23f876ca5d79 (diff)
downloadphosphor-user-manager-536ea32ddc61bc3f5ad34eada5788797e1771832.zip
phosphor-user-manager-536ea32ddc61bc3f5ad34eada5788797e1771832.tar.gz
ldap: Add application to configure privilege for LDAP groups
The application implements the xyz.openbmc_project.User.PrivilegeMapper D-Bus interface to configure privilege levels for LDAP groups. The Create method is used to create privilege mapping for the LDAP group. D-Bus object is created for each LDAP group and implements the D-Bus interface xyz.openbmc_project.User.PrivilegeMapperEntry. : Change-Id: I20935229a8a79ce1e52a857672a6a0085cb5ace4 Signed-off-by: Tom Joseph <tomjoseph@in.ibm.com>
-rw-r--r--.gitignore2
-rw-r--r--Makefile.am2
-rw-r--r--configure.ac6
-rw-r--r--phosphor-ldap-mapper/Makefile.am19
-rw-r--r--phosphor-ldap-mapper/ldap_mapper_entry.cpp62
-rw-r--r--phosphor-ldap-mapper/ldap_mapper_entry.hpp83
-rw-r--r--phosphor-ldap-mapper/ldap_mapper_mgr.cpp88
-rw-r--r--phosphor-ldap-mapper/ldap_mapper_mgr.hpp103
-rw-r--r--phosphor-ldap-mapper/main.cpp25
9 files changed, 388 insertions, 2 deletions
diff --git a/.gitignore b/.gitignore
index 075e76a..961e9b3 100644
--- a/.gitignore
+++ b/.gitignore
@@ -45,3 +45,5 @@ Makefile.in
Makefile
.deps
/*-libtool
+.project
+/phosphor-ldap-mapper/phosphor-ldap-mapper
diff --git a/Makefile.am b/Makefile.am
index b8b753d..915eedc 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -23,4 +23,4 @@ phosphor_user_manager_CXXFLAGS = $(SYSTEMD_CFLAGS) \
-DBOOST_SYSTEM_NO_DEPRECATED \
-DBOOST_ERROR_CODE_HEADER_ONLY
-SUBDIRS = . test
+SUBDIRS = . test phosphor-ldap-mapper
diff --git a/configure.ac b/configure.ac
index cf78609..fa32305 100644
--- a/configure.ac
+++ b/configure.ac
@@ -20,6 +20,10 @@ AC_ARG_VAR(USER_MANAGER_BUSNAME, [The Dbus busname to own])
AS_IF([test "x$USER_MANAGER_BUSNAME" == "x"], [USER_MANAGER_BUSNAME="xyz.openbmc_project.User.Manager"])
AC_DEFINE_UNQUOTED([USER_MANAGER_BUSNAME], ["$USER_MANAGER_BUSNAME"], [The DBus busname to own])
+AC_ARG_VAR(LDAP_MAPPER_MANAGER_BUSNAME, [The Dbus busname LDAP privilege mapper application])
+AS_IF([test "x$LDAP_MAPPER_MANAGER_BUSNAME" == "x"], [LDAP_MAPPER_MANAGER_BUSNAME="xyz.openbmc_project.LDAP.PrivilegeMapper"])
+AC_DEFINE_UNQUOTED([LDAP_MAPPER_MANAGER_BUSNAME], ["$LDAP_MAPPER_MANAGER_BUSNAME"], [The Dbus busname LDAP privilege mapper application])
+
# Default crypt algorithm to choose if one not found in shadow file
# Per crypt(3), 1 is for MD5
AC_ARG_VAR(DEFAULT_CRYPT_ALGO, [The default crypt algorithm if one not found in shadow])
@@ -57,5 +61,5 @@ AX_APPEND_COMPILE_FLAGS([-Wall -Werror], [CXXFLAGS])
LT_INIT
# Create configured output
-AC_CONFIG_FILES([Makefile test/Makefile])
+AC_CONFIG_FILES([Makefile test/Makefile phosphor-ldap-mapper/Makefile])
AC_OUTPUT
diff --git a/phosphor-ldap-mapper/Makefile.am b/phosphor-ldap-mapper/Makefile.am
new file mode 100644
index 0000000..4aeca7b
--- /dev/null
+++ b/phosphor-ldap-mapper/Makefile.am
@@ -0,0 +1,19 @@
+sbin_PROGRAMS = phosphor-ldap-mapper
+
+noinst_HEADERS = ldap_mapper_mgr.hpp \
+ ldap_mapper_entry.hpp
+
+phosphor_ldap_mapper_SOURCES = \
+ main.cpp \
+ ldap_mapper_mgr.cpp \
+ ldap_mapper_entry.cpp
+
+phosphor_ldap_mapper_LDFLAGS = $(SDBUSPLUS_LIBS) \
+ $(PHOSPHOR_DBUS_INTERFACES_LIBS) \
+ $(PHOSPHOR_LOGGING_LIBS) \
+ -lstdc++fs
+
+phosphor_ldap_mapper_CXXFLAGS = $(SYSTEMD_CFLAGS) \
+ $(PHOSPHOR_DBUS_INTERFACES_CFLAGS) \
+ $(PHOSPHOR_LOGGING_CFLAGS) \
+ -flto
diff --git a/phosphor-ldap-mapper/ldap_mapper_entry.cpp b/phosphor-ldap-mapper/ldap_mapper_entry.cpp
new file mode 100644
index 0000000..64d3578
--- /dev/null
+++ b/phosphor-ldap-mapper/ldap_mapper_entry.cpp
@@ -0,0 +1,62 @@
+#include <experimental/filesystem>
+#include <xyz/openbmc_project/Common/error.hpp>
+#include <xyz/openbmc_project/User/Common/error.hpp>
+#include <phosphor-logging/log.hpp>
+#include <phosphor-logging/elog.hpp>
+#include <phosphor-logging/elog-errors.hpp>
+#include "config.h"
+#include "ldap_mapper_entry.hpp"
+#include "ldap_mapper_mgr.hpp"
+
+namespace phosphor
+{
+namespace user
+{
+
+using namespace phosphor::logging;
+using InvalidArgument =
+ sdbusplus::xyz::openbmc_project::Common::Error::InvalidArgument;
+using Argument = xyz::openbmc_project::Common::InvalidArgument;
+
+LDAPMapperEntry::LDAPMapperEntry(sdbusplus::bus::bus &bus, const char *path,
+ const std::string &groupName,
+ const std::string &privilege,
+ LDAPMapperMgr &parent) :
+ Ifaces(bus, path, true),
+ id(std::stol(std::experimental::filesystem::path(path).filename())),
+ manager(parent)
+{
+ Ifaces::privilege(privilege, true);
+ Ifaces::groupName(groupName, true);
+ Ifaces::emit_object_added();
+}
+
+void LDAPMapperEntry::delete_(void)
+{
+ manager.deletePrivilegeMapper(id);
+}
+
+std::string LDAPMapperEntry::groupName(std::string value)
+{
+ if (value == Ifaces::groupName())
+ {
+ return value;
+ }
+
+ manager.checkPrivilegeMapper(value);
+ return Ifaces::groupName(value);
+}
+
+std::string LDAPMapperEntry::privilege(std::string value)
+{
+ if (value == Ifaces::privilege())
+ {
+ return value;
+ }
+
+ manager.checkPrivilegeLevel(value);
+ return Ifaces::privilege(value);
+}
+
+} // namespace user
+} // namespace phosphor
diff --git a/phosphor-ldap-mapper/ldap_mapper_entry.hpp b/phosphor-ldap-mapper/ldap_mapper_entry.hpp
new file mode 100644
index 0000000..689639d
--- /dev/null
+++ b/phosphor-ldap-mapper/ldap_mapper_entry.hpp
@@ -0,0 +1,83 @@
+#pragma once
+
+#include <sdbusplus/bus.hpp>
+#include <sdbusplus/server/object.hpp>
+#include <xyz/openbmc_project/User/PrivilegeMapperEntry/server.hpp>
+#include <xyz/openbmc_project/Object/Delete/server.hpp>
+
+namespace phosphor
+{
+namespace user
+{
+
+namespace Base = sdbusplus::xyz::openbmc_project;
+using Entry =
+ sdbusplus::xyz::openbmc_project::User::server::PrivilegeMapperEntry;
+using Delete = sdbusplus::xyz::openbmc_project::Object::server::Delete;
+using Ifaces = sdbusplus::server::object::object<Entry, Delete>;
+
+// Forward declaration for LDAPMapperMgr
+class LDAPMapperMgr;
+
+using Id = size_t;
+
+/** @class LDAPMapperEntry
+ *
+ * @brief This D-Bus object represents the privilege level for the LDAP group.
+ */
+class LDAPMapperEntry : public Ifaces
+{
+ public:
+ LDAPMapperEntry() = delete;
+ ~LDAPMapperEntry() = default;
+ LDAPMapperEntry(const LDAPMapperEntry &) = delete;
+ LDAPMapperEntry &operator=(const LDAPMapperEntry &) = delete;
+ LDAPMapperEntry(LDAPMapperEntry &&) = default;
+ LDAPMapperEntry &operator=(LDAPMapperEntry &&) = default;
+
+ /** @brief Constructs LDAP privilege mapper entry object.
+ *
+ * @param[in] bus - sdbusplus handler
+ * @param[in] path - D-Bus path
+ * @param[in] privilege - the privilege for the group
+ * @param[in] parent - LDAP privilege mapper manager
+ */
+ LDAPMapperEntry(sdbusplus::bus::bus &bus, const char *path,
+ const std::string &groupName, const std::string &privilege,
+ LDAPMapperMgr &parent);
+
+ /** @brief Delete privilege mapper entry object
+ *
+ * This method deletes the privilege mapper entry.
+ */
+ void delete_(void) override;
+
+ /** @brief Update the group name of the mapper object
+ *
+ * @param[in] value - group name
+ *
+ * @return On success the updated group name
+ */
+ std::string groupName(std::string value) override;
+
+ /** @brief Update privilege associated with LDAP group
+ *
+ * @param[in] value - privilege level
+ *
+ * @return On success the updated privilege level
+ */
+ std::string privilege(std::string value) override;
+
+ using sdbusplus::xyz::openbmc_project::User::server::PrivilegeMapperEntry::
+ privilege;
+
+ using sdbusplus::xyz::openbmc_project::User::server::PrivilegeMapperEntry::
+ groupName;
+
+ private:
+ Id id;
+ LDAPMapperMgr &manager;
+};
+
+} // namespace user
+} // namespace phosphor
diff --git a/phosphor-ldap-mapper/ldap_mapper_mgr.cpp b/phosphor-ldap-mapper/ldap_mapper_mgr.cpp
new file mode 100644
index 0000000..9fe40ad
--- /dev/null
+++ b/phosphor-ldap-mapper/ldap_mapper_mgr.cpp
@@ -0,0 +1,88 @@
+#include <xyz/openbmc_project/Common/error.hpp>
+#include <xyz/openbmc_project/User/Common/error.hpp>
+#include <phosphor-logging/log.hpp>
+#include <phosphor-logging/elog.hpp>
+#include <phosphor-logging/elog-errors.hpp>
+#include "config.h"
+#include "ldap_mapper_mgr.hpp"
+
+namespace phosphor
+{
+namespace user
+{
+
+using namespace phosphor::logging;
+using InvalidArgument =
+ sdbusplus::xyz::openbmc_project::Common::Error::InvalidArgument;
+using Argument = xyz::openbmc_project::Common::InvalidArgument;
+using PrivilegeMappingExists = sdbusplus::xyz::openbmc_project::User::Common::
+ Error::PrivilegeMappingExists;
+
+LDAPMapperMgr::LDAPMapperMgr(sdbusplus::bus::bus &bus, const char *path) :
+ MapperMgrIface(bus, path), bus(bus), path(path)
+{
+}
+
+ObjectPath LDAPMapperMgr::create(std::string groupName, std::string privilege)
+{
+ checkPrivilegeMapper(groupName);
+ checkPrivilegeLevel(privilege);
+
+ entryId++;
+
+ // Object path for the LDAP group privilege mapper entry
+ auto mapperObject =
+ std::string(mapperMgrRoot) + "/" + std::to_string(entryId);
+
+ // Create mapping for LDAP privilege mapper entry
+ auto entry = std::make_unique<phosphor::user::LDAPMapperEntry>(
+ bus, mapperObject.c_str(), groupName, privilege, *this);
+
+ PrivilegeMapperList.emplace(entryId, std::move(entry));
+
+ return mapperObject;
+}
+
+void LDAPMapperMgr::deletePrivilegeMapper(Id id)
+{
+ PrivilegeMapperList.erase(id);
+}
+
+void LDAPMapperMgr::checkPrivilegeMapper(const std::string &groupName)
+{
+ if (groupName.empty())
+ {
+ log<level::ERR>("Group name is empty");
+ elog<InvalidArgument>(Argument::ARGUMENT_NAME("Group name"),
+ Argument::ARGUMENT_VALUE("Null"));
+ }
+
+ for (const auto &val : PrivilegeMapperList)
+ {
+ if (val.second.get()->groupName() == groupName)
+ {
+ log<level::ERR>("Group name already exists");
+ elog<PrivilegeMappingExists>();
+ }
+ }
+}
+
+void LDAPMapperMgr::checkPrivilegeLevel(const std::string &privilege)
+{
+ if (privilege.empty())
+ {
+ log<level::ERR>("Privilege level is empty");
+ elog<InvalidArgument>(Argument::ARGUMENT_NAME("Privilege level"),
+ Argument::ARGUMENT_VALUE("Null"));
+ }
+
+ if (std::find(privMgr.begin(), privMgr.end(), privilege) == privMgr.end())
+ {
+ log<level::ERR>("Invalid privilege");
+ elog<InvalidArgument>(Argument::ARGUMENT_NAME("Privilege level"),
+ Argument::ARGUMENT_VALUE(privilege.c_str()));
+ }
+}
+
+} // namespace user
+} // namespace phosphor
diff --git a/phosphor-ldap-mapper/ldap_mapper_mgr.hpp b/phosphor-ldap-mapper/ldap_mapper_mgr.hpp
new file mode 100644
index 0000000..450626d
--- /dev/null
+++ b/phosphor-ldap-mapper/ldap_mapper_mgr.hpp
@@ -0,0 +1,103 @@
+#pragma once
+
+#include <sdbusplus/bus.hpp>
+#include <sdbusplus/server/object.hpp>
+#include "ldap_mapper_entry.hpp"
+#include <xyz/openbmc_project/User/PrivilegeMapper/server.hpp>
+#include <map>
+#include <set>
+
+namespace phosphor
+{
+
+namespace user
+{
+
+using MapperMgrIface =
+ sdbusplus::xyz::openbmc_project::User::server::PrivilegeMapper;
+using ObjectPath = sdbusplus::message::object_path;
+
+// D-Bus root for LDAP privilege mapper
+constexpr auto mapperMgrRoot = "/xyz/openbmc_project/user/ldap";
+
+/** @class LDAPMapperMgr
+ *
+ * @brief Responsible for managing LDAP groups to privilege mapping.
+ */
+class LDAPMapperMgr : public MapperMgrIface
+{
+ public:
+ LDAPMapperMgr() = delete;
+ ~LDAPMapperMgr() = default;
+ LDAPMapperMgr(const LDAPMapperMgr &) = delete;
+ LDAPMapperMgr &operator=(const LDAPMapperMgr &) = delete;
+ LDAPMapperMgr(LDAPMapperMgr &&) = delete;
+ LDAPMapperMgr &operator=(LDAPMapperMgr &&) = delete;
+
+ /** @brief Constructs LDAPMapperMgr object.
+ *
+ * @param[in] bus - sdbusplus handler
+ * @param[in] path - D-Bus path
+ */
+ LDAPMapperMgr(sdbusplus::bus::bus &bus, const char *path);
+
+ /** @brief Creates a mapping for the group to the privilege
+ *
+ * @param[in] groupName - Group Name to which the privilege needs to be
+ * assigned.
+ * @param[in] privilege - The privilege role associated with the group.
+ *
+ * @return On success return the D-Bus object path of the created privilege
+ * mapper entry.
+ */
+ ObjectPath create(std::string groupName, std::string privilege) override;
+
+ /** @brief Delete privilege mapping for LDAP group
+ *
+ * This method deletes the privilege mapping
+ *
+ * @param[in] groupName - name of the LDAP group for which privilege
+ * mapping is to be deleted.
+ */
+ void deletePrivilegeMapper(Id id);
+
+ /** @brief Check if LDAP group privilege mapping requested is valid
+ *
+ * Check if the privilege mapping already exists for the LDAP group name
+ * and group name is empty.
+ *
+ * @param[in] groupName - LDAP group name
+ *
+ * @return throw exception if the conditions are not met.
+ */
+ void checkPrivilegeMapper(const std::string &groupName);
+
+ /** @brief Check if the privilege level is a valid one
+ *
+ * @param[in] privilege - Privilege level
+ *
+ * @return throw exception if the conditions are not met.
+ */
+ void checkPrivilegeLevel(const std::string &privilege);
+
+ private:
+ /** @brief sdbusplus handler */
+ sdbusplus::bus::bus &bus;
+
+ /** @brief object path for the manager object*/
+ const std::string path;
+
+ /** @brief available privileges container */
+ std::set<std::string> privMgr = {"priv-admin", "priv-operator", "priv-user",
+ "priv-callback"};
+
+ /** @brief Id of the last privilege mapper entry */
+ Id entryId = 0;
+
+ /** @brief container to hold privilege mapper objects */
+ std::map<Id, std::unique_ptr<phosphor::user::LDAPMapperEntry>>
+ PrivilegeMapperList;
+};
+
+} // namespace user
+} // namespace phosphor
diff --git a/phosphor-ldap-mapper/main.cpp b/phosphor-ldap-mapper/main.cpp
new file mode 100644
index 0000000..b4a0650
--- /dev/null
+++ b/phosphor-ldap-mapper/main.cpp
@@ -0,0 +1,25 @@
+#include <string>
+#include <experimental/filesystem>
+#include "config.h"
+#include "ldap_mapper_mgr.hpp"
+
+int main(int argc, char** argv)
+{
+ auto bus = sdbusplus::bus::new_default();
+ sdbusplus::server::manager::manager objManager(
+ bus, phosphor::user::mapperMgrRoot);
+
+ phosphor::user::LDAPMapperMgr mapperMgr(bus, phosphor::user::mapperMgrRoot);
+
+ // Claim the bus name for the application
+ bus.request_name(LDAP_MAPPER_MANAGER_BUSNAME);
+
+ // Wait for client request
+ while (true)
+ {
+ // Process D-Bus calls
+ bus.process_discard();
+ bus.wait();
+ }
+ return 0;
+}
OpenPOWER on IntegriCloud