#include <stdio.h>
#include <string.h>
#include <unistd.h>
-#include <getopt.h>
+
#include "logger.h"
#include "oic_malloc.h"
#include "utlist.h"
-#include "securevirtualresourcetypes.h"
-#include "provisioningmanager.h"
+#include "ocprovisioningmanager.h"
+#include "secureresourceprovider.h"
+#include "oxmjustworks.h"
+#include "oxmrandompin.h"
+#include "pinoxmcommon.h"
+#include "oic_string.h"
#define MAX_URI_LENGTH (64)
#define MAX_PERMISSION_LENGTH (5)
-#define MAX_INPUT_ID_LENGTH (16)
-#define PREDEFINED_TIMEOUT (10)
#define CREATE (1)
#define READ (2)
#define UPDATE (4)
#define DELETE (8)
#define NOTIFY (16)
#define DASH '-'
+#define PREDEFINED_TIMEOUT (10)
+#define MAX_OWNED_DEVICE (10)
#define TAG "provisioningclient"
-static OicSecAcl_t *gAcl = NULL;
-static char PROV_TOOL_DB_FILE[] = "oic_svr_db_prov_tool.json";
+static char CRED_FILE[] = "oic_svr_db_client.json";
+static OicSecAcl_t *gAcl1 = NULL;
+static OicSecAcl_t *gAcl2 = NULL;
+static int gOwnershipState = 0;
+
+typedef enum
+{
+ ownershipDone = 1 << 1,
+ finalizeDone = 1 << 2,
+ provisionCredDone = 1 << 3,
+ provisionAclDone = 1 << 4
+} StateManager;
+
/**
- * Perform cleanup for ACL list
- *
- * @param[in] ACL list
+ * Perform cleanup for ACL
+ * @param[in] ACL
*/
-static void DeleteACLList(OicSecAcl_t *acl)
+static void deleteACL(OicSecAcl_t *acl)
{
if (acl)
{
- OicSecAcl_t *aclTmp1 = NULL;
- OicSecAcl_t *aclTmp2 = NULL;
- LL_FOREACH_SAFE(acl, aclTmp1, aclTmp2)
+ /* Clean Resources */
+ for (size_t i = 0; i < (acl)->resourcesLen; i++)
{
- LL_DELETE(acl, aclTmp1);
+ OICFree((acl)->resources[i]);
+ }
+ OICFree((acl)->resources);
- /* Clean Resources */
- for (int i = 0; i < aclTmp1->resourcesLen; i++)
- {
- OICFree(aclTmp1->resources[i]);
- }
- OICFree(aclTmp1->resources);
+ /* Clean Owners */
+ OICFree((acl)->owners);
- /* Clean Owners */
- OICFree(aclTmp1->owners);
+ /* Clean ACL node itself */
+ OICFree((acl));
- /* Clean ACL node itself */
- OICFree(aclTmp1);
- }
acl = NULL;
}
}
*
* @param[in] temp_psm Input data of ACL permission string
* @param[in,out] pms The pointer of ACL permission value
- * @return 0 on success otherwise a positive error value
- * @retval SP_RESULT_SUCCESS Successful
- * @retval SP_RESULT_INVALID_PARAM Invaild input arguments
+ * @return 0 on success otherwise -1.
*/
-static SPResult CalculateAclPermission(const char *temp_pms, uint16_t *pms)
+static int CalculateAclPermission(const char *temp_pms, uint16_t *pms)
{
int i = 0;
if (NULL == temp_pms || NULL == pms)
{
- return SP_RESULT_INVALID_PARAM;
+ return -1;
}
*pms = 0;
while (temp_pms[i] != '\0')
}
default:
{
- return SP_RESULT_INVALID_PARAM;
+ return -1;
}
}
}
- return SP_RESULT_SUCCESS;
+ return 0;
}
/**
* Get the ACL property from user
*
* @param[in] ACL Datastructure to save user inputs
- * @return 0 on success otherwise a positive error value
- * @retval SP_RESULT_SUCCESS Successful
- * @retval SP_RESULT_MEM_ALLOCATION_FAIL Memmory allocation failure
+ * @return 0 on success otherwise -1.
*/
-static SPResult InputACL(OicSecAcl_t *acl)
+static int InputACL(OicSecAcl_t *acl)
{
- int unused __attribute__((unused));
- char temp_id [MAX_INPUT_ID_LENGTH + 4] = {0,};
+ int ret;
+ char temp_id [UUID_LENGTH + 4] = {0,};
char temp_rsc[MAX_URI_LENGTH + 1] = {0,};
char temp_pms[MAX_PERMISSION_LENGTH + 1] = {0,};
printf("******************************************************************************\n");
printf("-URN identifying the subject\n");
printf("ex) 1111-1111-1111-1111 (16 Numbers except to '-')\n");
printf("Subject : ");
- unused = scanf("%19s", temp_id);
+ char *ptr = NULL;
+ ret = scanf("%19ms", &ptr);
+ if(1==ret)
+ {
+ OICStrcpy(temp_id, sizeof(temp_id), ptr);
+ OICFree(ptr);
+ }
+ else
+ {
+ printf("Error while input\n");
+ return -1;
+ }
int j = 0;
for (int i = 0; temp_id[i] != '\0'; i++)
{
if (DASH != temp_id[i])
+ {
+ if(j>UUID_LENGTH)
+ {
+ printf("Invalid input\n");
+ return -1;
+ }
acl->subject.id[j++] = temp_id[i];
+ }
}
//Set Resource.
- printf("Num. of Resource : ");
- unused = scanf("%zu", &acl->resourcesLen);
+ printf("Num. of Resource : \n");
+ ret = scanf("%zu", &acl->resourcesLen);
printf("-URI of resource\n");
printf("ex)/oic/sh/temp/0 (Max_URI_Length: 64 Byte )\n");
- acl->resources = (char **)OICMalloc(acl->resourcesLen * sizeof(char *));
+ acl->resources = (char **)OICCalloc(acl->resourcesLen, sizeof(char *));
if (NULL == acl->resources)
{
OC_LOG(ERROR, TAG, "Error while memory allocation");
- return SP_RESULT_MEM_ALLOCATION_FAIL;
+ return -1;
}
- for (int i = 0; i < acl->resourcesLen; i++)
+ for (size_t i = 0; i < acl->resourcesLen; i++)
{
- printf("[%d]Resource : ", i + 1);
- unused = scanf("%64s", temp_rsc);
- acl->resources[i] = (char *)OICMalloc((strlen(temp_rsc) + 1) * sizeof(char));
+ printf("[%zu]Resource : ", i + 1);
+ char *ptr_tempRsc = NULL;
+ ret = scanf("%64ms", &ptr_tempRsc);
+ if (1==ret)
+ {
+ OICStrcpy(temp_rsc, sizeof(temp_rsc), ptr_tempRsc);
+ OICFree(ptr_tempRsc);
+ }
+ else
+ {
+ printf("Error while input\n");
+ return -1;
+ }
+ acl->resources[i] = OICStrdup(temp_rsc);
+
if (NULL == acl->resources[i])
{
OC_LOG(ERROR, TAG, "Error while memory allocation");
- return SP_RESULT_MEM_ALLOCATION_FAIL;
+ return -1;
}
- strncpy(acl->resources[i], temp_rsc, strlen(temp_rsc));
- acl->resources[i][strlen(temp_rsc)] = '\0';
}
// Set Permission
do
printf("-Set the permission(C,R,U,D,N)\n");
printf("ex) CRUDN, CRU_N,..(5 Charaters)\n");
printf("Permission : ");
- unused = scanf("%5s", temp_pms);
+ char *ptr_temp_pms = NULL;
+ ret = scanf("%5ms", &ptr_temp_pms);
+ if(1 == ret)
+ {
+ OICStrcpy(temp_pms, sizeof(temp_pms), ptr_temp_pms);
+ OICFree(ptr_temp_pms);
+
+ }
+ else
+ {
+ printf("Error while input\n");
+ return -1;
+ }
}
- while (SP_RESULT_SUCCESS != CalculateAclPermission(temp_pms, &(acl->permission)) );
+ while (0 != CalculateAclPermission(temp_pms, &(acl->permission)) );
// Set Rowner
printf("Num. of Rowner : ");
- unused = scanf("%zu", &acl->ownersLen);
+ ret = scanf("%zu", &acl->ownersLen);
printf("-URN identifying the rowner\n");
printf("ex) 1111-1111-1111-1111 (16 Numbers except to '-')\n");
acl->owners = (OicUuid_t *)OICCalloc(acl->ownersLen, sizeof(OicUuid_t));
if (NULL == acl->owners)
{
OC_LOG(ERROR, TAG, "Error while memory allocation");
- return SP_RESULT_MEM_ALLOCATION_FAIL;
+ return -1;
}
- for (int i = 0; i < acl->ownersLen; i++)
+ for (size_t i = 0; i < acl->ownersLen; i++)
{
- printf("[%d]Rowner : ", i + 1);
- unused = scanf("%19s", temp_id);
+ printf("[%zu]Rowner : ", i + 1);
+ char *ptr_temp_id = NULL;
+ ret = scanf("%19ms", &ptr_temp_id);
+ if (1 == ret)
+ {
+ OICStrcpy(temp_id, sizeof(temp_id), ptr_temp_id);
+ OICFree(ptr_temp_id);
+ }
+ else
+ {
+ printf("Error while input\n");
+ return -1;
+ }
j = 0;
for (int k = 0; temp_id[k] != '\0'; k++)
{
}
}
}
- return SP_RESULT_SUCCESS;
+ return 0;
+}
+
+
+//FILE *client_fopen(const char *path, const char *mode)
+FILE *client_fopen(const char* UNUSED_PARAM , const char *mode)
+{
+ (void)UNUSED_PARAM;
+ return fopen(CRED_FILE, mode);
+}
+
+void PrintfResult(const char* procName, void* ctx, int nOfRes, OCProvisionResult_t *arr, bool hasError)
+{
+ printf("-----------------------------------------------------------\n");
+ if(!hasError)
+ {
+ printf("%s was successfully done.\n", procName);
+ }
+ else
+ {
+ for(int i = 0; i < nOfRes; i++)
+ {
+ printf("UUID : ");
+ for(int j = 0; j < UUID_LENGTH; i++)
+ {
+ printf("%c", arr[i].deviceId.id[j]);
+ }
+ printf("\t");
+ printf("Result=%d\n", arr[i].res);
+ }
+ }
+
+ if(ctx)
+ {
+ printf("Context is %s\n", (char*)ctx);
+ }
+ printf("-----------------------------------------------------------\n");
+}
+
+void ProvisionCredCB(void* ctx, int nOfRes, OCProvisionResult_t *arr, bool hasError)
+{
+ if(!hasError)
+ {
+ gOwnershipState = 1;
+ PrintfResult("Provision Credential", ctx, nOfRes, arr, hasError);
+ }
+}
+
+void ProvisionAclCB(void* ctx, int nOfRes, OCProvisionResult_t *arr, bool hasError)
+{
+ if(!hasError)
+ {
+ gOwnershipState = 1;
+ PrintfResult("Provision ACL", ctx, nOfRes, arr, hasError);
+ }
}
-FILE* client_fopen(const char *path, const char *mode)
+void ProvisionPairwiseCB(void* ctx, int nOfRes, OCProvisionResult_t *arr, bool hasError)
{
- (void)path;
- return fopen(PROV_TOOL_DB_FILE, mode);
+ if(!hasError)
+ {
+ gOwnershipState = 1;
+ PrintfResult("Provision Pairwise Credential", ctx, nOfRes, arr, hasError);
+ }
+}
+
+void OwnershipTransferCB(void* ctx, int nOfRes, OCProvisionResult_t *arr, bool hasError)
+{
+ if(!hasError)
+ {
+ gOwnershipState = 1;
+ PrintfResult("Ownership transfer", ctx, nOfRes, arr, hasError);
+ }
+}
+
+void InputPinCB(char* pinBuf, size_t bufSize)
+{
+ if(pinBuf)
+ {
+ printf("INPUT PIN : ");
+ char *ptr = NULL;
+ int ret = scanf("%ms", &ptr);
+ if(1 == ret)
+ {
+ OICStrcpy(pinBuf, bufSize, ptr);
+ OICFree(ptr);
+ }
+ else
+ {
+ printf("Error in input\n");
+ return;
+ }
+ }
}
/**
- * Provisioning client sample using ProvisioningAPI on provisioningmanager.c
- * To change network type use command line option -w for Wifi and -e for Ethernet
+ * Provisioning client sample using ProvisioningAPI
*/
-int main(int argc, char **argv)
+int main()
{
- SPResult res = SP_RESULT_SUCCESS;
- SPTargetDeviceInfo_t *pDeviceList = NULL;
- gAcl = (OicSecAcl_t *)OICMalloc(sizeof(OicSecAcl_t));
+ OCStackResult res = OC_STACK_OK;
+ int unused;
+ (void)unused;
// Initialize Persistent Storage for SVR database
- OCPersistentStorage ps = {};
+ OCPersistentStorage ps = { .open = NULL,
+ .read = NULL,
+ .write = NULL,
+ .close = NULL,
+ .unlink = NULL };
ps.open = client_fopen;
ps.read = fread;
ps.write = fwrite;
ps.unlink = unlink;
OCRegisterPersistentStorageHandler(&ps);
- if (OCInit(NULL, 0, OC_CLIENT_SERVER) != OC_STACK_OK)
+ if (OC_STACK_OK != OCInit(NULL, 0, OC_CLIENT_SERVER))
{
OC_LOG(ERROR, TAG, "OCStack init error");
- return 0;
+ goto error;
}
- if (NULL == gAcl)
+ OCProvisionDev_t* pDeviceList = NULL;
+ res = OCDiscoverUnownedDevices(PREDEFINED_TIMEOUT, &pDeviceList);
+ if(OC_STACK_OK != res)
{
- OC_LOG(ERROR, TAG, "Error while memory allocation");
- return SP_RESULT_MEM_ALLOCATION_FAIL;
+ OC_LOG_V(ERROR, TAG, "Failed to PMDeviceDiscovery : %d", res);
+ goto error;
+ }
+
+ OCProvisionDev_t* pCurDev = pDeviceList;
+ int i;
+ while(pCurDev !=NULL)
+ {
+ for(i = 0; i < UUID_LENGTH; i++)
+ printf("%c", pCurDev->doxm->deviceID.id[i]);
+ printf("\n");
+ pCurDev = pCurDev->next;
+ }
+
+ //Register callback function to each OxM
+ OTMCallbackData_t justWorksCBData = {.loadSecretCB=NULL,
+ .createSecureSessionCB=NULL,
+ .createSelectOxmPayloadCB=NULL,
+ .createOwnerTransferPayloadCB=NULL};
+ justWorksCBData.loadSecretCB = LoadSecretJustWorksCallback;
+ justWorksCBData.createSecureSessionCB = CreateSecureSessionJustWorksCallback;
+ justWorksCBData.createSelectOxmPayloadCB = CreateJustWorksSelectOxmPayload;
+ justWorksCBData.createOwnerTransferPayloadCB = CreateJustWorksOwnerTransferPayload;
+ OTMSetOwnershipTransferCallbackData(OIC_JUST_WORKS, &justWorksCBData);
+
+ OTMCallbackData_t pinBasedCBData = {.loadSecretCB=NULL,
+ .createSecureSessionCB=NULL,
+ .createSelectOxmPayloadCB=NULL,
+ .createOwnerTransferPayloadCB=NULL};
+ pinBasedCBData.loadSecretCB = InputPinCodeCallback;
+ pinBasedCBData.createSecureSessionCB = CreateSecureSessionRandomPinCallbak;
+ pinBasedCBData.createSelectOxmPayloadCB = CreatePinBasedSelectOxmPayload;
+ pinBasedCBData.createOwnerTransferPayloadCB = CreatePinBasedOwnerTransferPayload;
+ OTMSetOwnershipTransferCallbackData(OIC_RANDOM_DEVICE_PIN, &pinBasedCBData);
+
+ SetInputPinCB(&InputPinCB);
+
+ char* myContext = "OTM Context";
+ //Perform ownership transfer
+ res = OCDoOwnershipTransfer((void*)myContext, pDeviceList, OwnershipTransferCB);
+ if(OC_STACK_OK == res)
+ {
+ OC_LOG(INFO, TAG, "Request for ownership transfer is sent successfully.");
+ }
+ else
+ {
+ OC_LOG_V(ERROR, TAG, "Failed to OCDoOwnershipTransfer : %d", res);
+ }
+
+ gOwnershipState = 0;
+ while ( gOwnershipState == 0 )
+ {
+ if (OCProcess() != OC_STACK_OK)
+ {
+ OC_LOG(ERROR, TAG, "OCStack process error");
+ goto error;
+ }
+ sleep(1);
}
- res = SPProvisioningDiscovery(PREDEFINED_TIMEOUT, &pDeviceList);
- if (SP_RESULT_SUCCESS == res)
+// Credential & ACL provisioning between two devices.
+
+ OCProvisionDev_t *pOwnedList = NULL;
+ OCProvisionDev_t *pOwnedDevices [MAX_OWNED_DEVICE] = {0,};
+ int nOwnedDevice = 0;
+
+ res = OCDiscoverOwnedDevices(PREDEFINED_TIMEOUT, &pOwnedList);
+ if (OC_STACK_OK == res)
{
- while (pDeviceList != NULL)
+ printf("################## Owned Device List #######################\n");
+ while (pOwnedList != NULL)
{
- printf("-Provisioning device ID : ");
- for (int i = 0; i < MAX_INPUT_ID_LENGTH; i++)
+ nOwnedDevice ++;
+ printf(" %d : ", nOwnedDevice);
+ for (int i = 0; i < UUID_LENGTH; i++)
{
- if (pDeviceList->doxm->deviceID.id[i] == '\0')
- {
- break;
- }
- printf("%c", pDeviceList->doxm->deviceID.id[i]);
+ printf("%c", pOwnedList->doxm->deviceID.id[i]);
}
printf("\n");
- res = SPInitProvisionContext(PREDEFINED_TIMEOUT, pDeviceList);
- if (SP_RESULT_SUCCESS != res)
- {
- OC_LOG(ERROR, TAG, "Error while init provisioning Context");
- goto error;
- }
- res = InputACL(gAcl);
- if (SP_RESULT_SUCCESS != res)
- {
- OC_LOG(ERROR, TAG, "Error while user ACL input ");
- goto error;
- }
- res = SPProvisionACL(PREDEFINED_TIMEOUT, pDeviceList, gAcl);
- if (SP_RESULT_SUCCESS != res)
- {
- OC_LOG(ERROR, TAG, "Error while provisioning ACL");
- goto error;
- }
- res = SPFinalizeProvisioning(PREDEFINED_TIMEOUT, pDeviceList);
- if (SP_RESULT_SUCCESS == res)
- {
- printf("Provisioning Success~!!\n");
- }
- else if (SP_RESULT_SUCCESS != res)
- {
- OC_LOG(ERROR, TAG, "Error while Finalize Provisioning");
- goto error;
- }
- pDeviceList = pDeviceList->next;
+ pOwnedDevices[nOwnedDevice] = pOwnedList;
+ pOwnedList = pOwnedList->next;
}
}
else
{
- OC_LOG(ERROR, TAG, "Error while Provisioning Discovery");
+ OC_LOG(ERROR, TAG, "Error while Owned Device Discovery");
+ }
+
+ int Device1 = 0;
+ int Device2 = 0;
+
+ printf("Select 2 devices for Credential & ACL provisioning\n");
+ printf("Device 1: ");
+ unused = scanf("%d", &Device1);
+ printf("Device 2: ");
+ unused = scanf("%d", &Device2);
+
+
+ gAcl1 = (OicSecAcl_t *)OICCalloc(1,sizeof(OicSecAcl_t));
+ if (NULL == gAcl1)
+ {
+ OC_LOG(ERROR, TAG, "Error while memory allocation");
+ goto error;
+ }
+
+ gAcl2 = (OicSecAcl_t *)OICCalloc(1,sizeof(OicSecAcl_t));
+ if (NULL == gAcl2)
+ {
+ OC_LOG(ERROR, TAG, "Error while memory allocation");
+ goto error;
+ }
+
+ printf("Input ACL for Device1\n");
+ if ( 0 == InputACL(gAcl1))
+ {
+ printf("Success Input ACL\n");
+ }
+ else
+ {
+ OC_LOG(ERROR, TAG, "InputACL error");
+ goto error;
+ }
+
+ printf("Input ACL for Device2\n");
+ if (0 == InputACL(gAcl2))
+ {
+ printf("Success Input ACL\n");
+ }
+ else
+ {
+ OC_LOG(ERROR, TAG, "InputACL error");
+ goto error;
+ }
+ char *ctx = "DUMMY";
+ OCProvisionPairwiseDevices(ctx,SYMMETRIC_PAIR_WISE_KEY, OWNER_PSK_LENGTH_128, pOwnedDevices[Device1],
+ gAcl1, pOwnedDevices[Device2], gAcl2, ProvisionPairwiseCB);
+
+ gOwnershipState = 0;
+ while ( gOwnershipState == 0 )
+ {
+ if (OCProcess() != OC_STACK_OK)
+ {
+ OC_LOG(ERROR, TAG, "OCStack process error");
+ goto error;
+ }
+ sleep(1);
+ }
+
+ if (OCStop() != OC_STACK_OK)
+ {
+ OC_LOG(ERROR, TAG, "OCStack process error");
goto error;
}
error:
- DeleteACLList(gAcl);
- SPTerminateProvisioning();
+ deleteACL(gAcl1);
+ deleteACL(gAcl2);
+ OCDeleteDiscoveredDevices(&pDeviceList);
+ OCDeleteDiscoveredDevices(&pOwnedList);
+
return 0;
}