Implementation of API for user management
[platform/core/security/security-manager.git] / src / client / client-security-manager.cpp
index 14fbcbf..f9e3484 100644 (file)
 #include <client-common.h>
 #include <protocols.h>
 #include <smack-common.h>
+#include <service_impl.h>
+#include <file-lock.h>
 
 #include <security-manager.h>
 
+/**
+ * Mapping of lib_retcode error codes to theirs strings equivalents
+ */
+static std::map<enum lib_retcode, std::string> lib_retcode_string_map = {
+    {SECURITY_MANAGER_SUCCESS, "Success"},
+    {SECURITY_MANAGER_ERROR_UNKNOWN, "Unknown error"},
+    {SECURITY_MANAGER_ERROR_INPUT_PARAM, "Invalid function parameter was given"},
+    {SECURITY_MANAGER_ERROR_MEMORY, "Memory allocation error"},
+    {SECURITY_MANAGER_ERROR_REQ_NOT_COMPLETE, "Incomplete data in application request"},
+    {SECURITY_MANAGER_ERROR_AUTHENTICATION_FAILED, "User does not have sufficient "
+                                                   "rigths to perform an operation"}
+};
 
+SECURITY_MANAGER_API
+const char *security_manager_strerror(enum lib_retcode rc)
+{
+    try {
+        return lib_retcode_string_map.at(rc).c_str();
+    } catch (const std::out_of_range &e) {
+        return "Unknown error code";
+    }
+}
 
 SECURITY_MANAGER_API
 int security_manager_app_inst_req_new(app_inst_req **pp_req)
@@ -60,7 +83,7 @@ int security_manager_app_inst_req_new(app_inst_req **pp_req)
     } catch (std::bad_alloc& ex) {
         return SECURITY_MANAGER_ERROR_MEMORY;
     }
-    (*pp_req)->uid = 0;
+    (*pp_req)->uid = geteuid();
 
     return SECURITY_MANAGER_SUCCESS;
 }
