From: Chul Lee Date: Wed, 8 Mar 2017 23:13:39 +0000 (+0900) Subject: Update PDM X-Git-Tag: 1.3.0~511 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=ffe4d951647e0d093d150e9c1dcacb6427378b6e;p=platform%2Fupstream%2Fiotivity.git Update PDM This patch addresses the following exceptional cases : 1. The PT terminates unexpectedly. - Start the OTM process - Device information will be changed to INIT state. - PT terminated while OTM. - Restart the PT process. - Retry the OTM process. * OTM start will be failed due to device info already save as INIT state. 2. Timeout is occured PT side while OTM. - Start the OTM process - Device information will be changed to INIT state. - OTM timeout is occured at the application side. - PT retry the OTM. * OTM start will be failed due to device info already save as INIT state. I've added defence code and added cleanup API that can be used when timeout occurs. Patch #1 : Initial upload Patch #2 : Retrigger Patch #3 : Fix the bug for incorrect PIN inputed while random PIN OxM. Patch #4-5 : Retrigger Patch #6 : minor bug fix Patch #7-8 : Retrigger Patch #9 : Fix the incorrect log Patch #10 : Retrigger Patch #12 : Retrigger Change-Id: I7781c0d864db6fdac93fa41acbcbf1ac123d15da Signed-off-by: Chul Lee Reviewed-on: https://gerrit.iotivity.org/gerrit/16187 Tested-by: jenkins-iotivity Reviewed-by: Randeep Singh Reviewed-on: https://gerrit.iotivity.org/gerrit/17309 --- diff --git a/resource/csdk/security/provisioning/include/internal/provisioningdatabasemanager.h b/resource/csdk/security/provisioning/include/internal/provisioningdatabasemanager.h index dd1801b..9e8fbec 100644 --- a/resource/csdk/security/provisioning/include/internal/provisioningdatabasemanager.h +++ b/resource/csdk/security/provisioning/include/internal/provisioningdatabasemanager.h @@ -114,6 +114,15 @@ OCStackResult PDMUnlinkDevices(const OicUuid_t *uuidOfDevice1, const OicUuid_t * OCStackResult PDMDeleteDevice(const OicUuid_t *uuidOfDevice); /** + * This method is used by OTM & PDM to remove device information with device state. + * + * @param[in] state device state to be removed. + * + * @return OC_STACK_OK in case of success and other value otherwise. + */ +OCStackResult PDMDeleteDeviceWithState(const PdmDeviceState_t state); + +/** * This method is used by provisioning manager to get owned devices' Device IDs. * * @param[out] uuidList information about the list of owned devices' uuids. diff --git a/resource/csdk/security/provisioning/include/ocprovisioningmanager.h b/resource/csdk/security/provisioning/include/ocprovisioningmanager.h index 9bc129b..1421f39 100644 --- a/resource/csdk/security/provisioning/include/ocprovisioningmanager.h +++ b/resource/csdk/security/provisioning/include/ocprovisioningmanager.h @@ -45,6 +45,14 @@ extern "C" { OCStackResult OCInitPM(const char* dbPath); /** + * API to cleanup PDM in case of timeout. + * It will remove the PDM_DEVICE_INIT state devices from PDM. + * + * @return OC_STACK_OK in case of success and other value otherwise. + */ +OCStackResult OCPDMCleanupForTimeout(); + +/** * The function is responsible for discovery of owned/unowned device is specified endpoint/deviceID. * It will return the found device even though timeout is not exceeded. * diff --git a/resource/csdk/security/provisioning/sample/provisioningclient.c b/resource/csdk/security/provisioning/sample/provisioningclient.c index 0824b2f..58fa2be 100644 --- a/resource/csdk/security/provisioning/sample/provisioningclient.c +++ b/resource/csdk/security/provisioning/sample/provisioningclient.c @@ -2261,6 +2261,11 @@ static int waitCallbackRet(void) } } + if(!g_doneCB) + { + OCPDMCleanupForTimeout(); + } + return 0; } diff --git a/resource/csdk/security/provisioning/sample/subownerclient.c b/resource/csdk/security/provisioning/sample/subownerclient.c index ef26f9c..e3e0a66 100644 --- a/resource/csdk/security/provisioning/sample/subownerclient.c +++ b/resource/csdk/security/provisioning/sample/subownerclient.c @@ -867,6 +867,11 @@ static int waitCallbackRet(void) } } + if(!g_doneCB) + { + OCPDMCleanupForTimeout(); + } + return 0; } diff --git a/resource/csdk/security/provisioning/src/ocprovisioningmanager.c b/resource/csdk/security/provisioning/src/ocprovisioningmanager.c index 31df69b..4adc3f6 100644 --- a/resource/csdk/security/provisioning/src/ocprovisioningmanager.c +++ b/resource/csdk/security/provisioning/src/ocprovisioningmanager.c @@ -81,6 +81,11 @@ OCStackResult OCInitPM(const char* dbPath) return PDMInit(dbPath); } +OCStackResult OCPDMCleanupForTimeout() +{ + return PDMDeleteDeviceWithState(PDM_DEVICE_INIT); +} + /** * The function is responsible for discovery of owned/unowned device is specified endpoint/deviceID. * And this function will only return the specified device's response. diff --git a/resource/csdk/security/provisioning/src/ownershiptransfermanager.c b/resource/csdk/security/provisioning/src/ownershiptransfermanager.c old mode 100755 new mode 100644 index 299496b..9c27e04 --- a/resource/csdk/security/provisioning/src/ownershiptransfermanager.c +++ b/resource/csdk/security/provisioning/src/ownershiptransfermanager.c @@ -333,6 +333,14 @@ static void SelectOperationMode(const OCProvisionDev_t *selectedDeviceInfo, */ static OCStackResult StartOwnershipTransfer(void* ctx, OCProvisionDev_t* selectedDevice); +/* + * Internal function to setup & cleanup PDM to performing provisioning. + * + * @param[in] selectedDevice selected device information to performing provisioning. + * @return OC_STACK_OK on success + */ +static OCStackResult SetupPDM(const OCProvisionDev_t* selectedDevice); + /** * Function to update owner transfer mode * @@ -656,6 +664,9 @@ static void OwnershipTransferSessionFailed(const CAEndpoint_t *endpoint, newDevDoxm->owned = false; otmCtx->attemptCnt++; + RemoveOTMContext(otmCtx->selectedDeviceInfo->endpoint.addr, + otmCtx->selectedDeviceInfo->securePort); + // In order to re-start ownership transfer, device information should be deleted from PDM. OCStackResult res = PDMDeleteDevice(&(otmCtx->selectedDeviceInfo->doxm->deviceID)); if (OC_STACK_OK != res) @@ -2109,84 +2120,131 @@ static OCStackResult GetAndVerifyDoxmResource(OTMContext_t* otmCtx) return res; } -static OCStackResult StartOwnershipTransfer(void* ctx, OCProvisionDev_t* selectedDevice) +static OCStackResult SetupPDM(const OCProvisionDev_t* selectedDevice) { - OIC_LOG(INFO, TAG, "IN StartOwnershipTransfer"); + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + + char* strUuid = NULL; OCStackResult res = OC_STACK_INVALID_PARAM; VERIFY_NOT_NULL(TAG, selectedDevice, ERROR); VERIFY_NOT_NULL(TAG, selectedDevice->doxm, ERROR); - OTMContext_t* otmCtx = (OTMContext_t*)ctx; - otmCtx->selectedDeviceInfo = selectedDevice; + PdmDeviceState_t pdmState = PDM_DEVICE_UNKNOWN; + res = PDMGetDeviceState(&selectedDevice->doxm->deviceID, &pdmState); + if (OC_STACK_OK != res) + { + OIC_LOG_V(ERROR, TAG, "Internal error in PDMGetDeviceState : %d", res); + return res; + } - //Checking duplication of Device ID. - bool isDuplicate = true; - res = PDMIsDuplicateDevice(&selectedDevice->doxm->deviceID, &isDuplicate); + bool removeCredReq = false; + res = ConvertUuidToStr(&selectedDevice->doxm->deviceID, &strUuid); if (OC_STACK_OK != res) { - OIC_LOG(ERROR, TAG, "Internal error in PDMIsDuplicateDevice"); + OIC_LOG(WARNING, TAG, "Failed to covert uuid to string"); return res; } - if (isDuplicate) + + if (PDM_DEVICE_UNKNOWN == pdmState && !selectedDevice->doxm->owned) + { + removeCredReq = true; + } + else if (PDM_DEVICE_ACTIVE == pdmState && !selectedDevice->doxm->owned) { - PdmDeviceState_t state = PDM_DEVICE_UNKNOWN; - res = PDMGetDeviceState(&selectedDevice->doxm->deviceID, &state); + OIC_LOG_V(WARNING, TAG, "Unowned device[%s] dectected from PDM.", strUuid); + OIC_LOG_V(WARNING, TAG, "[%s] will be removed from PDM.", strUuid); + res = PDMDeleteDevice(&selectedDevice->doxm->deviceID); if(OC_STACK_OK != res) { - OIC_LOG(ERROR, TAG, "Internal error in PDMGetDeviceState"); - SetResult(otmCtx, res); - return res; + OIC_LOG_V(ERROR, TAG, "Failed to remove [%s] information from PDM.", strUuid); + goto exit; } - char* strUuid = NULL; - res = ConvertUuidToStr(&selectedDevice->doxm->deviceID, &strUuid); - if(OC_STACK_OK != res) + removeCredReq = true; + } + + if (removeCredReq) + { + OIC_LOG_V(WARNING, TAG, "[%s]'s credential will be removed.", strUuid); + res = RemoveCredential(&selectedDevice->doxm->deviceID); + if (OC_STACK_RESOURCE_DELETED != res) { - OIC_LOG(ERROR, TAG, "Failed to convert UUID to str"); - SetResult(otmCtx, res); - return res; + OIC_LOG_V(WARNING, TAG, "Can not find [%s]'s credential.", strUuid); } + } - if(PDM_DEVICE_STALE == state) + //Checking duplication of Device ID. + bool isDuplicate = true; + res = PDMIsDuplicateDevice(&selectedDevice->doxm->deviceID, &isDuplicate); + if (OC_STACK_OK != res) + { + OIC_LOG_V(ERROR, TAG, "Internal error in PDMIsDuplicateDevice : %d", res); + goto exit; + } + + if (isDuplicate) + { + if (PDM_DEVICE_STALE == pdmState) { OIC_LOG(INFO, TAG, "Detected duplicated UUID in stale status, " "device status will revert back to initial status."); res = PDMSetDeviceState(&selectedDevice->doxm->deviceID, PDM_DEVICE_INIT); - if(OC_STACK_OK != res) + if (OC_STACK_OK != res) { - OIC_LOG(ERROR, TAG, "Internal error in PDMSetDeviceState"); - OICFree(strUuid); - SetResult(otmCtx, res); - return res; + OIC_LOG_V(ERROR, TAG, "Internal error in PDMSetDeviceState : %d", res); + goto exit; } } - else if(PDM_DEVICE_INIT == state) + else if (PDM_DEVICE_INIT == pdmState) { 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; + res = OC_STACK_DUPLICATE_REQUEST; + goto exit; } else { OIC_LOG(ERROR, TAG, "Unknow device status while OTM."); - OICFree(strUuid); - SetResult(otmCtx, OC_STACK_ERROR); - return OC_STACK_ERROR; + res = OC_STACK_ERROR; + goto exit; } } else { res = PDMAddDevice(&selectedDevice->doxm->deviceID); - if(OC_STACK_OK != res) + if (OC_STACK_OK != res) { - OIC_LOG(ERROR, TAG, "Internal error in PDMAddDevice"); - SetResult(otmCtx, res); - return res; + OIC_LOG_V(ERROR, TAG, "Internal error in PDMAddDevice : %d", res); + goto exit; } } +exit: + OICFree(strUuid); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); + return res; +} + +static OCStackResult StartOwnershipTransfer(void* ctx, OCProvisionDev_t* selectedDevice) +{ + OIC_LOG(INFO, TAG, "IN StartOwnershipTransfer"); + OCStackResult res = OC_STACK_INVALID_PARAM; + + VERIFY_NOT_NULL(TAG, selectedDevice, ERROR); + VERIFY_NOT_NULL(TAG, selectedDevice->doxm, ERROR); + + OTMContext_t* otmCtx = (OTMContext_t*)ctx; + otmCtx->selectedDeviceInfo = selectedDevice; + + //Setup PDM to perform the OTM, PDM will be cleanup if necessary. + res = SetupPDM(selectedDevice); + if(OC_STACK_OK != res) + { + OIC_LOG_V(ERROR, TAG, "SetupPDM error : %d", res); + SetResult(otmCtx, res); + return res; + } + //Select the OxM to performing ownership transfer res = OTMSelectOwnershipTransferMethod(selectedDevice->doxm->oxm, selectedDevice->doxm->oxmLen, @@ -2194,7 +2252,7 @@ static OCStackResult StartOwnershipTransfer(void* ctx, OCProvisionDev_t* selecte SUPER_OWNER); if(OC_STACK_OK != res) { - OIC_LOG(ERROR, TAG, "Failed to select the provisioning method"); + OIC_LOG_V(ERROR, TAG, "Failed to select the provisioning method : %d", res); SetResult(otmCtx, res); return res; } @@ -2219,7 +2277,7 @@ static OCStackResult StartOwnershipTransfer(void* ctx, OCProvisionDev_t* selecte res = PostOwnerTransferModeToResource(otmCtx); if(OC_STACK_OK != res) { - OIC_LOG(WARNING, TAG, "Failed to select the provisioning method"); + OIC_LOG_V(WARNING, TAG, "Failed to select the provisioning method : %d", res); SetResult(otmCtx, res); return res; } diff --git a/resource/csdk/security/provisioning/src/provisioningdatabasemanager.c b/resource/csdk/security/provisioning/src/provisioningdatabasemanager.c index 51e0b4d..608b0f3 100644 --- a/resource/csdk/security/provisioning/src/provisioningdatabasemanager.c +++ b/resource/csdk/security/provisioning/src/provisioningdatabasemanager.c @@ -94,7 +94,7 @@ PDM_VERIFY_STATEMENT_SIZE(PDM_SQLITE_DELETE_LINK); #define PDM_SQLITE_DELETE_DEVICE "DELETE FROM T_DEVICE_LIST WHERE ID = ?" #define PDM_SQLITE_DELETE_DEVICE_SIZE (int)sizeof(PDM_SQLITE_DELETE_DEVICE) PDM_VERIFY_STATEMENT_SIZE(PDM_SQLITE_DELETE_DEVICE); - +#define PDM_SQLITE_DELETE_DEVICE_WITH_STATE "DELETE FROM T_DEVICE_LIST WHERE STATE= ?" #define PDM_SQLITE_UPDATE_LINK "UPDATE T_DEVICE_LINK_STATE SET STATE = ? WHERE ID = ? and ID2 = ?" #define PDM_SQLITE_UPDATE_LINK_SIZE (int)sizeof(PDM_SQLITE_UPDATE_LINK) PDM_VERIFY_STATEMENT_SIZE(PDM_SQLITE_UPDATE_LINK); @@ -146,6 +146,7 @@ static bool gInit = false; /* Only if we can open sqlite db successfully, gInit */ static OCStackResult createDB(const char* path) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); int result = 0; result = sqlite3_open_v2(path, &g_db, SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE, NULL); @@ -160,6 +161,9 @@ static OCStackResult createDB(const char* path) OIC_LOG(INFO, TAG, "Created T_DEVICE_LINK_STATE"); gInit = true; + + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); + return OC_STACK_OK; } @@ -205,11 +209,13 @@ void errLogCallback(void *pArg, int iErrCode, const char *zMsg) (void) pArg; (void) iErrCode; (void) zMsg; - OIC_LOG_V(DEBUG,TAG, "(%d) %s", iErrCode, zMsg); + OIC_LOG_V(DEBUG,TAG, "%s : (%d) %s", __func__, iErrCode, zMsg); } OCStackResult PDMInit(const char *path) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + int rc; const char *dbPath = NULL; if (SQLITE_OK != sqlite3_config(SQLITE_CONFIG_LOG, errLogCallback, NULL)) @@ -232,12 +238,28 @@ OCStackResult PDMInit(const char *path) return createDB(dbPath); } gInit = true; + + /* + * Remove PDM_DEVICE_INIT status devices. + * PDM_DEVICE_INIT means that the OTM process is in progress. + * PDM_DEVICE_INIT state device can be existed when the program is terminated during the OTM process in progress. + * For this reason, PDM_DEVICE_INIT devices should be removed at PDM initialization time. + */ + if(OC_STACK_OK != PDMDeleteDeviceWithState(PDM_DEVICE_INIT)) + { + OIC_LOG_V(WARNING, TAG, "Failed to delete init state devices."); + } + + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); + return OC_STACK_OK; } OCStackResult PDMAddDevice(const OicUuid_t *UUID) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + CHECK_PDM_INIT(TAG); if (NULL == UUID) { @@ -271,6 +293,8 @@ OCStackResult PDMAddDevice(const OicUuid_t *UUID) return OC_STACK_ERROR; } sqlite3_finalize(stmt); + + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } @@ -279,6 +303,8 @@ OCStackResult PDMAddDevice(const OicUuid_t *UUID) */ static OCStackResult getIdForUUID(const OicUuid_t *UUID , int *id) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + sqlite3_stmt *stmt = 0; int res = 0; res = sqlite3_prepare_v2(g_db, PDM_SQLITE_GET_ID, PDM_SQLITE_GET_ID_SIZE, @@ -295,6 +321,7 @@ static OCStackResult getIdForUUID(const OicUuid_t *UUID , int *id) OIC_LOG_V(DEBUG, TAG, "ID is %d", tempId); *id = tempId; sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } sqlite3_finalize(stmt); @@ -306,6 +333,7 @@ static OCStackResult getIdForUUID(const OicUuid_t *UUID , int *id) */ OCStackResult PDMIsDuplicateDevice(const OicUuid_t* UUID, bool *result) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); CHECK_PDM_INIT(TAG); if (NULL == UUID || NULL == result) @@ -332,6 +360,8 @@ OCStackResult PDMIsDuplicateDevice(const OicUuid_t* UUID, bool *result) sqlite3_finalize(stmt); *result = retValue; + + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } @@ -340,6 +370,8 @@ OCStackResult PDMIsDuplicateDevice(const OicUuid_t* UUID, bool *result) */ static OCStackResult addlink(int id1, int id2) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + sqlite3_stmt *stmt = 0; int res = 0; res = sqlite3_prepare_v2(g_db, PDM_SQLITE_INSERT_LINK_DATA, @@ -362,11 +394,14 @@ static OCStackResult addlink(int id1, int id2) return OC_STACK_ERROR; } sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } OCStackResult PDMLinkDevices(const OicUuid_t *UUID1, const OicUuid_t *UUID2) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + CHECK_PDM_INIT(TAG); if (NULL == UUID1 || NULL == UUID2) { @@ -412,6 +447,7 @@ OCStackResult PDMLinkDevices(const OicUuid_t *UUID1, const OicUuid_t *UUID2) } ASCENDING_ORDER(id1, id2); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return addlink(id1, id2); } @@ -420,6 +456,8 @@ OCStackResult PDMLinkDevices(const OicUuid_t *UUID1, const OicUuid_t *UUID2) */ static OCStackResult removeLink(int id1, int id2) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + int res = 0; sqlite3_stmt *stmt = 0; res = sqlite3_prepare_v2(g_db, PDM_SQLITE_DELETE_LINK, @@ -439,11 +477,14 @@ static OCStackResult removeLink(int id1, int id2) return OC_STACK_ERROR; } sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } OCStackResult PDMUnlinkDevices(const OicUuid_t *UUID1, const OicUuid_t *UUID2) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + CHECK_PDM_INIT(TAG); if (NULL == UUID1 || NULL == UUID2) { @@ -465,11 +506,14 @@ OCStackResult PDMUnlinkDevices(const OicUuid_t *UUID1, const OicUuid_t *UUID2) return OC_STACK_INVALID_PARAM; } ASCENDING_ORDER(id1, id2); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return removeLink(id1, id2); } static OCStackResult removeFromDeviceList(int id) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + sqlite3_stmt *stmt = 0; int res = 0; res = sqlite3_prepare_v2(g_db, PDM_SQLITE_DELETE_DEVICE, @@ -486,11 +530,14 @@ static OCStackResult removeFromDeviceList(int id) return OC_STACK_ERROR; } sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } OCStackResult PDMDeleteDevice(const OicUuid_t *UUID) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + CHECK_PDM_INIT(TAG); if (NULL == UUID) { @@ -510,12 +557,15 @@ OCStackResult PDMDeleteDevice(const OicUuid_t *UUID) return OC_STACK_ERROR; } commit(); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } static OCStackResult updateLinkState(int id1, int id2, int state) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + sqlite3_stmt *stmt = 0; int res = 0 ; res = sqlite3_prepare_v2(g_db, PDM_SQLITE_UPDATE_LINK, @@ -538,11 +588,14 @@ static OCStackResult updateLinkState(int id1, int id2, int state) return OC_STACK_ERROR; } sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } OCStackResult PDMSetLinkStale(const OicUuid_t* uuidOfDevice1, const OicUuid_t* uuidOfDevice2) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + CHECK_PDM_INIT(TAG); if (NULL == uuidOfDevice1 || NULL == uuidOfDevice2) { @@ -564,11 +617,14 @@ OCStackResult PDMSetLinkStale(const OicUuid_t* uuidOfDevice1, const OicUuid_t* u return OC_STACK_INVALID_PARAM; } ASCENDING_ORDER(id1, id2); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return updateLinkState(id1, id2, PDM_DEVICE_STALE); } OCStackResult PDMGetOwnedDevices(OCUuidList_t **uuidList, size_t *numOfDevices) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + CHECK_PDM_INIT(TAG); if (NULL != *uuidList) { @@ -599,11 +655,14 @@ OCStackResult PDMGetOwnedDevices(OCUuidList_t **uuidList, size_t *numOfDevices) } *numOfDevices = counter; sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } static OCStackResult getUUIDforId(int id, OicUuid_t *uid, bool *result) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + sqlite3_stmt *stmt = 0; int res = 0; res = sqlite3_prepare_v2(g_db, PDM_SQLITE_GET_UUID, @@ -637,11 +696,14 @@ static OCStackResult getUUIDforId(int id, OicUuid_t *uid, bool *result) return OC_STACK_OK; } sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_INVALID_PARAM; } OCStackResult PDMGetLinkedDevices(const OicUuid_t *UUID, OCUuidList_t **UUIDLIST, size_t *numOfDevices) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + CHECK_PDM_INIT(TAG); if (NULL == UUID || NULL == numOfDevices || !UUIDLIST) { @@ -713,11 +775,14 @@ OCStackResult PDMGetLinkedDevices(const OicUuid_t *UUID, OCUuidList_t **UUIDLIST } *numOfDevices = counter; sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } OCStackResult PDMGetToBeUnlinkedDevices(OCPairList_t **staleDevList, size_t *numOfDevices) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + CHECK_PDM_INIT(TAG); if (NULL != *staleDevList) { @@ -758,20 +823,26 @@ OCStackResult PDMGetToBeUnlinkedDevices(OCPairList_t **staleDevList, size_t *num } *numOfDevices = counter; sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } OCStackResult PDMClose() { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + CHECK_PDM_INIT(TAG); int res = 0; res = sqlite3_close(g_db); PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } void PDMDestoryOicUuidLinkList(OCUuidList_t* ptr) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + if(ptr) { OCUuidList_t *tmp1 = NULL,*tmp2=NULL; @@ -781,10 +852,14 @@ void PDMDestoryOicUuidLinkList(OCUuidList_t* ptr) OICFree(tmp1); } } + + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); } void PDMDestoryStaleLinkList(OCPairList_t* ptr) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + if(ptr) { OCPairList_t *tmp1 = NULL,*tmp2=NULL; @@ -794,11 +869,15 @@ void PDMDestoryStaleLinkList(OCPairList_t* ptr) OICFree(tmp1); } } + + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); } OCStackResult PDMIsLinkExists(const OicUuid_t* uuidOfDevice1, const OicUuid_t* uuidOfDevice2, bool* result) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + CHECK_PDM_INIT(TAG); if (NULL == uuidOfDevice1 || NULL == uuidOfDevice2 || NULL == result) { @@ -864,11 +943,14 @@ OCStackResult PDMIsLinkExists(const OicUuid_t* uuidOfDevice1, const OicUuid_t* u } sqlite3_finalize(stmt); *result = ret; + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } static OCStackResult updateDeviceState(const OicUuid_t *uuid, PdmDeviceState_t state) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + sqlite3_stmt *stmt = 0; int res = 0 ; res = sqlite3_prepare_v2(g_db, PDM_SQLITE_UPDATE_DEVICE, @@ -888,11 +970,14 @@ static OCStackResult updateDeviceState(const OicUuid_t *uuid, PdmDeviceState_t s return OC_STACK_ERROR; } sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } static OCStackResult updateLinkForStaleDevice(const OicUuid_t *devUuid) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + sqlite3_stmt *stmt = 0; int res = 0 ; @@ -921,11 +1006,14 @@ static OCStackResult updateLinkForStaleDevice(const OicUuid_t *devUuid) return OC_STACK_ERROR; } sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } OCStackResult PDMSetDeviceState(const OicUuid_t* uuid, PdmDeviceState_t state) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + OCStackResult res = OC_STACK_ERROR; CHECK_PDM_INIT(TAG); @@ -955,11 +1043,14 @@ OCStackResult PDMSetDeviceState(const OicUuid_t* uuid, PdmDeviceState_t state) return res; } commit(); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } OCStackResult PDMGetDeviceState(const OicUuid_t *uuid, PdmDeviceState_t* result) { + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + if (NULL == uuid || NULL == result) { OIC_LOG(ERROR, TAG, "UUID or result is NULL"); @@ -983,6 +1074,37 @@ OCStackResult PDMGetDeviceState(const OicUuid_t *uuid, PdmDeviceState_t* result) *result = (PdmDeviceState_t)tempStaleStateFromDb; } sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); return OC_STACK_OK; } +OCStackResult PDMDeleteDeviceWithState(const PdmDeviceState_t state) +{ + OIC_LOG_V(DEBUG, TAG, "IN %s", __func__); + + CHECK_PDM_INIT(TAG); + if (PDM_DEVICE_ACTIVE != state && PDM_DEVICE_STALE != state && + PDM_DEVICE_INIT != state && PDM_DEVICE_UNKNOWN != state) + { + return OC_STACK_INVALID_PARAM; + } + + sqlite3_stmt *stmt = 0; + int res =0; + res = sqlite3_prepare_v2(g_db, PDM_SQLITE_DELETE_DEVICE_WITH_STATE, + (int)strlen(PDM_SQLITE_DELETE_DEVICE_WITH_STATE) + 1, &stmt, NULL); + PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR); + + res = sqlite3_bind_int(stmt, PDM_BIND_INDEX_FIRST, state); + PDM_VERIFY_SQLITE_OK(TAG, res, ERROR, OC_STACK_ERROR); + + if (SQLITE_DONE != sqlite3_step(stmt)) + { + OIC_LOG_V(ERROR, TAG, "Error message: %s", sqlite3_errmsg(g_db)); + sqlite3_finalize(stmt); + return OC_STACK_ERROR; + } + sqlite3_finalize(stmt); + OIC_LOG_V(DEBUG, TAG, "OUT %s", __func__); + return OC_STACK_OK; +} diff --git a/resource/csdk/stack/octbstack_product_secured.def b/resource/csdk/stack/octbstack_product_secured.def index 642856d..aa4f1a7 100644 --- a/resource/csdk/stack/octbstack_product_secured.def +++ b/resource/csdk/stack/octbstack_product_secured.def @@ -28,6 +28,7 @@ OCGetCredResource OCGetDevInfoFromNetwork OCGetLinkedStatus OCInitPM +OCPDMCleanupForTimeout OCProvisionACL OCSaveACL OCProvisionCredentials diff --git a/resource/include/OCProvisioningManager.hpp b/resource/include/OCProvisioningManager.hpp index 0f1ab4d..f7f6bb3 100644 --- a/resource/include/OCProvisioningManager.hpp +++ b/resource/include/OCProvisioningManager.hpp @@ -486,6 +486,14 @@ namespace OC static OCStackResult setVerifyOptionMask(VerifyOptionBitmask_t optionMask); + /** + * API to cleanup PDM in case of timeout. + * It will remove the PDM_DEVICE_INIT state devices from PDM. + * + * @return OC_STACK_OK in case of success and other value otherwise. + */ + static OCStackResult pdmCleanupForTimeout(); + #if defined(__WITH_DTLS__) || defined(__WITH_TLS__) /** * API to save Trust certificate chain into Cred of SVR. diff --git a/resource/provisioning/src/OCProvisioningManager.cpp b/resource/provisioning/src/OCProvisioningManager.cpp index 73e0b3c..8362831 100644 --- a/resource/provisioning/src/OCProvisioningManager.cpp +++ b/resource/provisioning/src/OCProvisioningManager.cpp @@ -971,6 +971,23 @@ namespace OC return result; } + OCStackResult OCSecure::pdmCleanupForTimeout() + { + OCStackResult result; + auto cLock = OCPlatform_impl::Instance().csdkLock().lock(); + + if (cLock) + { + result = OCPDMCleanupForTimeout(); + } + 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,