Added AgentPolicyAdapter to agent_policy lib to provide API for agent to enforce...
authorAndriy Gudz <a.gudz@samsung.com>
Thu, 18 May 2017 18:09:25 +0000 (21:09 +0300)
committerAndriy Gudz <a.gudz@samsung.com>
Thu, 18 May 2017 18:09:25 +0000 (21:09 +0300)
device_core/agent_lib/CMakeLists.txt
device_core/agent_lib/inc/agentpolicyadapter.h [new file with mode: 0644]
device_core/agent_lib/inc/iagentpolicy.h [new file with mode: 0644]
device_core/agent_lib/rmi/CMakeLists.txt
device_core/agent_lib/src/agentpolicyadapter.cpp [new file with mode: 0644]
device_core/packaging/ioswsec.spec
device_core/scripts/deploy.sh
device_core/utest/test_rmi.cpp

index 65e7e9a..800c935 100644 (file)
@@ -11,12 +11,9 @@ include_directories (
 
 FILE(GLOB SRCS src/*.cpp)
 
-add_library (${PROJECT_NAME} ${SRCS})
+add_library (${PROJECT_NAME} SHARED ${SRCS})
 
-target_link_libraries(${PROJECT_NAME}
-       ${IOTIVITY_LIB_PROJECT_NAME}
-       ${RMI_PROJECT_NAME}
-)
+target_link_libraries(${PROJECT_NAME} ${RMI_PROJECT_NAME})
 
 install(TARGETS ${PROJECT_NAME} DESTINATION ${LIBDIR})
 #install(FILES tests.manifest DESTINATION ${MANIFESTDIR})
diff --git a/device_core/agent_lib/inc/agentpolicyadapter.h b/device_core/agent_lib/inc/agentpolicyadapter.h
new file mode 100644 (file)
index 0000000..c6b13d9
--- /dev/null
@@ -0,0 +1,50 @@
+/**
+ * @brief  TODO
+ * @date   Created 18.05.2017
+ * @author Created 2017 in Samsung Ukraine R&D Center (SURC) under a contract
+ *                between LLC "Samsung Electronics Ukraine Company" (Kiev, Ukraine)
+ *                and "Samsung Electronics Co", Ltd (Seoul, Republic of Korea).
+ *         Copyright: (c) Samsung Electronics Co, Ltd 2017. All rights reserved.
+ * @author Mail to: <A HREF="mailto:a.gudz@samsung.com">Andriy Gudz, a.gudz@samsung.com</A>
+ */
+#ifndef AGENTPOLICYADAPTER_H
+#define AGENTPOLICYADAPTER_H
+
+#include <string>
+
+#include "rmi/client.h"
+#include "iagentpolicy.h"
+
+class AgentPolicyAdapter: public IAgentPolicy
+{
+public:
+    /**
+     * @brief AgentPolicyAdapter
+     * @param agentId
+     */
+    AgentPolicyAdapter();
+
+    /**
+     * @brief AgentPolicyAdapter Destructor
+     */
+    ~AgentPolicyAdapter();
+
+    /**
+     * @brief enforcePolicy method sends policy (json data) from calling process to service daemon.
+     * @param agentId id of agent program that want to enforce policy
+     * @param jsonData string that represent json data
+     * @return result code of type AgentPolicyResult
+     */
+    virtual int enforcePolicy(std::string agentId, std::string jsonData);
+
+    /**
+     * @brief getServicePid returns process id of running service
+     * @return process id of running service
+     */
+    virtual pid_t getServicePid();
+
+private:
+    std::unique_ptr<rmi::Client> rmiClient;
+};
+
+#endif // AGENTPOLICYADAPTER_H
diff --git a/device_core/agent_lib/inc/iagentpolicy.h b/device_core/agent_lib/inc/iagentpolicy.h
new file mode 100644 (file)
index 0000000..9f25a46
--- /dev/null
@@ -0,0 +1,57 @@
+/**
+ * @brief  Common interface for agent policy IPC
+ * @date   Created 18.05.2017
+ * @author Created 2017 in Samsung Ukraine R&D Center (SURC) under a contract
+ *                between LLC "Samsung Electronics Ukraine Company" (Kiev, Ukraine)
+ *                and "Samsung Electronics Co", Ltd (Seoul, Republic of Korea).
+ *         Copyright: (c) Samsung Electronics Co, Ltd 2017. All rights reserved.
+ * @author Mail to: <A HREF="mailto:a.gudz@samsung.com">Andriy Gudz, a.gudz@samsung.com</A>
+ */
+#ifndef IAGENTPOLICY_H
+#define IAGENTPOLICY_H
+
+/**
+ * @brief The AgentPolicyResult enum describes possible result codes
+ */
+enum AgentPolicyResult
+{
+    SUCCESS,
+    FAIL,
+};
+
+/**
+ * @brief The IAgentPolicy class is common interface for classes that implement
+ * adapter and service.
+ */
+class IAgentPolicy
+{
+public:
+    /**
+     * @brief enforcePolicy method sends policy (json data) from calling process to service daemon.
+     * @param agentId id of agent program that want to enforce policy
+     * @param jsonData string that represent json data
+     * @return result code of type AgentPolicyResult
+     */
+    virtual int enforcePolicy(std::string agentId, std::string jsonData) = 0;
+
+    /**
+     * @brief getServicePid returns process id of running service
+     * @return process id of running service
+     */
+    virtual pid_t getServicePid() = 0;
+
+    /**
+     * @brief RMI_ADDRESS is path to file. Contact point of adapter and service on a filesystem.
+     */
+    static const std::string RMI_ADDRESS;
+
+    /**
+     * @brief RMI_SERVICE_NAME is default name of service class. Adapter implementation use it call service
+     */
+    static const std::string RMI_SERVICE_NAME;
+};
+
+const std::string IAgentPolicy::RMI_ADDRESS = "/tmp/.rmi_agent_policy";
+const std::string IAgentPolicy::RMI_SERVICE_NAME = "AgentPolicyService";
+
+#endif // IAGENTPOLICY_H
index 115386f..df9a086 100644 (file)
@@ -1,5 +1,7 @@
 project(${RMI_PROJECT_NAME})
 
+SET (CMAKE_CXX_FLAGS " ${CMAKE_CXX_FLAGS} -fPIC ")
+
 FILE(GLOB SRCS src/*.cpp src/rmi/*.cpp)
 
 include_directories(inc inc/rmi)
diff --git a/device_core/agent_lib/src/agentpolicyadapter.cpp b/device_core/agent_lib/src/agentpolicyadapter.cpp
new file mode 100644 (file)
index 0000000..b2f5337
--- /dev/null
@@ -0,0 +1,35 @@
+/**
+ * @brief  TODO
+ * @date   Created 18.05.2017
+ * @author Created 2017 in Samsung Ukraine R&D Center (SURC) under a contract
+ *                between LLC "Samsung Electronics Ukraine Company" (Kiev, Ukraine)
+ *                and "Samsung Electronics Co", Ltd (Seoul, Republic of Korea).
+ *         Copyright: (c) Samsung Electronics Co, Ltd 2017. All rights reserved.
+ * @author Mail to: <A HREF="mailto:a.gudz@samsung.com">Andriy Gudz, a.gudz@samsung.com</A>
+ */
+#include "agentpolicyadapter.h"
+
+#include <stdexcept>
+
+AgentPolicyAdapter::AgentPolicyAdapter()
+{
+    rmiClient.reset(new rmi::Client(RMI_ADDRESS));
+    rmiClient->connect();
+}
+
+pid_t AgentPolicyAdapter::getServicePid()
+{
+    static std::string serviceMethod = RMI_SERVICE_NAME + "::" + __FUNCTION__;
+    return rmiClient->methodCall<pid_t>(serviceMethod);
+}
+
+int AgentPolicyAdapter::enforcePolicy(std::string agentId, std::string jsonData)
+{
+    static std::string serviceMethod = RMI_SERVICE_NAME + "::" + __FUNCTION__;
+    return (AgentPolicyResult)rmiClient->methodCall<int>(serviceMethod, agentId, jsonData);
+}
+
+AgentPolicyAdapter::~AgentPolicyAdapter()
+{
+    rmiClient->disconnect();
+}
index aff1aa6..50b00e7 100644 (file)
@@ -79,6 +79,7 @@ Network Manager shared library
 %manifest %{_manifestdir}/NetworkManager.manifest
 %defattr(-,root,root,-)
 %{_libdir}/libnmlib.so
+%{_libdir}/libagent_policy.so
 
 
 ##############################################
index f148bc0..d97c809 100755 (executable)
@@ -61,4 +61,4 @@ sdb push ${RPMS_TO_PUSH} /tmp/nm/
 
 sdb shell "rpm -Uvih --nodeps --force --replacefiles /tmp/nm/nwmanager-*.rpm"
 
-sdb shell "/usr/apps/network-manager/utest"
+sdb shell "/usr/apps/network-manager/utest --gtest_filter=-IoTDevManagerTest.device_discovery"
index 430c385..862fae5 100644 (file)
 
 #include "rmi/service.h"
 #include "rmi/client.h"
+#include "agentpolicyadapter.h"
+
 #include <signal.h>
 #include <execinfo.h>
 
 using namespace std;
 
-namespace
-{
-const std::string RMI_SERVICE_ADDRESS = "/tmp/.rmi_handshakeCorrect";
-}
-
-class AgentInterface
+/**
+ * @brief The AgentPolicyService class is mock RMI Service for IPC test
+ */
+class AgentPolicyService: public IAgentPolicy
 {
 public:
+    AgentPolicyService()
+    {
+        service.reset(new rmi::Service(RMI_ADDRESS));
+        service->registerParametricMethod(this, (int)(AgentPolicyService::enforcePolicy)(string, string));
+        service->registerNonparametricMethod(this, (pid_t)(AgentPolicyService::getServicePid)());
+
+        service->registerParametricMethod(this, (string)(AgentPolicyService::handshake)(string));
+        service->registerNonparametricMethod(this, (pid_t)(AgentPolicyService::getPeerPid)());
+    }
+
+    ~AgentPolicyService()
+    {
+    }
+
     void run()
     {
         service->start();
@@ -46,30 +60,17 @@ public:
         return service->getPeerPid();
     }
 
-    pid_t getChildPid()
+    virtual pid_t getServicePid()
     {
         return getpid();
     }
 
-    static AgentInterface& instance()
+    virtual int enforcePolicy(std::string agentId, std::string jsonData)
     {
-        static AgentInterface _instance_;
-        return _instance_;
+        return 0;
     }
 
 private:
-    AgentInterface()
-    {
-        service.reset(new rmi::Service(RMI_SERVICE_ADDRESS));
-        service->registerParametricMethod(this, (string)(AgentInterface::handshake)(string));
-        service->registerNonparametricMethod(this, (pid_t)(AgentInterface::getPeerPid)());
-        service->registerNonparametricMethod(this, (pid_t)(AgentInterface::getChildPid)());
-    }
-
-    ~AgentInterface()
-    {
-    }
-
     std::unique_ptr<rmi::Service> service;
 };
 
@@ -92,7 +93,11 @@ TEST(test_rmi, handshakeCorrect)
     if (pid == 0)
     {
         // child process
-        ASSERT_NO_THROW(AgentInterface::instance().run());
+        ASSERT_NO_THROW(
+        {
+            AgentPolicyService service;
+            service.run();
+        });
     }
     else if (pid > 0)
     {
@@ -101,12 +106,12 @@ TEST(test_rmi, handshakeCorrect)
         // wait some time to init service
         std::this_thread::sleep_for(std::chrono::milliseconds(100));
 
-        rmi::Client client(RMI_SERVICE_ADDRESS);
+        rmi::Client client(IAgentPolicy::RMI_ADDRESS);
         ASSERT_NO_THROW(client.connect());
-        ASSERT_EQ("SYN-ACC", client.methodCall<string>("AgentInterface::handshake", string("SYN")));
-        ASSERT_EQ("FAIL", client.methodCall<string>("AgentInterface::handshake", string("NOTSYN")));
-        pid_t peerPid = client.methodCall<pid_t>("AgentInterface::getPeerPid");
-        pid_t childPid = client.methodCall<pid_t>("AgentInterface::getChildPid");
+        ASSERT_EQ("SYN-ACC", client.methodCall<string>("AgentPolicyService::handshake", string("SYN")));
+        ASSERT_EQ("FAIL", client.methodCall<string>("AgentPolicyService::handshake", string("NOTSYN")));
+        pid_t peerPid = client.methodCall<pid_t>("AgentPolicyService::getPeerPid");
+        pid_t childPid = client.methodCall<pid_t>("AgentPolicyService::getServicePid");
         ASSERT_NO_THROW(client.disconnect());
 
         // kill child process
@@ -118,5 +123,60 @@ TEST(test_rmi, handshakeCorrect)
     else
     {
         FAIL();
-    }    
+    }
+}
+
+/**
+ * Test checks example agent_lib class AgentPolicyAdapter with a help of mock Service
+ * 1. Start service in child process
+ * 2. Connect client to service from parent process
+ * 3. Call enforcePolicy() method
+ * 4. Check correct return code
+ * 5. Disconnect client
+ * 6. Kill service process
+ */
+TEST(test_rmi, agentPolicyAdapterCorrect)
+{
+
+    pid_t pid = fork();
+
+    if (pid == 0)
+    {
+        // child process
+        ASSERT_NO_THROW(
+        {
+            AgentPolicyService service;
+            service.run();
+        });
+    }
+    else if (pid > 0)
+    {
+        // parent process
+
+        // wait some time to init service
+        std::this_thread::sleep_for(std::chrono::milliseconds(100));
+
+        std::string agentId = "AGENT_NUMBER_42";
+        std::string jsonData = "{key:\"value\"}";
+
+        int result = -1;
+        pid_t servicePid = -1;
+
+        ASSERT_NO_THROW(
+        {
+            AgentPolicyAdapter adapter;
+            result = adapter.enforcePolicy(agentId, jsonData);
+            servicePid = adapter.getServicePid();
+        });
+        ASSERT_EQ(0, result) << "enforcePolicy() error\n";
+
+        // kill child process
+        ASSERT_TRUE(servicePid > 0);
+        ASSERT_TRUE(servicePid < 65000);
+        kill(servicePid, SIGKILL);
+    }
+    else
+    {
+        FAIL();
+    }
 }