1. Apply the list mechanism to manage the OTMContext.
-> It replaces the global variables of OTMContext.
2. Add the OCDoHandle member into OTMContext.
-> In case of OTM process stopped before OTM process complete,
unnecessary retransmission can be occur
due to request is performed just before the OTM process stops.
So we need to cancel this request to prevent retransmission.
OCDoHandle will be used at this time.
3. Add the device status of PDM to prevent duplicate OTM.
-> Added PDM_DEVICE_INIT to prevent deplicate OTM.
If device status is PDM_DEVICE_INIT, PT will skip OTM process of this device.
Change-Id: I74e200aa88a0c5016c065a518b75614bf4a3a7a8
Signed-off-by: Chul Lee <chuls.lee@samsung.com>
Reviewed-on: https://gerrit.iotivity.org/gerrit/13857
Tested-by: jenkins-iotivity <jenkins-iotivity@opendaylight.org>
Reviewed-by: Kevin Kane <kkane@microsoft.com>
Reviewed-by: Randeep Singh <randeep.s@samsung.com>
provisioning_src = [
'src/pmutility.c',
'src/credentialgenerator.c',
+ 'src/otmcontextlist.c',
'src/ownershiptransfermanager.c',
'src/secureresourceprovider.c',
'src/ocprovisioningmanager.c',
--- /dev/null
+/* *****************************************************************
+ *
+ * Copyright 2016 Samsung Electronics All Rights Reserved.
+ *
+ *
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ * *****************************************************************/
+
+#ifndef _OTM_CONTEXT_LIST_H_
+#define _OTM_CONTEXT_LIST_H_
+
+#include "pmtypes.h"
+#include "ocstack.h"
+#include "octypes.h"
+#include "securevirtualresourcetypes.h"
+#include "ownershiptransfermanager.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif // __cplusplus
+
+typedef struct OTMContextItem {
+ OTMContext_t* otmCtx;
+ OCDevAddr endpoint;
+ struct OTMContextItem* next;
+}OTMContextItem_t;
+
+/**
+ * API to remove OTMContext from OTMContext list.
+ *
+ * @param[in] addr IP address of peer
+ * @param[in] port secure port number of peer
+ */
+void RemoveOTMContext(const char* addr, uint16_t port);
+
+/**
+ * API to add OTMContext to OTMContext list.
+ * If same OTMContext exist, will be ignored.
+ *
+ * @param[in] ctx new OTMContext
+ * @param[in] addr IP address of peer
+ * @param[in] port secure port number of peer
+ *
+ * @return OC_STACK_OK in case of success and other value otherwise.
+ */
+OCStackResult AddOTMContext(OTMContext_t* ctx, const char* addr, uint16_t port);
+
+/**
+ * API to read OTMContext from OTMContext list
+ *
+ * @param[in] addr IP address of peer
+ * @param[in] port secure port number of peer
+ *
+ * @return OTMContext in case of context found, otherwise NULL.
+ */
+const OTMContext_t* GetOTMContext(const char* addr, uint16_t port);
+
+#ifdef __cplusplus
+}
+#endif //__cplusplus
+
+#endif //_OTM_CONTEXT_LIST_H_
\ No newline at end of file
*/\r
typedef OCStackResult (*OTMLoadSecret)(OTMContext_t* otmCtx);\r
\r
-\r
/*\r
* Callback for create secure channel using secret inputed from OTMLoadSecret callback\r
*/\r
OCProvisionResult_t* ctxResultArray; /**< Result array having result of all device. */\r
size_t ctxResultArraySize; /**< No of elements in result array. */\r
bool ctxHasError; /**< Does OT process have any error. */\r
+ OCDoHandle ocDoHandle; /** <A handle for latest request message*/\r
OTMCallbackData_t otmCallback; /**< OTM callbacks to perform the OT/MOT. **/\r
int attemptCnt;\r
};\r
extern "C" {
#endif
+typedef enum PdmDeviceState {
+ PDM_DEVICE_ACTIVE = 0,
+ PDM_DEVICE_STALE = 1,
+ PDM_DEVICE_INIT = 2,
+ PDM_DEVICE_UNKNOWN = 99
+}PdmDeviceState_t;
/**
* This method is used by provisioning manager to open provisioning database.
OCStackResult PDMInit(const char* dbPath);
/**
- * This method is used by provisioning manager to check whether device is stale or not with PDM.
+ * This method is used by provisioning manager to check device status.
*
* @param[in] uuid information about the target device's uuid.
- * @param[out] result true in case device is stale.
+ * @param[out] result device status.
*
* @return OC_STACK_OK in case of success and other value otherwise.
*/
-OCStackResult PDMIsDeviceStale(const OicUuid_t *uuid, bool *result);
+OCStackResult PDMGetDeviceState(const OicUuid_t* uuid, PdmDeviceState_t* result);
+
+/**
+ * This method is used by provisioning manager to update device status.
+ *
+ * @param[in] uuid id of device.
+ * @param[in] state device state. (ref. PdmDeviceState_t)
+ *
+ * @return OC_STACK_OK in case of success and other value otherwise.
+ */
+OCStackResult PDMSetDeviceState(const OicUuid_t* uuid, PdmDeviceState_t state);
/**
* This method is used by provisioning manager to check duplication of device's Device ID with
OCStackResult PDMSetLinkStale(const OicUuid_t* uuidOfDevice1, const OicUuid_t* uuidOfDevice2);
/**
- * This method is used by provisioning manager to update device status as stale.
- *
- * @param[in] uuidOfDevice id of stale device.
- *
- * @return OC_STACK_OK in case of success and other value otherwise.
- */
-OCStackResult PDMSetDeviceStale(const OicUuid_t* uuidOfDevice);
-
-/**
* This method is used by provisioning manager to get stale devices.
*
* @note in case of sqllite, the caller should set NULL for parameters.
#include "oxmjustworks.h"
#include "oxmpreconfpin.h"
#include "oxmrandompin.h"
+#include "otmcontextlist.h"
#define TAG "MULTIPLE_OTM"
**********************************************************************/
/**
- * Structure to carry SuperOwner's multiple ownership transfer API data to callback.
- */
-typedef struct MOTContext MOTContext_t;
-struct MOTContext
-{
- void *ctx; /**< Pointer to user context.**/
- const OCProvisionDev_t *deviceInfo; /**< Pointer to OCProvisionDev_t.**/
- OCProvisionResultCB resultCallback; /**< Pointer to result callback.**/
- OCProvisionResult_t *resArr; /**< Result array.**/
- int numOfResults; /**< Number of results in result array.**/
- bool hasError; /**< Does MOT API have any error.. **/
-};
-
-/**
* Callback handler of security resource's POST request.
*
* @param[in] ctx ctx value passed to callback from calling function.
{
OIC_LOG_V(INFO, TAG, "Inside MOTUpdateMomCB.");
(void)UNUSED;
- MOTContext_t *motCtx = (MOTContext_t*)ctx;
+ OTMContext_t *motCtx = (OTMContext_t*)ctx;
VERIFY_NON_NULL(TAG, motCtx, ERROR);
- VERIFY_NON_NULL(TAG, motCtx->resultCallback, ERROR);
- VERIFY_NON_NULL(TAG, motCtx->resArr, ERROR);
+ VERIFY_NON_NULL(TAG, motCtx->ctxResultCallback, ERROR);
+ VERIFY_NON_NULL(TAG, motCtx->ctxResultArray, ERROR);
if(clientResponse)
{
- memcpy(motCtx->resArr[0].deviceId.id, motCtx->deviceInfo->doxm->deviceID.id, sizeof(OicUuid_t));
- motCtx->resArr[0].res = clientResponse->result;
+ memcpy(motCtx->ctxResultArray[0].deviceId.id,
+ motCtx->selectedDeviceInfo->doxm->deviceID.id,
+ sizeof(OicUuid_t));
+ motCtx->ctxResultArray[0].res = clientResponse->result;
if(OC_STACK_RESOURCE_CHANGED == clientResponse->result)
{
- motCtx->hasError = false;
+ motCtx->ctxHasError = false;
}
else
{
- motCtx->hasError = true;
+ motCtx->ctxHasError = true;
}
}
else
{
OIC_LOG_V(ERROR, TAG, "SRPGetACLResourceCB received Null clientResponse");
- motCtx->resArr[0].res = OC_STACK_ERROR;
- motCtx->hasError = true;
+ motCtx->ctxResultArray[0].res = OC_STACK_ERROR;
+ motCtx->ctxHasError = true;
}
- motCtx->resultCallback(motCtx->ctx, motCtx->numOfResults, motCtx->resArr, motCtx->hasError);
+ motCtx->ctxResultCallback(motCtx->userCtx, motCtx->ctxResultArraySize,
+ motCtx->ctxResultArray, motCtx->ctxHasError);
exit:
if(motCtx)
{
- OICFree(motCtx->resArr);
+ OICFree(motCtx->ctxResultArray);
OICFree(motCtx);
}
return OC_STACK_DELETE_TRANSACTION;
{
OCStackResult postMomRes = OC_STACK_ERROR;
OCSecurityPayload* secPayload = NULL;
- MOTContext_t *motCtx = NULL;
+ OTMContext_t *motCtx = NULL;
bool freeFlag = true;
OIC_LOG(DEBUG, TAG, "IN MOTSendPostDoxm");
OIC_LOG_V(DEBUG, TAG, "Query=%s", query);
//Create the MOT Context to handle the response message
- motCtx = (MOTContext_t*)OICCalloc(1, sizeof(MOTContext_t));
+ motCtx = (OTMContext_t*)OICCalloc(1, sizeof(OTMContext_t));
VERIFY_NON_NULL(TAG, motCtx, ERROR);
- motCtx->deviceInfo = targetDeviceInfo;
- motCtx->resultCallback = resultCallback;
- motCtx->numOfResults=1;
- motCtx->hasError = false;
- motCtx->ctx = ctx;
- motCtx->resArr = (OCProvisionResult_t*)OICCalloc(1, sizeof(OCProvisionResult_t));
- VERIFY_NON_NULL(TAG, motCtx->resArr, ERROR);
+ motCtx->selectedDeviceInfo = targetDeviceInfo;
+ motCtx->ctxResultCallback = resultCallback;
+ motCtx->ctxResultArraySize = 1;
+ motCtx->ctxHasError = false;
+ motCtx->userCtx = ctx;
+ motCtx->ctxResultArray= (OCProvisionResult_t*)OICCalloc(1, sizeof(OCProvisionResult_t));
+ VERIFY_NON_NULL(TAG, motCtx->ctxResultArray, ERROR);
//Send POST request
OCCallbackData cbData = {.context=NULL, .cb=NULL, .cd=NULL};
//If POST request successfully sent, motCtx will be cleaned from response handler.
if(freeFlag && motCtx)
{
- OICFree(motCtx->resArr);
+ OICFree(motCtx->ctxResultArray);
OICFree(motCtx);
}
OCStackResult postCredRes = OC_STACK_INVALID_CALLBACK;
bool freeFlag = true;
OCSecurityPayload* secPayload = NULL;
- MOTContext_t *motCtx = NULL;
+ OTMContext_t *motCtx = NULL;
OicSecCred_t* pinCred = NULL;
OIC_LOG(DEBUG, TAG, "IN MOTProvisionPreconfigPIN");
OIC_LOG_V(DEBUG, TAG, "Query=%s", query);
//Create the MOT Context to handle the response message
- motCtx = (MOTContext_t*)OICCalloc(1, sizeof(MOTContext_t));
+ motCtx = (OTMContext_t*)OICCalloc(1, sizeof(OTMContext_t));
VERIFY_NON_NULL(TAG, motCtx, ERROR);
- motCtx->deviceInfo = targetDeviceInfo;
- motCtx->resultCallback = resultCallback;
- motCtx->numOfResults=1;
- motCtx->hasError = false;
- motCtx->ctx = ctx;
- motCtx->resArr = (OCProvisionResult_t*)OICCalloc(1, sizeof(OCProvisionResult_t));
- VERIFY_NON_NULL(TAG, motCtx->resArr, ERROR);
+ motCtx->selectedDeviceInfo= targetDeviceInfo;
+ motCtx->ctxResultCallback = resultCallback;
+ motCtx->ctxResultArraySize =1;
+ motCtx->ctxHasError = false;
+ motCtx->userCtx = ctx;
+ motCtx->ctxResultArray = (OCProvisionResult_t*)OICCalloc(1, sizeof(OCProvisionResult_t));
+ VERIFY_NON_NULL(TAG, motCtx->ctxResultArray, ERROR);
//Send POST request
OCCallbackData cbData = {.context=NULL, .cb=NULL, .cd=NULL};
//If POST request successfully sent, motCtx will be cleaned from response handler.
if(freeFlag && motCtx)
{
- OICFree(motCtx->resArr);
+ OICFree(motCtx->ctxResultArray);
OICFree(motCtx);
}
if(pinCred)
static void SetMOTResult(OTMContext_t* motCtx, const OCStackResult res)
{
OIC_LOG_V(DEBUG, TAG, "IN SetMOTResult : %d ", res);
-
VERIFY_NON_NULL(TAG, motCtx, ERROR);
if(motCtx->selectedDeviceInfo)
SetUuidForPinBasedOxm(&emptyUuid);
}
+ OCStackResult pdmRetVal = PDMSetDeviceState(&motCtx->selectedDeviceInfo->doxm->deviceID,
+ PDM_DEVICE_ACTIVE);
+ if (OC_STACK_OK != pdmRetVal)
+ {
+ OIC_LOG_V(ERROR, TAG, "Failed to add device information into PDM_DB : %d", res);
+ }
+
for(size_t i = 0; i < motCtx->ctxResultArraySize; i++)
{
if(memcmp(motCtx->selectedDeviceInfo->doxm->deviceID.id,
}
}
- g_MotCtx = NULL;
+ //Remove the current OTM Context from OTM queue
+ RemoveOTMContext(motCtx->selectedDeviceInfo->endpoint.addr,
+ motCtx->selectedDeviceInfo->securePort);
+
+ //If there is a request being performed, cancel it to prevent retransmission.
+ if(motCtx->ocDoHandle)
+ {
+ OCCancel(motCtx->ocDoHandle, OC_HIGH_QOS, NULL, 0);
+ motCtx->ocDoHandle = NULL;
+ }
//If all request is completed, invoke the user callback.
if(IsComplete(motCtx))
OIC_LOG(DEBUG, TAG, "IN SubOwnerCredentialHandler");
(void)UNUSED;
- OCStackResult res = OC_STACK_ERROR;
OTMContext_t* motCtx = (OTMContext_t*)ctx;
if(OC_STACK_RESOURCE_CHANGED == clientResponse->result)
return OC_STACK_DELETE_TRANSACTION;
}
- res = PDMAddDevice(&motCtx->selectedDeviceInfo->doxm->deviceID);
- if (OC_STACK_OK == res)
- {
- OIC_LOG_V(INFO, TAG, "Add device's UUID in PDM_DB");
- }
- else
- {
- OIC_LOG(ERROR, TAG, "MOT is complete but adding information to DB is failed.");
- }
-
- SetMOTResult(motCtx, res);
+ SetMOTResult(motCtx, OC_STACK_OK);
}
}
else
{
- res = clientResponse->result;
- OIC_LOG_V(ERROR, TAG, "SubOwnerCredentialHandler : Unexpected result %d", res);
- SetMOTResult(motCtx, res);
+ OIC_LOG_V(ERROR, TAG, "SubOwnerCredentialHandler : Unexpected result %d",
+ clientResponse->result);
+ SetMOTResult(motCtx, clientResponse->result);
}
OIC_LOG(DEBUG, TAG, "OUT SubOwnerCredentialHandler");
*/
static void MOTDtlsHandshakeCB(const CAEndpoint_t *endpoint, const CAErrorInfo_t *info)
{
- if(NULL != g_MotCtx && NULL != g_MotCtx->selectedDeviceInfo &&
- NULL != endpoint && NULL != info)
+ OIC_LOG(INFO, TAG, "IN MOTDtlsHandshakeCB");
+
+ if(NULL != endpoint && NULL != info)
{
OIC_LOG_V(INFO, TAG, "Received status from remote device(%s:%d) : %d",
endpoint->addr, endpoint->port, info->result);
- OicSecDoxm_t* newDevDoxm = g_MotCtx->selectedDeviceInfo->doxm;
-
- if(NULL != newDevDoxm)
+ OTMContext_t* motCtx = GetOTMContext(endpoint->addr, endpoint->port);
+ if(motCtx)
{
- OicUuid_t emptyUuid = {.id={0}};
+ OicSecDoxm_t* newDevDoxm = motCtx->selectedDeviceInfo->doxm;
- //Make sure the address matches.
- if(strncmp(g_MotCtx->selectedDeviceInfo->endpoint.addr,
- endpoint->addr,
- sizeof(endpoint->addr)) == 0 &&
- g_MotCtx->selectedDeviceInfo->securePort == endpoint->port)
+ if(NULL != newDevDoxm)
{
- OCStackResult res = OC_STACK_ERROR;
+ OicUuid_t emptyUuid = {.id={0}};
- //If temporal secure sesstion established successfully
- if(CA_STATUS_OK == info->result)
+ //Make sure the address matches.
+ if(strncmp(motCtx->selectedDeviceInfo->endpoint.addr,
+ endpoint->addr,
+ sizeof(endpoint->addr)) == 0 &&
+ motCtx->selectedDeviceInfo->securePort == endpoint->port)
{
- //Delete previous credential such as preconfigured-pin
- RemoveCredential(&(g_MotCtx->selectedDeviceInfo->doxm->deviceID));
+ OCStackResult res = OC_STACK_ERROR;
- res = SaveSubOwnerPSK(g_MotCtx->selectedDeviceInfo);
- if(OC_STACK_OK == res)
+ //If temporal secure sesstion established successfully
+ if(CA_STATUS_OK == info->result)
{
- //POST sub owner credential to new device.
- res = PostSubOwnerCredential(g_MotCtx);
- if(OC_STACK_OK != res)
+ //Delete previous credential such as preconfigured-pin
+ RemoveCredential(&(motCtx->selectedDeviceInfo->doxm->deviceID));
+
+ res = SaveSubOwnerPSK(motCtx->selectedDeviceInfo);
+ if(OC_STACK_OK == res)
{
- OIC_LOG(ERROR, TAG,
- "Failed to send POST request for SubOwner Credential");
- SetMOTResult(g_MotCtx, res);
+ //POST sub owner credential to new device.
+ res = PostSubOwnerCredential(motCtx);
+ if(OC_STACK_OK != res)
+ {
+ OIC_LOG(ERROR, TAG,
+ "Failed to send POST request for SubOwner Credential");
+ SetMOTResult(motCtx, res);
+ }
+ }
+ else
+ {
+ OIC_LOG(ERROR, TAG, "Failed to save the SubOwner PSK.");
+ SetMOTResult(motCtx, res);
}
}
- else
- {
- OIC_LOG(ERROR, TAG, "Failed to save the SubOwner PSK.");
- SetMOTResult(g_MotCtx, res);
- }
- }
- //In case of authentication failure
- else if(CA_DTLS_AUTHENTICATION_FAILURE == info->result)
- {
- //in case of error from wrong PIN, re-start the ownership transfer
- if(OIC_RANDOM_DEVICE_PIN == newDevDoxm->oxmSel)
+ //In case of authentication failure
+ else if(CA_DTLS_AUTHENTICATION_FAILURE == info->result)
{
- OIC_LOG(ERROR, TAG, "The PIN number may incorrect.");
+ //in case of error from wrong PIN, re-start the ownership transfer
+ if(OIC_RANDOM_DEVICE_PIN == newDevDoxm->oxmSel)
+ {
+ OIC_LOG(ERROR, TAG, "The PIN number may incorrect.");
- g_MotCtx->attemptCnt++;
+ motCtx->attemptCnt++;
- if(WRONG_PIN_MAX_ATTEMP > g_MotCtx->attemptCnt)
- {
- res = StartMultipleOwnershipTransfer(g_MotCtx, g_MotCtx->selectedDeviceInfo);
- if(OC_STACK_OK != res)
+ if(WRONG_PIN_MAX_ATTEMP > motCtx->attemptCnt)
{
- SetMOTResult(g_MotCtx, res);
- OIC_LOG(ERROR, TAG, "Failed to Re-StartOwnershipTransfer");
+ res = StartMultipleOwnershipTransfer(motCtx, motCtx->selectedDeviceInfo);
+ if(OC_STACK_OK != res)
+ {
+ SetMOTResult(motCtx, res);
+ OIC_LOG(ERROR, TAG, "Failed to Re-StartOwnershipTransfer");
+ }
+ }
+ else
+ {
+ OIC_LOG(ERROR, TAG, "User has exceeded the number of authentication attempts.");
+ SetMOTResult(motCtx, OC_STACK_AUTHENTICATION_FAILURE);
}
}
else
{
- OIC_LOG(ERROR, TAG, "User has exceeded the number of authentication attempts.");
- SetMOTResult(g_MotCtx, OC_STACK_AUTHENTICATION_FAILURE);
+ OIC_LOG(ERROR, TAG, "Failed to establish DTLS session.");
+ SetMOTResult(motCtx, OC_STACK_AUTHENTICATION_FAILURE);
}
}
- else
- {
- OIC_LOG(ERROR, TAG, "Failed to establish DTLS session.");
- SetMOTResult(g_MotCtx, OC_STACK_AUTHENTICATION_FAILURE);
- }
}
}
}
+ else
+ {
+ OIC_LOG_V(ERROR, TAG, "Can not find the [%s:%d]'s OTMContext for MOT", endpoint->addr, endpoint->port);
+ }
}
+
+ OIC_LOG(INFO, TAG, "OUT MOTDtlsHandshakeCB");
}
static OCStackResult StartMultipleOwnershipTransfer(OTMContext_t* motCtx,
OIC_LOG(INFO, TAG, "IN StartMultipleOwnershipTransfer");
OCStackResult res = OC_STACK_INVALID_PARAM;
+ VERIFY_NON_NULL(TAG, motCtx, ERROR);
VERIFY_NON_NULL(TAG, selectedDevice, ERROR);
VERIFY_NON_NULL(TAG, selectedDevice->doxm, ERROR);
-
motCtx->selectedDeviceInfo = selectedDevice;
+ //Checking duplication of Device ID.
+ char* strUuid = NULL;
+ PdmDeviceState_t deviceState = PDM_DEVICE_UNKNOWN;
+ res = PDMGetDeviceState(&selectedDevice->doxm->deviceID, &deviceState);
+ VERIFY_SUCCESS(TAG, OC_STACK_OK == res, ERROR);
+
+ res = ConvertUuidToStr(&selectedDevice->doxm->deviceID, &strUuid);
+ if(OC_STACK_OK != res)
+ {
+ OIC_LOG(ERROR, TAG, "Failed to convert UUID to str");
+ SetMOTResult(motCtx, res);
+ return res;
+ }
+
+ if(PDM_DEVICE_STALE == deviceState)
+ {
+ OIC_LOG_V(WARNING, TAG, "Detected duplicated UUID in stale status, "
+ "[%s] will be removed from PDM", strUuid);
+
+ res = PDMDeleteDevice(&selectedDevice->doxm->deviceID);
+ if(OC_STACK_OK != res)
+ {
+ OIC_LOG(ERROR, TAG, "Internal error in PDMDeleteDevice");
+ OICFree(strUuid);
+ SetMOTResult(motCtx, res);
+ }
+ }
+ else if(PDM_DEVICE_INIT == deviceState)
+ {
+ OIC_LOG_V(ERROR, TAG, "[%s]'s multiple owner transfer process is already started.", strUuid);
+ OICFree(strUuid);
+ SetMOTResult(motCtx, OC_STACK_DUPLICATE_REQUEST);
+ return OC_STACK_OK;
+ }
+
+ res = PDMAddDevice(&selectedDevice->doxm->deviceID);
+ if (OC_STACK_OK != res)
+ {
+ OIC_LOG_V(INFO, TAG, "Error in PDMAddDevice for [%s]", strUuid);
+ OICFree(strUuid);
+ SetMOTResult(motCtx, res);
+ return res;
+ }
+ OICFree(strUuid);
+
//Register DTLS event handler to catch the dtls event while handshake
if(CA_STATUS_OK != CAregisterSslHandshakeCallback(MOTDtlsHandshakeCB))
{
OicSecOxm_t oxmSel = selectedDevice->doxm->oxmSel;
OIC_LOG_V(DEBUG, TAG, "Multiple Ownership Transfer method = %d", (int)oxmSel);
+ if(OIC_PRECONFIG_PIN != oxmSel && OIC_RANDOM_DEVICE_PIN != oxmSel)
+ {
+ OIC_LOG(ERROR, TAG, "Unsupported OxM");
+ return OC_STACK_ERROR;
+ }
+
res = OTMSetOTCallback(selectedDevice->doxm->oxmSel, &motCtx->otmCallback);
if(OC_STACK_OK != res)
{
VERIFY_NON_NULL(TAG, motCtx->otmCallback.loadSecretCB, ERROR);
VERIFY_NON_NULL(TAG, motCtx->otmCallback.createSecureSessionCB, ERROR);
- if(OIC_PRECONFIG_PIN != oxmSel && OIC_RANDOM_DEVICE_PIN != oxmSel)
- {
- OIC_LOG(ERROR, TAG, "Unsupported OxM");
- return OC_STACK_ERROR;
- }
-
if(OIC_RANDOM_DEVICE_PIN == oxmSel)
{
if(CA_STATUS_OK != CAregisterPskCredentialsHandler(GetDtlsPskForRandomPinOxm))
}
}
- res = motCtx->otmCallback.loadSecretCB(motCtx);
+ //Save the current context instance to use on the dtls handshake callback
+ res = AddOTMContext(motCtx, selectedDevice->endpoint.addr, selectedDevice->securePort);
VERIFY_SUCCESS(TAG, OC_STACK_OK == res, ERROR);
- //Save the current context instance to use on the dtls handshake callback
- g_MotCtx = motCtx;
+ res = motCtx->otmCallback.loadSecretCB(motCtx);
+ VERIFY_SUCCESS(TAG, OC_STACK_OK == res, ERROR);
res = motCtx->otmCallback.createSecureSessionCB(motCtx);
VERIFY_SUCCESS(TAG, OC_STACK_OK == res, ERROR);
//Fill the device UUID for result array.
size_t devIdx = 0;
- res = OC_STACK_OK;
pCurDev = NULL;
LL_FOREACH(selectedDevicelist, pCurDev)
{
- //Checking duplication of Device ID.
- bool isDuplicate = true;
- res = PDMIsDuplicateDevice(&pCurDev->doxm->deviceID, &isDuplicate);
- VERIFY_SUCCESS(TAG, OC_STACK_OK == res, ERROR);
-
- if (isDuplicate)
- {
- bool isStale = false;
- res = PDMIsDeviceStale(&pCurDev->doxm->deviceID, &isStale);
- VERIFY_SUCCESS(TAG, OC_STACK_OK == res, ERROR);
- VERIFY_SUCCESS(TAG, isStale, ERROR);
-
- if(isStale)
- {
- OIC_LOG(INFO, TAG, "Detected duplicated UUID in stale status, "\
- "this UUID will be removed from PDM");
-
- res = PDMDeleteDevice(&pCurDev->doxm->deviceID);
- VERIFY_SUCCESS(TAG, OC_STACK_OK == res, ERROR);
- }
- }
-
memcpy(motCtx->ctxResultArray[devIdx].deviceId.id,
pCurDev->doxm->deviceID.id,
UUID_LENGTH);
devIdx++;
}
+ motCtx->selectedDeviceInfo = selectedDevicelist;
res = StartMultipleOwnershipTransfer(motCtx, selectedDevicelist);
VERIFY_SUCCESS(TAG, OC_STACK_OK == res, ERROR);
* Change the device status as stale status.
* If all request are successed, this device information will be deleted.
*/
- res = PDMSetDeviceStale(&pTargetDev->doxm->deviceID);
+ res = PDMSetDeviceState(&pTargetDev->doxm->deviceID, PDM_DEVICE_STALE);
if (res != OC_STACK_OK)
{
OIC_LOG(WARNING, TAG, "OCRemoveDevice : Failed to set device status as stale");
--- /dev/null
+#include "logger.h"
+#include "oic_malloc.h"
+#include "oic_string.h"
+#include "octypes.h"
+#include "ownershiptransfermanager.h"
+#include "utlist.h"
+#include "otmcontextlist.h"
+
+#define TAG "OTM_CTX_LIST"
+
+/**
+ * List for saving the OTMContext to be used while ownership transfer.
+ */
+static OTMContextItem_t* g_otmCtxList = NULL;
+
+void RemoveOTMContext(const char* addr, uint16_t port)
+{
+ OTMContext_t* retCtx = NULL;
+
+ OIC_LOG(DEBUG, TAG, "IN RemoveOTMContext");
+
+ if (NULL != addr && 0 != port)
+ {
+ OTMContextItem_t* item = NULL;
+ OTMContextItem_t* temp = NULL;
+
+ LL_FOREACH_SAFE(g_otmCtxList, item, temp)
+ {
+ if (strncmp(addr, item->endpoint.addr, sizeof(item->endpoint.addr)) == 0 &&
+ port == item->endpoint.port)
+ {
+ OIC_LOG_V(DEBUG, TAG, "Remove [%s:%d]'s context from OTMContext list", addr, port);
+ retCtx = item->otmCtx;
+ item->otmCtx = NULL;
+ LL_DELETE(g_otmCtxList, item);
+ OICFree(item);
+ break;
+ }
+ }
+ }
+
+ OIC_LOG(DEBUG, TAG, "OUT RemoveOTMContext");
+
+ return retCtx;
+}
+
+OCStackResult AddOTMContext(OTMContext_t* ctx, const char* addr, uint16_t port)
+{
+ OTMContextItem_t* item = NULL;
+ OTMContextItem_t* temp = NULL;
+ OTMContextItem_t* newItem = NULL;
+
+ OIC_LOG(DEBUG, TAG, "IN AddOTMContext");
+
+ if (NULL == ctx || NULL == addr || 0 == strlen(addr) || 0 == port)
+ {
+ return OC_STACK_INVALID_PARAM;
+ }
+
+ LL_FOREACH_SAFE(g_otmCtxList, item, temp)
+ {
+ if (strncmp(addr, item->endpoint.addr, sizeof(item->endpoint.addr)) == 0 &&
+ port == item->endpoint.port)
+ {
+ //if OTM Context already exists, just return OC_STACK_OK.
+ OIC_LOG(DEBUG, TAG, "Same OTMContext already exists.");
+ return OC_STACK_OK;
+ }
+ }
+
+ newItem = (OTMContextItem_t*)OICCalloc(1, sizeof(OTMContextItem_t));
+ if (NULL == newItem)
+ {
+ OIC_LOG(ERROR, TAG, "Failed to allocate memory.");
+ return OC_STACK_NO_MEMORY;
+ }
+
+ OIC_LOG_V(DEBUG, TAG, "Add [%s:%d]'s context to OTMContext list", addr, port);
+
+ newItem->otmCtx = ctx;
+ OICStrcpy(newItem->endpoint.addr, sizeof(newItem->endpoint.addr), addr);
+ newItem->endpoint.port = port;
+ LL_APPEND(g_otmCtxList, newItem);
+
+ OIC_LOG(DEBUG, TAG, "OUT AddOTMContext");
+
+ return OC_STACK_OK;
+}
+
+const OTMContext_t* GetOTMContext(const char* addr, uint16_t port)
+{
+ OIC_LOG(DEBUG, TAG, "IN GetOTMContext");
+
+ if (NULL != addr && 0 != port)
+ {
+ OTMContextItem_t* item = NULL;
+ OTMContextItem_t* temp = NULL;
+
+ LL_FOREACH_SAFE(g_otmCtxList, item, temp)
+ {
+ if (strncmp(addr, item->endpoint.addr, sizeof(item->endpoint.addr)) == 0 &&
+ port == item->endpoint.port)
+ {
+ OIC_LOG_V(DEBUG, TAG, "Found the OTMContext for [%s:%d]", addr, port);
+ return item->otmCtx;
+ }
+ }
+ }
+
+ OIC_LOG(DEBUG, TAG, "OUT GetOTMContext");
+
+ return NULL;
+}
+
#include "cJSON.h"
#include "global.h"
#include "utlist.h"
-
#include "srmresourcestrings.h"
#include "doxmresource.h"
#include "pstatresource.h"
#include "oxmrandompin.h"
#include "oxmpreconfpin.h"
#endif //_ENABLE_MULTIPLE_OWNER_
+#include "otmcontextlist.h"
#include "pmtypes.h"
#include "pmutility.h"
#include "srmutility.h"
return res;
}
-
/**
* Function to select appropriate provisioning method.
*
{
OIC_LOG_V(DEBUG, TAG, "IN SetResult : %d ", res);
- if(!otmCtx)
+ if(NULL == otmCtx || NULL == otmCtx->selectedDeviceInfo)
{
OIC_LOG(WARNING, TAG, "OTMContext is NULL");
return;
}
- if(otmCtx->selectedDeviceInfo)
+ //If OTM Context was removed from previous response handler, just exit the current OTM process.
+ if(NULL == GetOTMContext(otmCtx->selectedDeviceInfo->endpoint.addr,
+ otmCtx->selectedDeviceInfo->securePort))
+ {
+ OIC_LOG(WARNING, TAG, "Current OTM Process has already ended.");
+ return;
+ }
+
+ //Revert psk_info callback and new deivce uuid in case of random PIN OxM
+ if(OIC_RANDOM_DEVICE_PIN == otmCtx->selectedDeviceInfo->doxm->oxmSel)
{
- //Revert psk_info callback and new deivce uuid in case of random PIN OxM
- if(OIC_RANDOM_DEVICE_PIN == otmCtx->selectedDeviceInfo->doxm->oxmSel)
+ if(CA_STATUS_OK != CAregisterPskCredentialsHandler(GetDtlsPskCredentials))
{
- if(CA_STATUS_OK != CAregisterPskCredentialsHandler(GetDtlsPskCredentials))
- {
- OIC_LOG(WARNING, TAG, "Failed to revert is DTLS credential handler.");
- }
- OicUuid_t emptyUuid = { .id={0}};
- SetUuidForPinBasedOxm(&emptyUuid);
+ OIC_LOG(WARNING, TAG, "Failed to revert is DTLS credential handler.");
}
+ OicUuid_t emptyUuid = { .id={0}};
+ SetUuidForPinBasedOxm(&emptyUuid);
+ }
- for(size_t i = 0; i < otmCtx->ctxResultArraySize; i++)
+ for(size_t i = 0; i < otmCtx->ctxResultArraySize; i++)
+ {
+ if(memcmp(otmCtx->selectedDeviceInfo->doxm->deviceID.id,
+ otmCtx->ctxResultArray[i].deviceId.id, UUID_LENGTH) == 0)
{
- if(memcmp(otmCtx->selectedDeviceInfo->doxm->deviceID.id,
- otmCtx->ctxResultArray[i].deviceId.id, UUID_LENGTH) == 0)
+ otmCtx->ctxResultArray[i].res = res;
+ if(OC_STACK_OK != res && OC_STACK_CONTINUE != res && OC_STACK_DUPLICATE_REQUEST != res)
{
- otmCtx->ctxResultArray[i].res = res;
- if(OC_STACK_OK != res)
- {
- otmCtx->ctxHasError = true;
- }
+ otmCtx->ctxHasError = true;
}
}
+ }
- g_otmCtx = NULL;
+ //In case of duplicated OTM process, OTMContext and OCDoHandle should not be removed.
+ if(OC_STACK_DUPLICATE_REQUEST != res)
+ {
+ //Remove the current OTM Context from OTM queue
+ RemoveOTMContext(otmCtx->selectedDeviceInfo->endpoint.addr,
+ otmCtx->selectedDeviceInfo->securePort);
- //If all request is completed, invoke the user callback.
- if(IsComplete(otmCtx))
- {
- otmCtx->ctxResultCallback(otmCtx->userCtx, otmCtx->ctxResultArraySize,
- otmCtx->ctxResultArray, otmCtx->ctxHasError);
- OICFree(otmCtx->ctxResultArray);
- OICFree(otmCtx);
- }
- else
+ //If there is a request being performed, cancel it to prevent retransmission.
+ if(otmCtx->ocDoHandle)
{
- if(OC_STACK_OK != StartOwnershipTransfer(otmCtx,
- otmCtx->selectedDeviceInfo->next))
+ OIC_LOG_V(DEBUG, TAG, "OCCancel - %s : %d",
+ otmCtx->selectedDeviceInfo->endpoint.addr,
+ otmCtx->selectedDeviceInfo->securePort);
+ if(OC_STACK_OK != OCCancel(otmCtx->ocDoHandle, OC_HIGH_QOS, NULL, 0))
+ {
+ OIC_LOG(WARNING, TAG, "Failed to remove registered callback");
+ }
+ else
{
- OIC_LOG(ERROR, TAG, "Failed to StartOwnershipTransfer");
+ otmCtx->ocDoHandle = NULL;
}
}
}
+ //If all OTM process is complete, invoke the user callback.
+ if(IsComplete(otmCtx))
+ {
+ otmCtx->ctxResultCallback(otmCtx->userCtx, otmCtx->ctxResultArraySize,
+ otmCtx->ctxResultArray, otmCtx->ctxHasError);
+ OICFree(otmCtx->ctxResultArray);
+ OICFree(otmCtx);
+ }
+ else
+ {
+ if(OC_STACK_OK != StartOwnershipTransfer(otmCtx,
+ otmCtx->selectedDeviceInfo->next))
+ {
+ OIC_LOG(ERROR, TAG, "Failed to StartOwnershipTransfer");
+ }
+ }
+
OIC_LOG(DEBUG, TAG, "OUT SetResult");
}
*/
void DTLSHandshakeCB(const CAEndpoint_t *endpoint, const CAErrorInfo_t *info)
{
- if(NULL != g_otmCtx && NULL != g_otmCtx->selectedDeviceInfo &&
- NULL != endpoint && NULL != info)
+ if(NULL != endpoint && NULL != info)
{
OIC_LOG_V(INFO, TAG, "Received status from remote device(%s:%d) : %d",
endpoint->addr, endpoint->port, info->result);
- OicSecDoxm_t* newDevDoxm = g_otmCtx->selectedDeviceInfo->doxm;
-
- if(NULL != newDevDoxm)
+ OTMContext_t* otmCtx = GetOTMContext(endpoint->addr, endpoint->port);
+ if(otmCtx)
{
- OicUuid_t emptyUuid = {.id={0}};
-
- //Make sure the address matches.
- if(strncmp(g_otmCtx->selectedDeviceInfo->endpoint.addr,
- endpoint->addr,
- sizeof(endpoint->addr)) == 0 &&
- g_otmCtx->selectedDeviceInfo->securePort == endpoint->port)
+ OicSecDoxm_t* newDevDoxm = otmCtx->selectedDeviceInfo->doxm;
+ if(NULL != newDevDoxm)
{
- OCStackResult res = OC_STACK_ERROR;
+ OicUuid_t emptyUuid = {.id={0}};
- //If temporal secure sesstion established successfully
- if(CA_STATUS_OK == info->result &&
- false == newDevDoxm->owned &&
- memcmp(&(newDevDoxm->owner), &emptyUuid, sizeof(OicUuid_t)) == 0)
- {
- //Send request : POST /oic/sec/doxm [{... , "devowner":"PT's UUID"}]
- res = PostOwnerUuid(g_otmCtx);
- if(OC_STACK_OK != res)
- {
- OIC_LOG(ERROR, TAG, "OperationModeUpdate : Failed to send owner information");
- SetResult(g_otmCtx, res);
- }
- }
- //In case of authentication failure
- else if(CA_DTLS_AUTHENTICATION_FAILURE == info->result)
+ //Make sure the address matches.
+ if(strncmp(otmCtx->selectedDeviceInfo->endpoint.addr,
+ endpoint->addr,
+ sizeof(endpoint->addr)) == 0 &&
+ otmCtx->selectedDeviceInfo->securePort == endpoint->port)
{
- //in case of error from owner credential
- if(memcmp(&(newDevDoxm->owner), &emptyUuid, sizeof(OicUuid_t)) != 0 &&
- true == newDevDoxm->owned)
- {
- OIC_LOG(ERROR, TAG, "The owner credential may incorrect.");
+ OCStackResult res = OC_STACK_ERROR;
- if(OC_STACK_OK != RemoveCredential(&(newDevDoxm->deviceID)))
+ //If temporal secure sesstion established successfully
+ if(CA_STATUS_OK == info->result &&
+ false == newDevDoxm->owned &&
+ memcmp(&(newDevDoxm->owner), &emptyUuid, sizeof(OicUuid_t)) == 0)
+ {
+ //Send request : POST /oic/sec/doxm [{... , "devowner":"PT's UUID"}]
+ res = PostOwnerUuid(otmCtx);
+ if(OC_STACK_OK != res)
{
- OIC_LOG(WARNING, TAG, "Failed to remove the invaild owner credential");
+ OIC_LOG(ERROR, TAG, "OperationModeUpdate : Failed to send owner information");
+ SetResult(otmCtx, res);
}
- SetResult(g_otmCtx, OC_STACK_AUTHENTICATION_FAILURE);
}
- //in case of error from wrong PIN, re-start the ownership transfer
- else if(OIC_RANDOM_DEVICE_PIN == newDevDoxm->oxmSel)
+ //In case of authentication failure
+ else if(CA_DTLS_AUTHENTICATION_FAILURE == info->result)
{
- OIC_LOG(ERROR, TAG, "The PIN number may incorrect.");
-
- memcpy(&(newDevDoxm->owner), &emptyUuid, sizeof(OicUuid_t));
- newDevDoxm->owned = false;
- g_otmCtx->attemptCnt++;
+ //in case of error from owner credential
+ if(memcmp(&(newDevDoxm->owner), &emptyUuid, sizeof(OicUuid_t)) != 0 &&
+ true == newDevDoxm->owned)
+ {
+ OIC_LOG(ERROR, TAG, "The owner credential may incorrect.");
- if(WRONG_PIN_MAX_ATTEMP > g_otmCtx->attemptCnt)
+ if(OC_STACK_OK != RemoveCredential(&(newDevDoxm->deviceID)))
+ {
+ OIC_LOG(WARNING, TAG, "Failed to remove the invaild owner credential");
+ }
+ SetResult(otmCtx, OC_STACK_AUTHENTICATION_FAILURE);
+ }
+ //in case of error from wrong PIN, re-start the ownership transfer
+ else if(OIC_RANDOM_DEVICE_PIN == newDevDoxm->oxmSel)
{
- res = StartOwnershipTransfer(g_otmCtx, g_otmCtx->selectedDeviceInfo);
- if(OC_STACK_OK != res)
+ OIC_LOG(ERROR, TAG, "The PIN number may incorrect.");
+
+ memcpy(&(newDevDoxm->owner), &emptyUuid, sizeof(OicUuid_t));
+ newDevDoxm->owned = false;
+ otmCtx->attemptCnt++;
+
+ if(WRONG_PIN_MAX_ATTEMP > otmCtx->attemptCnt)
+ {
+ res = StartOwnershipTransfer(otmCtx, otmCtx->selectedDeviceInfo);
+ if(OC_STACK_OK != res)
+ {
+ SetResult(otmCtx, res);
+ OIC_LOG(ERROR, TAG, "Failed to Re-StartOwnershipTransfer");
+ }
+ }
+ else
{
- SetResult(g_otmCtx, res);
- OIC_LOG(ERROR, TAG, "Failed to Re-StartOwnershipTransfer");
+ OIC_LOG(ERROR, TAG, "User has exceeded the number of authentication attempts.");
+ SetResult(otmCtx, OC_STACK_AUTHENTICATION_FAILURE);
}
}
else
{
- OIC_LOG(ERROR, TAG, "User has exceeded the number of authentication attempts.");
- SetResult(g_otmCtx, OC_STACK_AUTHENTICATION_FAILURE);
+ OIC_LOG(ERROR, TAG, "Failed to establish secure session.");
+ SetResult(otmCtx, OC_STACK_AUTHENTICATION_FAILURE);
}
}
- else
- {
- OIC_LOG(ERROR, TAG, "Failed to establish secure session.");
- SetResult(g_otmCtx, OC_STACK_AUTHENTICATION_FAILURE);
- }
}
}
}
+ else
+ {
+ OIC_LOG(ERROR, TAG, "Can not find the OTM Context.");
+ }
}
}
VERIFY_NON_NULL(TAG, ctx, WARNING);
OTMContext_t* otmCtx = (OTMContext_t*)ctx;
+ otmCtx->ocDoHandle = NULL;
(void)UNUSED;
if (OC_STACK_RESOURCE_CHANGED == clientResponse->result)
{
VERIFY_NON_NULL(TAG, ctx, WARNING);
OTMContext_t* otmCtx = (OTMContext_t*)ctx;
+ otmCtx->ocDoHandle = NULL;
(void)UNUSED;
if (OC_STACK_OK == clientResponse->result)
{
(void)UNUSED;
OCStackResult res = OC_STACK_OK;
OTMContext_t* otmCtx = (OTMContext_t*)ctx;
+ otmCtx->ocDoHandle = NULL;
if(OC_STACK_RESOURCE_CHANGED == clientResponse->result)
{
VERIFY_NON_NULL(TAG, ctx, WARNING);
OTMContext_t* otmCtx = (OTMContext_t*)ctx;
+ otmCtx->ocDoHandle = NULL;
(void) UNUSED;
if (OC_STACK_RESOURCE_CHANGED == clientResponse->result)
{
}
}
- //It will be used in handshake event handler
- g_otmCtx = otmCtx;
+ //Save the current context instance to use on the dtls handshake callback
+ if(OC_STACK_OK != AddOTMContext(otmCtx,
+ otmCtx->selectedDeviceInfo->endpoint.addr,
+ otmCtx->selectedDeviceInfo->securePort))
+ {
+ OIC_LOG(ERROR, TAG, "OperationModeUpdate : Failed to add OTM Context into OTM List.");
+ SetResult(otmCtx, res);
+ return OC_STACK_DELETE_TRANSACTION;
+ }
//Try DTLS handshake to generate secure session
if(otmCtx->otmCallback.createSecureSessionCB)
(void)UNUSED;
OCStackResult res = OC_STACK_OK;
OTMContext_t* otmCtx = (OTMContext_t*)ctx;
+ otmCtx->ocDoHandle = NULL;
if(OC_STACK_RESOURCE_CHANGED == clientResponse->result)
{
(void)UNUSED;
OCStackResult res = OC_STACK_OK;
OTMContext_t* otmCtx = (OTMContext_t*)ctx;
+ otmCtx->ocDoHandle = NULL;
if(OC_STACK_RESOURCE_CHANGED == clientResponse->result)
{
(void)UNUSED;
OCStackResult res = OC_STACK_OK;
OTMContext_t* otmCtx = (OTMContext_t*)ctx;
+ otmCtx->ocDoHandle = NULL;
if(OC_STACK_RESOURCE_CHANGED == clientResponse->result)
{
VERIFY_NON_NULL(TAG, ctx, ERROR);
OTMContext_t* otmCtx = (OTMContext_t*) ctx;
+ otmCtx->ocDoHandle = NULL;
(void)UNUSED;
OCStackResult res = OC_STACK_OK;
VERIFY_NON_NULL(TAG, ctx, ERROR);
OTMContext_t* otmCtx = (OTMContext_t*) ctx;
+ otmCtx->ocDoHandle = NULL;
(void)UNUSED;
if (OC_STACK_RESOURCE_CHANGED == clientResponse->result)
{
OIC_LOG(INFO, TAG, "Device state is in Ready for Normal Operation.");
- OCStackResult res = PDMAddDevice(&otmCtx->selectedDeviceInfo->doxm->deviceID);
+ OCStackResult res = PDMSetDeviceState(&otmCtx->selectedDeviceInfo->doxm->deviceID,
+ PDM_DEVICE_ACTIVE);
if (OC_STACK_OK == res)
{
OIC_LOG_V(INFO, TAG, "Add device's UUID in PDM_DB");
cbData.cb = &OwnerCredentialHandler;
cbData.context = (void *)otmCtx;
cbData.cd = NULL;
- OCStackResult res = OCDoResource(NULL, OC_REST_POST, query,
+ OCStackResult res = OCDoResource(&otmCtx->ocDoHandle, OC_REST_POST, query,
&deviceInfo->endpoint, (OCPayload*)secPayload,
deviceInfo->connType, OC_HIGH_QOS, &cbData, NULL, 0);
if (res != OC_STACK_OK)
cbData.cb = &OwnerAclHandler;
cbData.context = (void *)otmCtx;
cbData.cd = NULL;
- res = OCDoResource(NULL, OC_REST_POST, query,
+ res = OCDoResource(&otmCtx->ocDoHandle, OC_REST_POST, query,
&deviceInfo->endpoint, (OCPayload*)secPayload,
deviceInfo->connType, OC_HIGH_QOS, &cbData, NULL, 0);
if (res != OC_STACK_OK)
cbData.cb = &OwnerTransferModeHandler;
cbData.context = (void *)otmCtx;
cbData.cd = NULL;
- res = OCDoResource(NULL, OC_REST_POST, query,
+ res = OCDoResource(&otmCtx->ocDoHandle, OC_REST_POST, query,
&deviceInfo->endpoint, (OCPayload *)secPayload,
deviceInfo->connType, OC_HIGH_QOS, &cbData, NULL, 0);
if (res != OC_STACK_OK)
cbData.cb = &ListMethodsHandler;
cbData.context = (void *)otmCtx;
cbData.cd = NULL;
- OCStackResult res = OCDoResource(NULL, OC_REST_GET, query, NULL, NULL,
+ OCStackResult res = OCDoResource(&otmCtx->ocDoHandle, OC_REST_GET, query, NULL, NULL,
deviceInfo->connType, OC_HIGH_QOS, &cbData, NULL, 0);
if (res != OC_STACK_OK)
{
cbData.context = (void *)otmCtx;
cbData.cd = NULL;
- res = OCDoResource(NULL, OC_REST_POST, query, 0, (OCPayload *)secPayload,
+ res = OCDoResource(&otmCtx->ocDoHandle, OC_REST_POST, query, 0, (OCPayload *)secPayload,
deviceInfo->connType, OC_HIGH_QOS, &cbData, NULL, 0);
if (res != OC_STACK_OK)
{
cbData.context = (void *)otmCtx;
cbData.cd = NULL;
- res = OCDoResource(NULL, OC_REST_POST, query, 0, (OCPayload*)secPayload,
+ res = OCDoResource(&otmCtx->ocDoHandle, OC_REST_POST, query, 0, (OCPayload*)secPayload,
deviceInfo->connType, OC_HIGH_QOS, &cbData, NULL, 0);
if (res != OC_STACK_OK)
{
cbData.cb = &OperationModeUpdateHandler;
cbData.context = (void *)otmCtx;
cbData.cd = NULL;
- res = OCDoResource(NULL, OC_REST_POST, query, 0, (OCPayload *)secPayload,
+ res = OCDoResource(&otmCtx->ocDoHandle, OC_REST_POST, query, 0, (OCPayload *)secPayload,
deviceInfo->connType, OC_HIGH_QOS, &cbData, NULL, 0);
if (res != OC_STACK_OK)
{
OTMContext_t* otmCtx = (OTMContext_t*)ctx;
otmCtx->selectedDeviceInfo = selectedDevice;
+ //Checking duplication of Device ID.
+ bool isDuplicate = true;
+ res = PDMIsDuplicateDevice(&selectedDevice->doxm->deviceID, &isDuplicate);
+ if (OC_STACK_OK != res)
+ {
+ OIC_LOG(ERROR, TAG, "Internal error in PDMIsDuplicateDevice");
+ return res;
+ }
+ if (isDuplicate)
+ {
+ PdmDeviceState_t state = PDM_DEVICE_UNKNOWN;
+ res = PDMGetDeviceState(&selectedDevice->doxm->deviceID, &state);
+ if(OC_STACK_OK != res)
+ {
+ OIC_LOG(ERROR, TAG, "Internal error in PDMGetDeviceState");
+ SetResult(otmCtx, res);
+ return res;
+ }
+
+ char* strUuid = NULL;
+ res = ConvertUuidToStr(&selectedDevice->doxm->deviceID, &strUuid);
+ if(OC_STACK_OK != res)
+ {
+ OIC_LOG(ERROR, TAG, "Failed to convert UUID to str");
+ SetResult(otmCtx, res);
+ return res;
+ }
+
+ if(PDM_DEVICE_STALE == state)
+ {
+ OIC_LOG(INFO, TAG, "Detected duplicated UUID in stale status, "
+ "this UUID will be removed from PDM");
+
+ res = PDMDeleteDevice(&selectedDevice->doxm->deviceID);
+ if(OC_STACK_OK != res)
+ {
+ OIC_LOG(ERROR, TAG, "Internal error in PDMDeleteDevice");
+ OICFree(strUuid);
+ SetResult(otmCtx, res);
+ return res;
+ }
+ }
+ else if(PDM_DEVICE_INIT == state)
+ {
+ OIC_LOG_V(ERROR, TAG, "[%s]'s ownership transfer process is already started.", strUuid);
+ OICFree(strUuid);
+ SetResult(otmCtx, OC_STACK_DUPLICATE_REQUEST);
+ return OC_STACK_OK;
+ }
+ else
+ {
+ OIC_LOG(ERROR, TAG, "Unknow device status while OTM.");
+ OICFree(strUuid);
+ SetResult(otmCtx, OC_STACK_ERROR);
+ return OC_STACK_ERROR;
+ }
+ }
+ else
+ {
+ res = PDMAddDevice(&selectedDevice->doxm->deviceID);
+ if(OC_STACK_OK != res)
+ {
+ OIC_LOG(ERROR, TAG, "Internal error in PDMAddDevice");
+ SetResult(otmCtx, res);
+ return res;
+ }
+ }
+
+
//Set to the lowest level OxM, and then find more higher level OxM.
res = SelectProvisioningMethod(selectedDevice->doxm->oxm,
selectedDevice->doxm->oxmLen,
//Fill the device UUID for result array.
for(size_t devIdx = 0; devIdx < otmCtx->ctxResultArraySize; devIdx++)
{
- //Checking duplication of Device ID.
- bool isDuplicate = true;
- res = PDMIsDuplicateDevice(&pCurDev->doxm->deviceID, &isDuplicate);
- if (OC_STACK_OK != res)
- {
- goto error;
- }
- if (isDuplicate)
- {
- bool isStale = false;
- res = PDMIsDeviceStale(&pCurDev->doxm->deviceID, &isStale);
- if(OC_STACK_OK != res)
- {
- OIC_LOG(ERROR, TAG, "Internal error in PDMIsDeviceStale");
- goto error;
- }
- if(isStale)
- {
- OIC_LOG(INFO, TAG, "Detected duplicated UUID in stale status, "\
- "this UUID will be removed from PDM");
-
- res = PDMDeleteDevice(&pCurDev->doxm->deviceID);
- if(OC_STACK_OK != res)
- {
- OIC_LOG(ERROR, TAG, "Internal error in PDMDeleteDevice");
- goto error;
- }
- }
- else
- {
- OIC_LOG(ERROR, TAG, "OTMDoOwnershipTransfer : Device UUID is duplicated");
- res = OC_STACK_INVALID_PARAM;
- goto error;
- }
- }
memcpy(otmCtx->ctxResultArray[devIdx].deviceId.id,
pCurDev->doxm->deviceID.id,
UUID_LENGTH);
cbData.cb = &ProvisioningStatusHandler;
cbData.context = (void*)otmCtx;
cbData.cd = NULL;
- OCStackResult ret = OCDoResource(NULL, OC_REST_POST, query, 0, (OCPayload*)secPayload,
+ OCStackResult ret = OCDoResource(&otmCtx->ocDoHandle, OC_REST_POST, query, 0, (OCPayload*)secPayload,
otmCtx->selectedDeviceInfo->connType, OC_HIGH_QOS, &cbData, NULL, 0);
OIC_LOG_V(INFO, TAG, "OCDoResource returned: %d",ret);
if (ret != OC_STACK_OK)
cbData.cb = &ReadyForNomalStatusHandler;
cbData.context = (void*)otmCtx;
cbData.cd = NULL;
- OCStackResult ret = OCDoResource(NULL, OC_REST_POST, query, 0, (OCPayload*)secPayload,
+ OCStackResult ret = OCDoResource(&otmCtx->ocDoHandle, OC_REST_POST, query, 0, (OCPayload*)secPayload,
otmCtx->selectedDeviceInfo->connType, OC_HIGH_QOS, &cbData, NULL, 0);
OIC_LOG_V(INFO, TAG, "OCDoResource returned: %d",ret);
if (ret != OC_STACK_OK)
#define TAG "PDM"
-#define PDM_STALE_STATE 1
-#define PDM_ACTIVE_STATE 0
-
#define PDM_FIRST_INDEX 0
#define PDM_SECOND_INDEX 1
res = sqlite3_bind_blob(stmt, PDM_BIND_INDEX_SECOND, UUID, UUID_LENGTH, SQLITE_STATIC);
PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR);
- res = sqlite3_bind_int(stmt, PDM_BIND_INDEX_THIRD, PDM_ACTIVE_STATE);
+ res = sqlite3_bind_int(stmt, PDM_BIND_INDEX_THIRD, PDM_DEVICE_INIT);
PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR);
res = sqlite3_step(stmt);
}
/**
- * Function to check whether device is stale or not
- */
-OCStackResult PDMIsDeviceStale(const OicUuid_t *uuid, bool *result)
-{
- if (NULL == uuid || NULL == result)
- {
- OIC_LOG(ERROR, TAG, "UUID or result is NULL");
- return OC_STACK_INVALID_PARAM;
- }
-
- sqlite3_stmt *stmt = 0;
- int res = 0;
- res = sqlite3_prepare_v2(g_db, PDM_SQLITE_GET_DEVICE_STATUS, strlen(PDM_SQLITE_GET_DEVICE_STATUS) + 1,
- &stmt, NULL);
- PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR);
-
- res = sqlite3_bind_blob(stmt, PDM_BIND_INDEX_FIRST, uuid, UUID_LENGTH, SQLITE_STATIC);
- PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR);
-
- bool retValue = false;
- while(SQLITE_ROW == sqlite3_step(stmt))
- {
- int tempStaleStateFromDb = sqlite3_column_int(stmt, PDM_FIRST_INDEX);
- OIC_LOG_V(DEBUG, TAG, "Stale state is %d", tempStaleStateFromDb);
- if (PDM_STALE_STATE == tempStaleStateFromDb)
- {
- OIC_LOG(INFO, TAG, "Device is stale");
- retValue = true;
- }
- }
- *result = retValue;
- sqlite3_finalize(stmt);
- return OC_STACK_OK;
-}
-
-/**
*function to get Id for given UUID
*/
static OCStackResult getIdForUUID(const OicUuid_t *UUID , int *id)
res = sqlite3_bind_int(stmt, PDM_BIND_INDEX_SECOND, id2);
PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR);
- res = sqlite3_bind_int(stmt, PDM_BIND_INDEX_THIRD, PDM_ACTIVE_STATE);
+ res = sqlite3_bind_int(stmt, PDM_BIND_INDEX_THIRD, PDM_DEVICE_ACTIVE);
PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR);
if (sqlite3_step(stmt) != SQLITE_DONE)
return OC_STACK_INVALID_PARAM;
}
- bool result = false;
- if (OC_STACK_OK != PDMIsDeviceStale(UUID1, &result))
+ PdmDeviceState_t state = PDM_DEVICE_UNKNOWN;
+ if (OC_STACK_OK != PDMGetDeviceState(UUID1, &state))
{
OIC_LOG(ERROR, TAG, "Internal error occured");
return OC_STACK_ERROR;
}
- if (result)
+ if (PDM_DEVICE_ACTIVE != state)
{
- OIC_LOG(ERROR, TAG, "UUID1:Stale device");
+ OIC_LOG_V(ERROR, TAG, "UUID1: Device state is not active : %d", state);
return OC_STACK_INVALID_PARAM;
}
- result = false;
- if (OC_STACK_OK != PDMIsDeviceStale(UUID2, &result))
+
+ state = PDM_DEVICE_UNKNOWN;
+ if (OC_STACK_OK != PDMGetDeviceState(UUID2, &state))
{
OIC_LOG(ERROR, TAG, "Internal error occured");
return OC_STACK_ERROR;
}
- if (result)
+ if (PDM_DEVICE_ACTIVE != state)
{
- OIC_LOG(ERROR, TAG, "UUID2:Stale device");
+ OIC_LOG_V(ERROR, TAG, "UUID2: Device state is not active : %d", state);
return OC_STACK_INVALID_PARAM;
}
return OC_STACK_INVALID_PARAM;
}
ASCENDING_ORDER(id1, id2);
- return updateLinkState(id1, id2, PDM_STALE_STATE);
-
+ return updateLinkState(id1, id2, PDM_DEVICE_STALE);
}
OCStackResult PDMGetOwnedDevices(OCUuidList_t **uuidList, size_t *numOfDevices)
memcpy(uid, ptr, sizeof(OicUuid_t));
int temp = sqlite3_column_int(stmt, PDM_SECOND_INDEX);
- if(PDM_STALE_STATE == temp)
+ if(PDM_DEVICE_STALE == temp)
{
if(result)
{
OIC_LOG(ERROR, TAG, "Not null list will cause memory leak");
return OC_STACK_INVALID_PARAM;
}
- bool result = false;
- OCStackResult ret = PDMIsDeviceStale(UUID, &result);
+ PdmDeviceState_t state = PDM_DEVICE_UNKNOWN;
+ OCStackResult ret = PDMGetDeviceState(UUID, &state);
if (OC_STACK_OK != ret)
{
OIC_LOG(ERROR, TAG, "Internal error occured");
return OC_STACK_ERROR;
}
- if (result)
+ if (PDM_DEVICE_ACTIVE != state)
{
- OIC_LOG(ERROR, TAG, "Device is stale");
+ OIC_LOG_V(ERROR, TAG, "Device state is not active : %d", state);
return OC_STACK_INVALID_PARAM;
}
int id = 0;
strlen(PDM_SQLITE_GET_STALE_INFO) + 1, &stmt, NULL);
PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR);
- res = sqlite3_bind_int(stmt, PDM_BIND_INDEX_FIRST, PDM_STALE_STATE);
+ res = sqlite3_bind_int(stmt, PDM_BIND_INDEX_FIRST, PDM_DEVICE_STALE);
PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR);
size_t counter = 0;
return OC_STACK_INVALID_PARAM;
}
- bool isStale = false;
- if (OC_STACK_OK != PDMIsDeviceStale(uuidOfDevice1, &isStale))
+ PdmDeviceState_t state = PDM_DEVICE_UNKNOWN;
+ if (OC_STACK_OK != PDMGetDeviceState(uuidOfDevice1, &state))
{
OIC_LOG(ERROR, TAG, "uuidOfDevice1:Internal error occured");
return OC_STACK_ERROR;
}
- if (isStale)
+ if (PDM_DEVICE_ACTIVE != state)
{
- OIC_LOG(ERROR, TAG, "uuidOfDevice1:Device is stale");
+ OIC_LOG_V(ERROR, TAG, "uuidOfDevice1:Device state is not active : %d", state);
return OC_STACK_INVALID_PARAM;
}
- isStale = false;
- if (OC_STACK_OK != PDMIsDeviceStale(uuidOfDevice2, &isStale))
+ state = PDM_DEVICE_UNKNOWN;
+ if (OC_STACK_OK != PDMGetDeviceState(uuidOfDevice2, &state))
{
OIC_LOG(ERROR, TAG, "uuidOfDevice2:Internal error occured");
return OC_STACK_ERROR;
}
- if (isStale)
+ if (PDM_DEVICE_ACTIVE != state)
{
- OIC_LOG(ERROR, TAG, "uuidOfDevice2:Device is stale");
+ OIC_LOG_V(ERROR, TAG, "uuidOfDevice2:Device state is not active : %d", state);
return OC_STACK_INVALID_PARAM;
}
return OC_STACK_OK;
}
-static OCStackResult updateDeviceState(const OicUuid_t *uuid, int state)
+static OCStackResult updateDeviceState(const OicUuid_t *uuid, PdmDeviceState_t state)
{
sqlite3_stmt *stmt = 0;
int res = 0 ;
return OC_STACK_OK;
}
-OCStackResult PDMSetDeviceStale(const OicUuid_t* uuidOfDevice)
+OCStackResult PDMSetDeviceState(const OicUuid_t* uuid, PdmDeviceState_t state)
{
+ OCStackResult res = OC_STACK_ERROR;
+
CHECK_PDM_INIT(TAG);
- if (NULL == uuidOfDevice)
+ if (NULL == uuid)
{
OIC_LOG(ERROR, TAG, "Invalid PARAM");
return OC_STACK_INVALID_PARAM;
}
begin();
- OCStackResult res = updateLinkForStaleDevice(uuidOfDevice);
- if (OC_STACK_OK != res)
+
+ if(PDM_DEVICE_STALE == state)
{
- rollback();
- OIC_LOG(ERROR, TAG, "unable to update links");
- return res;
+ res = updateLinkForStaleDevice(uuid);
+ if (OC_STACK_OK != res)
+ {
+ rollback();
+ OIC_LOG(ERROR, TAG, "unable to update links");
+ return res;
+ }
}
- res = updateDeviceState(uuidOfDevice, PDM_STALE_STATE);
+
+ res = updateDeviceState(uuid, state);
if (OC_STACK_OK != res)
{
rollback();
commit();
return OC_STACK_OK;
}
+
+OCStackResult PDMGetDeviceState(const OicUuid_t *uuid, PdmDeviceState_t* result)
+{
+ if (NULL == uuid || NULL == result)
+ {
+ OIC_LOG(ERROR, TAG, "UUID or result is NULL");
+ return OC_STACK_INVALID_PARAM;
+ }
+
+ sqlite3_stmt *stmt = 0;
+ int res = 0;
+ res = sqlite3_prepare_v2(g_db, PDM_SQLITE_GET_DEVICE_STATUS, strlen(PDM_SQLITE_GET_DEVICE_STATUS) + 1,
+ &stmt, NULL);
+ PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR);
+
+ res = sqlite3_bind_blob(stmt, PDM_BIND_INDEX_FIRST, uuid, UUID_LENGTH, SQLITE_STATIC);
+ PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR);
+
+ *result = PDM_DEVICE_UNKNOWN;
+ while(SQLITE_ROW == sqlite3_step(stmt))
+ {
+ int tempStaleStateFromDb = sqlite3_column_int(stmt, PDM_FIRST_INDEX);
+ OIC_LOG_V(DEBUG, TAG, "Device state is %d", tempStaleStateFromDb);
+ *result = (PdmDeviceState_t)tempStaleStateFromDb;
+ }
+ sqlite3_finalize(stmt);
+ return OC_STACK_OK;
+}
+
{
OicUuid_t uid1 = {{0,}};
memcpy(&uid1.id, ID_1, sizeof(uid1.id));
- PDMAddDevice(&uid1);
+ EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid1));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid1, PDM_DEVICE_ACTIVE));
OicUuid_t uid2 = {{0,}};
memcpy(&uid2.id, ID_2, sizeof(uid2.id));
- PDMAddDevice(&uid2);
+ EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid2));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid2, PDM_DEVICE_ACTIVE));
OicUuid_t uid3 = {{0,}};
memcpy(&uid3.id, ID_3, sizeof(uid3.id));
bool isDuplicate = true;
{
OicUuid_t uid1 = {{0,}};
memcpy(&uid1.id, ID_4, sizeof(uid1.id));
- PDMAddDevice(&uid1);
+ EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid1));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid1, PDM_DEVICE_ACTIVE));
+
OicUuid_t uid2 = {{0,}};
memcpy(&uid2.id, ID_5, sizeof(uid2.id));
- PDMAddDevice(&uid2);
+ EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid2));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid2, PDM_DEVICE_ACTIVE));
+
EXPECT_EQ(OC_STACK_OK, PDMLinkDevices(&uid1, &uid2));
}
EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid1));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid1, PDM_DEVICE_ACTIVE));
+
EXPECT_EQ(OC_STACK_OK, PDMLinkDevices(&uid1, &uid2));
EXPECT_EQ(OC_STACK_OK, PDMSetLinkStale(&uid1, &uid2));
OicUuid_t uid1 = {{0,}};
memcpy(&uid1.id, ID_7, sizeof(uid1.id));
EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid1));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid1, PDM_DEVICE_ACTIVE));
+
OicUuid_t uid2 = {{0,}};
memcpy(&uid2.id, ID_8, sizeof(uid2.id));
EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid2));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid2, PDM_DEVICE_ACTIVE));
bool linkExisits = true;
OCStackResult res = PDMIsLinkExists(&uid1, &uid2, &linkExisits);
TEST(PDMSetDeviceStaleTest, NULLUUID)
{
EXPECT_EQ(OC_STACK_OK, PDMInit(NULL));
- EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMSetDeviceStale(NULL));
+ EXPECT_EQ(OC_STACK_INVALID_PARAM, PDMSetDeviceState(NULL, PDM_DEVICE_STALE));
}
TEST(PDMSetDeviceStaleTest, VALIDUUID)
OicUuid_t uid1 = {{0,}};
memcpy(&uid1.id, ID_9, sizeof(uid1.id));
EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid1));
- EXPECT_EQ(OC_STACK_OK,PDMSetDeviceStale(&uid1));
+ EXPECT_EQ(OC_STACK_OK,PDMSetDeviceState(&uid1, PDM_DEVICE_STALE));
}
TEST(PDMSetDeviceStaleTest, StaleDeviceNotinDeviceList)
OicUuid_t uid1 = {{0,}};
memcpy(&uid1.id, ID_10, sizeof(uid1.id));
EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid1));
- EXPECT_EQ(OC_STACK_OK,PDMSetDeviceStale(&uid1));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid1, PDM_DEVICE_STALE));
OCUuidList_t *list = NULL;
size_t noOfDevcies = 0;
memcpy(&uid3.id, ID_13, sizeof(uid3.id));
EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid1));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid1, PDM_DEVICE_ACTIVE));
EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid2));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid2, PDM_DEVICE_ACTIVE));
EXPECT_EQ(OC_STACK_OK, PDMAddDevice(&uid3));
+ EXPECT_EQ(OC_STACK_OK, PDMSetDeviceState(&uid3, PDM_DEVICE_ACTIVE));
EXPECT_EQ(OC_STACK_OK, PDMLinkDevices(&uid1, &uid2));
EXPECT_EQ(OC_STACK_OK, PDMLinkDevices(&uid2, &uid3));
EXPECT_EQ(OC_STACK_OK, PDMLinkDevices(&uid1, &uid3));
- EXPECT_EQ(OC_STACK_OK,PDMSetDeviceStale(&uid1));
+ EXPECT_EQ(OC_STACK_OK,PDMSetDeviceState(&uid1, PDM_DEVICE_STALE));
OCUuidList_t *list1 = NULL;
size_t noOfDevices1 = 0;
validity = NULL;
}
+#ifdef _ENABLE_MULTIPLE_OWNER_
+ OICFree(ace->eownerID);
+#endif
+
//Clean ACE
OICFree(ace);
ace = NULL;
}
}
+#ifdef _ENABLE_MULTIPLE_OWNER_
+ if (ace->eownerID)
+ {
+ if (NULL == newAce->eownerID)
+ {
+ newAce->eownerID = (OicUuid_t*)OICCalloc(1, sizeof(OicUuid_t));
+ VERIFY_NON_NULL(TAG, (newAce->eownerID), ERROR);
+ }
+ memcpy(newAce->eownerID->id, ace->eownerID->id, sizeof(ace->eownerID->id));
+ }
+#endif
+
newAce->next = NULL;
}
return false;
}
+#ifdef _ENABLE_MULTIPLE_OWNER_
+static bool IsSameEowner(OicUuid_t* eowner1, OicUuid_t* eowner2)
+{
+ if(NULL != eowner1 && NULL != eowner2)
+ {
+ if (memcmp(eowner1->id, eowner2->id, sizeof(eowner1->id)) == 0)
+ {
+ return true;
+ }
+ }
+
+ return false;
+}
+#endif
+
static bool IsSameACE(OicSecAce_t* ace1, OicSecAce_t* ace2)
{
if(ace1 && ace2)
return false;
}
+#ifdef _ENABLE_MULTIPLE_OWNER_
+ if(false == IsSameEowner(ace1->eownerID, ace2->eownerID))
+ {
+ return false;
+ }
+#endif
+
return true;
}
const CASecureEndpoint_t* authenticatedSubOwnerInfo = CAGetSecureEndpointData(object);
if(authenticatedSubOwnerInfo)
{
- OicSecSubOwner_t* subOwnerInst = (OicSecSubOwner_t*)OICMalloc(sizeof(OicSecSubOwner_t));
- if(subOwnerInst)
+ OicSecSubOwner_t* subOwnerInst = NULL;
+ LL_FOREACH(gDoxm->subOwners, subOwnerInst)
{
- OIC_LOG(DEBUG, TAG, "Adding New SubOwner");
- memcpy(subOwnerInst->uuid.id, authenticatedSubOwnerInfo->identity.id, authenticatedSubOwnerInfo->identity.id_length);
- LL_APPEND(gDoxm->subOwners, subOwnerInst);
- if(!UpdatePersistentStorage(gDoxm))
+ if(0 == memcmp(subOwnerInst->uuid.id,
+ authenticatedSubOwnerInfo->identity.id,
+ authenticatedSubOwnerInfo->identity.id_length))
{
- OIC_LOG(ERROR, TAG, "Failed to register SubOwner UUID into Doxm");
+ break;
+ }
+ }
+
+ if(NULL == subOwnerInst)
+ {
+ subOwnerInst = (OicSecSubOwner_t*)OICCalloc(1, sizeof(OicSecSubOwner_t));
+ if(subOwnerInst)
+ {
+ OIC_LOG(DEBUG, TAG, "Adding New SubOwner");
+ memcpy(subOwnerInst->uuid.id, authenticatedSubOwnerInfo->identity.id,
+ authenticatedSubOwnerInfo->identity.id_length);
+ LL_APPEND(gDoxm->subOwners, subOwnerInst);
+ if(!UpdatePersistentStorage(gDoxm))
+ {
+ OIC_LOG(ERROR, TAG, "Failed to register SubOwner UUID into Doxm");
+ }
}
}
}