Add function to save a ACL into local SVR DB
authorJoonghwan Lee <jh05.lee@samsung.com>
Wed, 19 Oct 2016 05:41:18 +0000 (14:41 +0900)
committerRandeep Singh <randeep.s@samsung.com>
Fri, 28 Oct 2016 07:50:49 +0000 (07:50 +0000)
This patch adds an API to insert new ACL with duplication check into local SVR database and sample menu added.

Change-Id: I71ba806ae1b5d169bb3fa875836143565b8b1acb
Signed-off-by: Joonghwan Lee <jh05.lee@samsung.com>
Reviewed-on: https://gerrit.iotivity.org/gerrit/13427
Tested-by: jenkins-iotivity <jenkins-iotivity@opendaylight.org>
Reviewed-by: Chul Lee <chuls.lee@samsung.com>
Reviewed-by: Randeep Singh <randeep.s@samsung.com>
(cherry picked from commit fef21899b621739349050eb50fe904001013bb86)
Reviewed-on: https://gerrit.iotivity.org/gerrit/13803

13 files changed:
resource/csdk/octbstack_product_secured.def
resource/csdk/security/include/internal/aclresource.h
resource/csdk/security/provisioning/include/internal/secureresourceprovider.h
resource/csdk/security/provisioning/include/ocprovisioningmanager.h
resource/csdk/security/provisioning/sample/provisioningclient.c
resource/csdk/security/provisioning/src/cloud/aclid.c
resource/csdk/security/provisioning/src/ocprovisioningmanager.c
resource/csdk/security/provisioning/src/secureresourceprovider.c
resource/csdk/security/src/aclresource.c
resource/csdk/security/src/amsmgr.c
resource/csdk/security/src/dpairingresource.c
resource/include/OCProvisioningManager.h
resource/provisioning/src/OCProvisioningManager.cpp

index 2960f4f7a2dae0452fd95ecfc3e26b49be9376ea..d41423584f40930bd4cc5943e269fd85fcc02910 100644 (file)
@@ -23,6 +23,7 @@ OCGetDevInfoFromNetwork
 OCGetLinkedStatus
 OCInitPM
 OCProvisionACL
+OCSaveACL
 OCProvisionCredentials
 OCProvisionDirectPairing
 OCProvisionPairwiseDevices
index 5fd9d7cdec179208b5f478d89c798f6daf46b2d8..db09e4655aa9140fa4d6f81ab180f5db5bbbdd83 100644 (file)
@@ -111,24 +111,35 @@ void FreeRsrc(OicSecRsrc_t *rsrc);
  */
 OicSecAce_t* DuplicateACE(const OicSecAce_t* ace);
 
+
+/**
+ * This function check the duplication with pre-installed ACL and installs only new ACEs.
+ *
+ * @param acl  acl to install.
+ *
+ * @return ::OC_STACK_OK for Success, otherwise some error value
+ */
+OCStackResult InstallACL(const OicSecAcl_t* acl);
+
 /**
- * This function installs a new ACL.
+ * This function appends a new ACL.
  *
  * @param payload cbor value representing a new ACL.
  * @param size of the cbor payload.
  *
  * @return ::OC_STACK_OK for Success, otherwise some error value
  */
-OCStackResult InstallNewACL(const uint8_t* payload, const size_t size);
+OCStackResult AppendACL(const uint8_t* payload, const size_t size);
 
 /**
- * This function installs a new ACL.
+ * This function appends a new ACL.
  *
- * @param acl  new acl to install.
+ * @param acl  new acl to append.
  *
  * @return ::OC_STACK_OK for Success, otherwise some error value
  */