@@ -131,7 +154,6 @@ SECURITY_MANAGER_API
 int security_manager_app_install(const app_inst_req *p_req)
 {
     using namespace SecurityManager;
-    MessageBuffer send, recv;
 
     return try_catch([&] {
         //checking parameters
@@ -140,28 +162,46 @@ int security_manager_app_install(const app_inst_req *p_req)
         if (p_req->appId.empty() || p_req->pkgId.empty())
             return SECURITY_MANAGER_ERROR_REQ_NOT_COMPLETE;
 
-        //put data into buffer
-        Serialization::Serialize(send, (int)SecurityModuleCall::APP_INSTALL);
-        Serialization::Serialize(send, p_req->appId);
-        Serialization::Serialize(send, p_req->pkgId);
-        Serialization::Serialize(send, p_req->privileges);
-        Serialization::Serialize(send, p_req->appPaths);
-        Serialization::Serialize(send, p_req->uid);
+        bool offlineMode;
+        int retval;
 
-        //send buffer to server
-        int retval = sendToServer(SERVICE_SOCKET, send.Pop(), recv);
-        if (retval != SECURITY_MANAGER_API_SUCCESS) {
-            LogError("Error in sendToServer. Error code: " << retval);
-            return SECURITY_MANAGER_ERROR_UNKNOWN;
+        try {
+            SecurityManager::FileLocker serviceLock(SecurityManager::SERVICE_LOCK_FILE);
+            if ((offlineMode = serviceLock.Locked())) {
+                LogInfo("Working in offline mode.");
+                retval = SecurityManager::ServiceImpl::appInstall(*p_req, geteuid());
+            }
+        } catch (const SecurityManager::FileLocker::Exception::Base &e) {
+            offlineMode = false;
         }
+        if (!offlineMode) {
+            MessageBuffer send, recv;
+
+            //put data into buffer
+            Serialization::Serialize(send, (int)SecurityModuleCall::APP_INSTALL);
+            Serialization::Serialize(send, p_req->appId);
+            Serialization::Serialize(send, p_req->pkgId);
+            Serialization::Serialize(send, p_req->privileges);
+            Serialization::Serialize(send, p_req->appPaths);
+            Serialization::Serialize(send, p_req->uid);
+
+            //send buffer to server
+            retval = sendToServer(SERVICE_SOCKET, send.Pop(), recv);
+            if (retval != SECURITY_MANAGER_API_SUCCESS) {
+                LogError("Error in sendToServer. Error code: " << retval);
+                return SECURITY_MANAGER_ERROR_UNKNOWN;
+            }
 
-        //receive response from server
-        Deserialization::Deserialize(recv, retval);
+            //receive response from server
+            Deserialization::Deserialize(recv, retval);
+        }
         switch(retval) {
             case SECURITY_MANAGER_API_SUCCESS:
                 return SECURITY_MANAGER_SUCCESS;
             case SECURITY_MANAGER_API_ERROR_AUTHENTICATION_FAILED:
                 return SECURITY_MANAGER_ERROR_AUTHENTICATION_FAILED;
+            case SECURITY_MANAGER_API_ERROR_INPUT_PARAM:
+                return SECURITY_MANAGER_ERROR_INPUT_PARAM;
             default:
                 return SECURITY_MANAGER_ERROR_UNKNOWN;
         }
@@ -477,3 +517,114 @@ int security_manager_prepare_app(const char *app_id)
     ret = security_manager_drop_process_privileges();
     return ret;
 }
+
+SECURITY_MANAGER_API
+int security_manager_user_req_new(user_req **pp_req)
+{
+    if (!pp_req)
+        return SECURITY_MANAGER_ERROR_INPUT_PARAM;
+    try {
+        *pp_req = new user_req;
+    } catch (std::bad_alloc& ex) {
+        return SECURITY_MANAGER_ERROR_MEMORY;
+    }
+    return SECURITY_MANAGER_SUCCESS;
+}
+
+SECURITY_MANAGER_API
+void security_manager_user_req_free(user_req *p_req)
+{
+    delete p_req;
+}
+
+SECURITY_MANAGER_API
+int security_manager_user_req_set_uid(user_req *p_req, uid_t uid)
+{
+    if (!p_req)
+        return SECURITY_MANAGER_ERROR_INPUT_PARAM;
+
+    p_req->uid = uid;
+
+    return SECURITY_MANAGER_SUCCESS;
+}
+
+SECURITY_MANAGER_API
+int security_manager_user_req_set_user_type(user_req *p_req, security_manager_user_type utype)
+{
+    if (!p_req)
+        return SECURITY_MANAGER_ERROR_INPUT_PARAM;
+
+    p_req->utype = static_cast<int>(utype);
+
+    return SECURITY_MANAGER_SUCCESS;
+}
+
+SECURITY_MANAGER_API
+int security_manager_user_add(const user_req *p_req)
+{
+    using namespace SecurityManager;
+    MessageBuffer send, recv;
+    if (!p_req)
+        return SECURITY_MANAGER_ERROR_INPUT_PARAM;
+    return try_catch([&] {
+
+        //put data into buffer
+        Serialization::Serialize(send, static_cast<int>(SecurityModuleCall::USER_ADD));
+
+        Serialization::Serialize(send, p_req->uid);
+        Serialization::Serialize(send, p_req->utype);
+
+        //send buffer to server
+        int retval = sendToServer(SERVICE_SOCKET, send.Pop(), recv);
+        if (retval != SECURITY_MANAGER_API_SUCCESS) {
+            LogError("Error in sendToServer. Error code: " << retval);
+            return SECURITY_MANAGER_ERROR_UNKNOWN;
+        }
+
+        //receive response from server
+        Deserialization::Deserialize(recv, retval);
+        switch(retval) {
+        case SECURITY_MANAGER_API_SUCCESS:
+            return SECURITY_MANAGER_SUCCESS;
+        case SECURITY_MANAGER_API_ERROR_AUTHENTICATION_FAILED:
+            return SECURITY_MANAGER_ERROR_AUTHENTICATION_FAILED;
+        default:
+            return SECURITY_MANAGER_ERROR_UNKNOWN;
+        }
+    });
+}
+
+SECURITY_MANAGER_API
+int security_manager_user_delete(const user_req *p_req)
+{
+    using namespace SecurityManager;
+    MessageBuffer send, recv;
+    if (!p_req)
+        return SECURITY_MANAGER_ERROR_INPUT_PARAM;
+    return try_catch([&] {
+
+        //put data into buffer
+        Serialization::Serialize(send, static_cast<int>(SecurityModuleCall::USER_DELETE));
+
+        Serialization::Serialize(send, p_req->uid);
+
+
+        //send buffer to server
+        int retval = sendToServer(SERVICE_SOCKET, send.Pop(), recv);
+        if (retval != SECURITY_MANAGER_API_SUCCESS) {
+            LogError("Error in sendToServer. Error code: " << retval);
+            return SECURITY_MANAGER_ERROR_UNKNOWN;
+        }
+
+        //receive response from server
+        Deserialization::Deserialize(recv, retval);
+        switch(retval) {
+        case SECURITY_MANAGER_API_SUCCESS:
+            return SECURITY_MANAGER_SUCCESS;
+        case SECURITY_MANAGER_API_ERROR_AUTHENTICATION_FAILED:
+            return SECURITY_MANAGER_ERROR_AUTHENTICATION_FAILED;
+        default:
+            return SECURITY_MANAGER_ERROR_UNKNOWN;
+        }
+    });
+}