-OCStackResult InstallNewACL2(const OicSecAcl_t* acl);
+OCStackResult AppendACL2(const OicSecAcl_t* acl);
+
 /**
  * This function updates default ACE which is required for ownership transfer.
  * This function should be invoked after OTM is complete to prevent anonymous user access.
index fa9813d5c6ceaed5bf29ad986ff99c9c32659011..5e621bfcd958ff8284d63ab4ca5d5a59bf3e0994 100644 (file)
@@ -42,6 +42,14 @@ extern "C"
 OCStackResult SRPProvisionACL(void *ctx, const OCProvisionDev_t *selectedDeviceInfo,
                                         OicSecAcl_t *acl, OCProvisionResultCB resultCallback);
 
+/**
+ * API to save ACL which has several ACE into Acl of SVR.
+ *
+ * @param acl ACL to be saved in Acl of SVR.
+ * @return  OC_STACK_OK in case of success and other value otherwise.
+ */
+OCStackResult SRPSaveACL(const OicSecAcl_t *acl);
+
 /**
  * API to request CRED information to resource.
  *
index 9531f4ff33c61f152636fb69cc792840e15bb60e..939af6335edcfb487d934c063570e7d936121639 100755 (executable)
@@ -168,6 +168,14 @@ OCStackResult OCProvisionPairwiseDevices(void* ctx, OicSecCredType_t type, size_
 OCStackResult OCProvisionACL(void *ctx, const OCProvisionDev_t *selectedDeviceInfo, OicSecAcl_t *acl,\r
                              OCProvisionResultCB resultCallback);\r
 \r
+/**\r
+ * function to save ACL which has several ACE into Acl of SVR.\r
+ *\r
+ * @param acl ACL to be saved in Acl of SVR.\r
+ * @return  OC_STACK_OK in case of success and other value otherwise.\r
+ */\r
+OCStackResult OCSaveACL(const OicSecAcl_t* acl);\r
+\r
 /**\r
  * this function requests CRED information to resource.\r
  *\r
index ddc372d5c92c71a2852284319d0b0ce296a71ff3..b7c44c40ca7d56638c3b67644dde250a9a4e5fbb 100644 (file)
@@ -56,6 +56,7 @@ extern "C"
 #define _32_PROVIS_ACL_             32
 #define _33_PROVIS_DP_              33
 #define _34_CHECK_LINK_STATUS_      34
+#define _35_SAVE_ACL_               35
 #define _40_UNLINK_PAIR_DEVS_       40
 #define _50_REMOVE_SELEC_DEV_       50
 #define _51_REMOVE_DEV_WITH_UUID_   51
@@ -109,6 +110,7 @@ static void setDevProtocol(OCProvisionDev_t* dev_lst);
 #endif
 // function declaration(s) for calling them before implementing
 static OicSecAcl_t* createAcl(const int);
+static OicSecAcl_t* createSimpleAcl(const OicUuid_t uuid);
 static OicSecPdAcl_t* createPdAcl(const int);
 static OCProvisionDev_t* getDevInst(const OCProvisionDev_t*, const int);
 static int printDevList(const OCProvisionDev_t*);
@@ -873,6 +875,79 @@ CKLST_ERROR:
     return -1;
 }
 
+static int saveAcl(void)
+{
+    // create ACL to save into local SVR DB
+    OicSecAcl_t* acl = NULL;
+    OicUuid_t uuid =   {.id={0}};
+    char strUuid[64] = {0};
+
+    printf("[1] Use a test UUID [11111111-2222-3333-4444-555555555555]\n");
+    printf("[2] Use a user input\n");
+    int sel_num = 0;
+    for( ; ; )
+    {
+        printf("   > Select Number, for Subject UUID of new ACE: ");
+        for(int ret=0; 1!=ret; )
+        {
+            ret = scanf("%d", &sel_num);
+            for( ; 0x20<=getchar(); );  // for removing overflow garbages
+                                        // '0x20<=code' is character region
+        }
+        if(1 == sel_num)
+        {
+            OICStrcpy(strUuid, sizeof(strUuid), "11111111-2222-3333-4444-555555555555");
+            break;
+        }
+        else if(2 == sel_num)
+        {
+            printf("   > Input the UUID : ");
+            for(int ret=0; 1!=ret; )
+            {
+                ret = scanf("%64s", strUuid);
+                for( ; 0x20<=getchar(); );  // for removing overflow garbages
+                                        // '0x20<=code' is character region
+            }
+            break;
+        }
+        printf("     Entered Wrong Number. Please Enter Again\n");
+    }
+
+
+    printf("Selected Subject UUID : %s\n", strUuid);
+    OCStackResult rst = ConvertStrToUuid(strUuid, &uuid);
+    if(OC_STACK_OK != rst)
+    {
+        OIC_LOG_V(ERROR, TAG, "ConvertStrToUuid API error: %d", rst);
+        goto SVACL_ERROR;
+    }
+
+    acl = createSimpleAcl(uuid);
+    if(!acl)
+    {
+        OIC_LOG(ERROR, TAG, "createAcl error return");
+        goto SVACL_ERROR;
+    }
+
+    // call |OCSaveACL| API actually
+    rst = OCSaveACL(acl);
+    if(OC_STACK_OK != rst)
+    {
+        OIC_LOG_V(ERROR, TAG, "OCSaveACL API error: %d", rst);
+        goto SVACL_ERROR;
+    }
+    OCDeleteACLList(acl);  // after here |acl| points nothing
+
+    // display the ACL-provisioned result
+    printf("   > Saved Selected ACL\n");
+
+    return 0;
+
+SVACL_ERROR:
+    OCDeleteACLList(acl);  // after here |acl| points nothing
+    return -1;
+}
+
 static int getCred(void)
 {
     // check |own_list| for checking selected link status on PRVN DB
@@ -1604,6 +1679,63 @@ CRACL_ERROR:
     return NULL;
 }
 
+static OicSecAcl_t* createSimpleAcl(const OicUuid_t uuid)
+{
+    OIC_LOG(DEBUG, TAG, "createSimpleAcl IN");
+
+    // allocate memory for |acl| struct
+    OicSecAcl_t* acl = (OicSecAcl_t*) OICCalloc(1, sizeof(OicSecAcl_t));
+    if(!acl)
+    {
+        OIC_LOG(DEBUG, TAG, "OICCalloc error return");
+        return NULL;  // not need to 'goto' |ERROR| before allocating |acl|
+    }
+    OicSecAce_t* ace = (OicSecAce_t*) OICCalloc(1, sizeof(OicSecAce_t));
+    if(!ace)
+    {
+        OIC_LOG(DEBUG, TAG,  "OICCalloc error return");
+        return NULL;  // not need to 'goto' |ERROR| before allocating |acl|
+    }
+    LL_APPEND(acl->aces, ace);
+
+    memcpy(&ace->subjectuuid, &uuid, UUID_LENGTH);
+
+    OicSecRsrc_t* rsrc = (OicSecRsrc_t*)OICCalloc(1, sizeof(OicSecRsrc_t));
+    if(!rsrc)
+    {
+        OIC_LOG(DEBUG, TAG, "OICCalloc error return");
+        OCDeleteACLList(acl);
+        return NULL;
+    }
+
+    char href[] = "*";
+    size_t len = strlen(href)+1;  // '1' for null termination
+    rsrc->href = (char*) OICCalloc(len, sizeof(char));
+    if(!rsrc->href)
+    {
+        OIC_LOG(DEBUG, TAG,  "OICCalloc error return");
+        OCDeleteACLList(acl);
+        return NULL;
+    }
+    OICStrcpy(rsrc->href, len, href);
+
+    size_t arrLen = 1;
+    rsrc->typeLen = arrLen;
+    rsrc->types = (char**)OICCalloc(arrLen, sizeof(char*));
+    rsrc->interfaceLen = 1;
+    rsrc->interfaces = (char**)OICCalloc(arrLen, sizeof(char*));
+    rsrc->types[0] = OICStrdup("");   // ignore
+    rsrc->interfaces[0] = OICStrdup("oic.if.baseline");  // ignore
+
+    LL_APPEND(ace->resources, rsrc);
+
+    ace->permission = 31;   // R/W/U/D
+
+    OIC_LOG(DEBUG, TAG, "createSimpleAcl OUT");
+
+    return acl;
+}
+
 static OicSecPdAcl_t* createPdAcl(const int dev_num)
 {
     if(0>=dev_num || g_own_cnt<dev_num)
@@ -1888,7 +2020,8 @@ static void printMenu(void)
     printf("** 31. Provision Credentials for Pairwise Things\n");
     printf("** 32. Provision the Selected Access Control List(ACL)\n");
     printf("** 33. Provision Direct-Pairing Configuration\n");
-    printf("** 34. Check Linked Status of the Selected Device on PRVN DB\n\n");
+    printf("** 34. Check Linked Status of the Selected Device on PRVN DB\n");
+    printf("** 35. Save the Selected Access Control List(ACL) into local SVR DB\n\n");
 
     printf("** [D] UNLINK PAIRWISE THINGS\n");
     printf("** 40. Unlink Pairwise Things\n\n");
@@ -2035,6 +2168,12 @@ int main()
                 OIC_LOG(ERROR, TAG, "_34_CHECK_LINK_STATUS_: error");
             }
             break;
+        case _35_SAVE_ACL_:
+            if(saveAcl())
+            {
+                OIC_LOG(ERROR, TAG, "_35_SAVE_ACL_: error");
+            }
+            break;
         case _40_UNLINK_PAIR_DEVS_:
             if(unlinkPairwise())
             {
index 5589a695f9d54d8fccd607bf602f19a7ee6c53c7..d5cd116366977df7612ab53e40ec2d3df602b242 100644 (file)
@@ -193,7 +193,7 @@ static OCStackResult handleAclGetInfoResponse(void *ctx, void **data, OCClientRe
 
     printACL(acl);
 
-    result = InstallNewACL2(acl);
+    result = InstallACL(acl);
     if (result != OC_STACK_OK)
     {
         OIC_LOG(ERROR, TAG, "Can't update ACL resource");
index efc407283c313f8eb19414b7be6a8eb0b77c40e0..3a59db9fe3aad23cd41c10e5bc3928eba29095b0 100755 (executable)
@@ -271,6 +271,17 @@ OCStackResult OCProvisionACL(void* ctx, const OCProvisionDev_t *selectedDeviceIn
     return SRPProvisionACL(ctx, selectedDeviceInfo, acl, resultCallback);
 }
 
+/**
+ * function to save ACL which has several ACE into Acl of SVR.
+ *
+ * @param acl ACL to be saved in Acl of SVR.
+ * @return  OC_STACK_OK in case of success and other value otherwise.
+ */
+OCStackResult OCSaveACL(const OicSecAcl_t* acl)
+{
+    return SRPSaveACL(acl);
+}
+
 /**
  * this function requests CRED information to resource.
  *
index a71da0b21c780362f53c827435bb5a4b2b033fc0..44e3eb4e5ae18c5109cbc66ecad29285d600a6ef 100644 (file)
@@ -957,6 +957,17 @@ OCStackResult SRPProvisionACL(void *ctx, const OCProvisionDev_t *selectedDeviceI
     return OC_STACK_OK;
 }
 
+OCStackResult SRPSaveACL(const OicSecAcl_t *acl)
+{
+    OIC_LOG(DEBUG, TAG, "IN SRPSaveACL");
+    VERIFY_NON_NULL(TAG, acl, ERROR,  OC_STACK_INVALID_PARAM);
+
+    OCStackResult res =  InstallACL(acl);
+
+    OIC_LOG(DEBUG, TAG, "OUT SRPSaveACL");
+    return res;
+}
+
 /**
  * Internal Function to store results in result array during Direct-Pairing provisioning.
  */
index bf6127314bd9027a1ae1dffdce15058590fcad09..d774ffab2845a85ca66e60eb0a0640b2f186f452 100644 (file)
@@ -2441,7 +2441,7 @@ void printACL(const OicSecAcl_t* acl)
     }
 }
 
-OCStackResult InstallNewACL2(const OicSecAcl_t* acl)
+OCStackResult AppendACL2(const OicSecAcl_t* acl)
 {
     OCStackResult ret = OC_STACK_ERROR;
 
@@ -2480,12 +2480,83 @@ OCStackResult InstallNewACL2(const OicSecAcl_t* acl)
     return ret;
 }
 
-OCStackResult InstallNewACL(const uint8_t *cborPayload, const size_t size)
+OCStackResult AppendACL(const uint8_t *cborPayload, const size_t size)
 {
     // Convert CBOR format to ACL data. This will also validate the ACL data received.
     OicSecAcl_t* newAcl = CBORPayloadToAcl(cborPayload, size);
 
-    return InstallNewACL2(newAcl);
+    return AppendACL2(newAcl);
+}
+
+OCStackResult InstallACL(const OicSecAcl_t* acl)
+{
+    OCStackResult ret = OC_STACK_ERROR;
+
+    if (!acl)
+    {
+        return OC_STACK_INVALID_PARAM;
+    }
+
+    bool isNewAce = true;
+    OicSecAce_t* existAce = NULL;
+    OicSecAce_t* newAce = NULL;
+    OicSecAce_t* tempAce1 = NULL;
+    OicSecAce_t* tempAce2 = NULL;
+    OicSecAcl_t* newInstallAcl = NULL;
+
+    LL_FOREACH_SAFE(acl->aces, newAce, tempAce1)
+    {
+        isNewAce = true;
+        LL_FOREACH_SAFE(gAcl->aces, existAce, tempAce2)
+        {
+            if(IsSameACE(newAce, existAce))
+            {
+                OIC_LOG(DEBUG, TAG, "Duplicated ACE dectected.");
+                ret = OC_STACK_DUPLICATE_REQUEST;
+                isNewAce = false;
+            }
+        }
+        if(isNewAce)
+        {
+            // Append new ACE to existing ACL
+            OIC_LOG(DEBUG, TAG, "NEW ACE dectected.");
+
+            OicSecAce_t* insertAce = DuplicateACE(newAce);
+            if(insertAce)
+            {
+                OIC_LOG(DEBUG, TAG, "Appending new ACE..");
+
+                if (!newInstallAcl)
+                {
+                    newInstallAcl = (OicSecAcl_t *) OICCalloc(1, sizeof(OicSecAcl_t));
+                    if (NULL == newInstallAcl)
+                    {
+                        OIC_LOG(ERROR, TAG, "Failed to acllocate ACL");
+                        return OC_STACK_NO_MEMORY;
+                    }
+                }
+                LL_PREPEND(newInstallAcl->aces, insertAce);
+            }
+            else
+            {
+                OIC_LOG(ERROR, TAG, "Failed to duplicate ACE");
+                DeleteACLList(newInstallAcl);
+                return OC_STACK_ERROR;
+            }
+        }
+    }
+
+    if (newInstallAcl)
+    {
+        ret = AppendACL2(newInstallAcl);
+        if (OC_STACK_OK != ret)
+        {
+            OIC_LOG(ERROR, TAG, "Failed to append ACL");
+        }
+        OICFree(newInstallAcl);
+    }
+
+    return ret;
 }
 
 /**
index 90f8484e1094dc1bf69ea4611a851aa7ec517efb..3ddaac40e67d5f7b31101e9901209a536807931f 100644 (file)
@@ -300,7 +300,7 @@ static OCStackApplicationResult AmsMgrAclReqCallback(void *ctx, OCDoHandle handl
     {
         size_t size = ((OCSecurityPayload*)clientResponse->payload)->payloadSize;
         OCStackResult ret =
-                InstallNewACL(((OCSecurityPayload*)clientResponse->payload)->securityData, size);
+                AppendACL(((OCSecurityPayload*)clientResponse->payload)->securityData, size);
         VERIFY_SUCCESS(TAG, OC_STACK_OK == ret, ERROR);
 
         OIC_LOG_V(INFO, TAG, "%s : Calling checkPermission", __func__);
index e2e4dbbed104d8b50296f35dac7df8c61cbb26d5..d005645c41020703dd12d71aab2db4f00c01115b 100644 (file)
@@ -635,7 +635,7 @@ static OCEntityHandlerResult HandleDpairingPutRequest (const OCEntityHandlerRequ
             uint8_t *payload = NULL;
             if (OC_STACK_OK == AclToCBORPayload(acl, &payload, &size))
             {
-                InstallNewACL(payload, size);
+                AppendACL(payload, size);
                 OICFree(payload);
             }
             DeleteACLList(acl);
index f23e39b1c478276fe9f111904cfadb12f8b2f5c3..5fe59fed7bab0fa8054039a7ab049820aea29aeb 100755 (executable)
@@ -208,6 +208,14 @@ namespace OC
                     std::string uuid,
                     ResultCallBack resultCallback);
 
+            /**
+             * API to save ACL which has several ACE into Acl of SVR.
+             *
+             * @param acl ACL to be saved in Acl of SVR.
+             * @return  OC_STACK_OK in case of success and other value otherwise.
+             */
+            static OCStackResult saveACL(const OicSecAcl_t* acl);
+
 #if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
             /**
              * API to save Trust certificate chain into Cred of SVR.
index f2e714c87eb0995cf5194efd5df09523807ce7ec..02f305a283328eeda0471982093bc47f6a048cdb 100755 (executable)
@@ -308,6 +308,30 @@ namespace OC
         return result;
     }
 
+    OCStackResult OCSecure::saveACL(const OicSecAcl_t* acl)
+    {
+        if (!acl)
+        {
+            oclog() <<"ACL can't be null";
+            return OC_STACK_INVALID_PARAM;
+        }
+
+        OCStackResult result;
+        auto cLock = OCPlatform_impl::Instance().csdkLock().lock();
+
+        if (cLock)
+        {
+            std::lock_guard<std::recursive_mutex> lock(*cLock);
+            result = OCSaveACL(const_cast<OicSecAcl_t*>(acl));
+        }
+        else
+        {
+            oclog() <<"Mutex not found";
+            result = OC_STACK_ERROR;
+        }
+        return result;
+    }
+
 #if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
     OCStackResult OCSecure::saveTrustCertChain(uint8_t *trustCertChain, size_t chainSize,
                                         OicEncodingType_t encodingType, uint16_t *credId)