#include <string.h>
#include <signal.h>
#include <unistd.h>
-
+#include "ocpayload.h"
#include "provisioninghandler.h"
-
+#include "common.h"
// External includes
-#include "cJSON.h"
+
#include "camutex.h"
#include "cathreadpool.h"
#include "logger.h"
#include "oic_malloc.h"
-
/**
* @var g_provisioningMutex
* @brief Mutex to synchronize access to g_caDtlsContext.
static OCProvisioningStatusCB cbData = NULL;
static ca_thread_pool_t g_threadPoolHandle = NULL;
-OCStackResult InitProvisioningHandler() {
+void ErrorCallback(ProvStatus status)
+{
+ ProvisioningInfo *provInfo = GetCallbackObjectOnError(status);
+ cbData(provInfo);
+ ResetProgress();
+}
+
+OCStackResult InitProvisioningHandler()
+{
OCStackResult ret = OC_STACK_ERROR;
/* Initialize OCStack*/
- if (OCInit(NULL, 0, OC_CLIENT) != OC_STACK_OK) {
+ if (OCInit(NULL, 0, OC_CLIENT) != OC_STACK_OK)
+ {
OIC_LOG(ERROR, TAG, "OCStack init error");
return ret;
}
OIC_LOG(DEBUG, TAG, "ca_thread_pool_init initializing");
- if (CA_STATUS_OK != ca_thread_pool_init(2, &g_threadPoolHandle)) {
+ if (CA_STATUS_OK != ca_thread_pool_init(2, &g_threadPoolHandle))
+ {
OIC_LOG(DEBUG, TAG, "thread_pool_init failed");
return OC_STACK_ERROR;
}
g_provisioningCond = ca_cond_new();
- if (NULL == g_provisioningCond) {
+ if (NULL == g_provisioningCond)
+ {
OIC_LOG(DEBUG, TAG, "Failed to create condition");
ca_mutex_free(g_provisioningMutex);
ca_thread_pool_free(g_threadPoolHandle);
}
char *string = "listeningFunc invoked in a thread";
- if (CA_STATUS_OK
- != ca_thread_pool_add_task(g_threadPoolHandle, listeningFunc,
- (void *) string)) {
+ if (CA_STATUS_OK != ca_thread_pool_add_task(g_threadPoolHandle, listeningFunc, (void *) string))
+ {
OIC_LOG(DEBUG, TAG, "thread_pool_add_task failed");
ca_thread_pool_free(g_threadPoolHandle);
ca_mutex_unlock(g_provisioningMutex);
ca_cond_free(g_provisioningCond);
return OC_STACK_ERROR;
}
+
+ ResetProgress();
+
return OC_STACK_OK;
}
-OCStackResult TerminateProvisioningHandler() {
+OCStackResult TerminateProvisioningHandler()
+{
OCStackResult ret = OC_STACK_ERROR;
- if (OCStop() != OC_STACK_OK) {
+ if (OCStop() != OC_STACK_OK)
+ {
OIC_LOG(ERROR, TAG, "OCStack stop error");
}
return ret;
}
-void listeningFunc(void *data) {
- while (!g_provisioningCondFlag) {
+void listeningFunc(void *data)
+{
+ while (!g_provisioningCondFlag)
+ {
OCStackResult result;
ca_mutex_lock(g_provisioningMutex);
result = OCProcess();
ca_mutex_unlock(g_provisioningMutex);
- if (result != OC_STACK_OK) {
+ if (result != OC_STACK_OK)
+ {
OIC_LOG(ERROR, TAG, "OCStack stop error");
}
}
OCStackApplicationResult ProvisionEnrolleeResponse(void* ctx, OCDoHandle handle,
- OCClientResponse * clientResponse) {
- ProvisioningInfo provInfo;
-
- if (clientResponse) {
- OIC_LOG_V(INFO, TAG, "Put Response JSON = %s",
- clientResponse->resJSONPayload);
- } else {
- OIC_LOG_V(INFO, TAG,
- "ProvisionEnrolleeResponse received Null clientResponse");
- PrepareProvisioingStatusCB(&provInfo, clientResponse,
- DEVICE_NOT_PROVISIONED);
- cbData(provInfo);
+ OCClientResponse * clientResponse)
+{
+
+ ProvisioningInfo *provInfo;
+
+ if (!ValidateEnrolleResponse(clientResponse))
+ {
+ ErrorCallback( DEVICE_NOT_PROVISIONED);
return OC_STACK_DELETE_TRANSACTION;
}
- uint16_t remotePortNum;
-
- OCDevAddrToPort((OCDevAddr *) clientResponse->addr, &remotePortNum);
+ char* tnn;
+ char* cd;
- char sourceaddr[OIC_STRING_MAX_VALUE] = { '\0' };
- snprintf(sourceaddr, sizeof(sourceaddr), "%d.%d.%d.%d:%d%s",
- clientResponse->addr->addr[0], clientResponse->addr->addr[1],
- clientResponse->addr->addr[2], clientResponse->addr->addr[3],
- remotePortNum, OIC_PROVISIONING_URI);
+ OCRepPayload* input = (OCRepPayload*) (clientResponse->payload);
- OIC_LOG_V(DEBUG, TAG, "ProvisionEnrolleeResponse %s @ %s",
- clientResponse->resJSONPayload, sourceaddr);
+ while (input)
+ {
- if (clientResponse->resJSONPayload) {
- cJSON *observeJson = cJSON_CreateObject();
- observeJson = cJSON_Parse(clientResponse->resJSONPayload);
+ int64_t ps;
+ if (OCRepPayloadGetPropInt(input, OC_RSRVD_ES_PS, &ps))
+ {
- cJSON *ocArray = cJSON_GetObjectItem(observeJson, "oic");
- cJSON *ocArray_sub = cJSON_GetArrayItem(ocArray, 0);
+ if (ps == 1)
+ {
+ OIC_LOG_V(DEBUG, TAG, "PS is proper");
+ input = input->next;
+ continue;
+ }
+ else
+ {
+ OIC_LOG_V(DEBUG, TAG, "PS is NOT proper");
+ goto Error;
- cJSON *representationArray = cJSON_GetObjectItem(ocArray_sub, "rep");
- char *ocArray_str = cJSON_PrintUnformatted(representationArray);
+ }
+ }
- if (strstr(ocArray_str, "[{}") == ocArray_str) {
- OIC_LOG_V(DEBUG, TAG, "invalid payload : %s", ocArray_str);
- cJSON_Delete(observeJson);
- return OC_STACK_DELETE_TRANSACTION;
+ if (OCRepPayloadGetPropString(input, OC_RSRVD_ES_TNN, &tnn))
+ {
+ if (!strcmp(tnn, netProvInfo->netAddressInfo.WIFI.ssid))
+ {
+ OIC_LOG_V(DEBUG, TAG, "SSID is proper");
+ input = input->next;
+ continue;
+ }
+ else
+ {
+ OIC_LOG_V(DEBUG, TAG, "SSID is NOT proper");
+ goto Error;
+ }
}
- int countofrep = cJSON_GetArraySize(representationArray);
-
- for (int i = 0; i < countofrep; ++i) {
- cJSON *arrayJSON = cJSON_GetArrayItem(representationArray, i);
- OIC_LOG_V(DEBUG, TAG, "rep#%d's name : %s", i, arrayJSON->string);
-
- switch (arrayJSON->type) {
- case cJSON_False:
- case cJSON_True:
- OIC_LOG_V(DEBUG, TAG, "rep#%d's value : %d", i,
- arrayJSON->valueint);
- break;
- case cJSON_Number:
- OIC_LOG_V(DEBUG, TAG, "rep#%d's value : %f", i,
- arrayJSON->valuedouble);
- break;
- case cJSON_String:
- OIC_LOG_V(DEBUG, TAG, "rep#%d's value : %s", i,
- arrayJSON->valuestring);
- break;
- case cJSON_NULL:
- default:
- OIC_LOG_V(DEBUG, TAG, "rep#%d's value : NULL", i);
- break;
+ if (OCRepPayloadGetPropString(input, OC_RSRVD_ES_CD, &cd))
+ {
+ if (!strcmp(cd, netProvInfo->netAddressInfo.WIFI.pwd))
+ {
+ OIC_LOG_V(DEBUG, TAG, "Password is proper");
+ input = input->next;
+ continue;
+ }
+ else
+ {
+ OIC_LOG_V(DEBUG, TAG, "Password is NOT proper");
+ goto Error;
}
}
- cJSON_Delete(observeJson);
+ LogProvisioningResponse(input->values);
- PrepareProvisioingStatusCB(&provInfo, clientResponse,
- DEVICE_PROVISIONED);
- cbData(provInfo);
+ input = input->next;
+
+ }
+
+ SuccessCallback(clientResponse);
+
+ return OC_STACK_KEEP_TRANSACTION;
+
+ Error:
+ {
+
+ ErrorCallback( DEVICE_NOT_PROVISIONED);
- return OC_STACK_KEEP_TRANSACTION;
- } else {
- OIC_LOG(INFO, TAG,
- "ProvisionEnrolleeResponse received NULL clientResponse. \
- Invoking Provisioing Status Callback");
- PrepareProvisioingStatusCB(&provInfo, clientResponse,
- DEVICE_NOT_PROVISIONED);
- cbData(provInfo);
return OC_STACK_DELETE_TRANSACTION;
}
+
}
-OCStackResult ProvisionEnrollee(OCQualityOfService qos, const char* query) {
+OCStackResult ProvisionEnrollee(OCQualityOfService qos, const char* query, const char* resUri,
+ OCDevAddr *destination)
+{
OIC_LOG_V(INFO, TAG, "\n\nExecuting ProvisionEnrollee%s", __func__);
- cJSON *jsonFinal = cJSON_CreateObject();
- cJSON *json = cJSON_CreateObject();
- cJSON *jsonArray;
- cJSON *format;
- char* payload = NULL;
-
- char nodeData[OIC_STRING_MAX_VALUE] = { '\0' };
- snprintf(nodeData, sizeof(nodeData), "%s", OIC_PROVISIONING_URI);
+ OCRepPayload* payload = OCRepPayloadCreate();
- cJSON_AddStringToObject(json, "href", nodeData);
- cJSON_AddItemToObject(json, "rep", format = cJSON_CreateObject());
- cJSON_AddStringToObject(format, "tnn", netProvInfo->netAddressInfo.WIFI.ssid);
- cJSON_AddStringToObject(format, "cd", netProvInfo->netAddressInfo.WIFI.pwd);
- cJSON_AddItemToObject(jsonFinal, "oic", jsonArray = cJSON_CreateArray());
- cJSON_AddItemToArray(jsonArray, json);
+ OCRepPayloadSetUri(payload, resUri);
+ OCRepPayloadSetPropString(payload, OC_RSRVD_ES_TNN, netProvInfo->netAddressInfo.WIFI.ssid);
+ OCRepPayloadSetPropString(payload, OC_RSRVD_ES_CD, netProvInfo->netAddressInfo.WIFI.pwd);
- OIC_LOG_V(DEBUG, TAG, "ProvisionEnrollee : %s",
- cJSON_PrintUnformatted(jsonFinal));
- payload = cJSON_Print(jsonFinal);
- OIC_LOG_V(DEBUG, TAG, "Payload : %s", payload);
+ OIC_LOG_V(DEBUG, TAG, "OCPayload ready for ProvisionEnrollee");
- OCStackResult ret = InvokeOCDoResource(query, OC_REST_PUT, OC_HIGH_QOS,
+ OCStackResult ret = InvokeOCDoResource(query, OC_REST_PUT, destination, OC_HIGH_QOS,
ProvisionEnrolleeResponse, payload, NULL, 0);
- cJSON_Delete(json);
return ret;
}
-OCStackApplicationResult GetProvisioningStatusResponse(void* ctx,
- OCDoHandle handle, OCClientResponse * clientResponse) {
- ProvisioningInfo provInfo;
+OCStackApplicationResult GetProvisioningStatusResponse(void* ctx, OCDoHandle handle,
+ OCClientResponse * clientResponse)
+{
- if (clientResponse == NULL) {
- OIC_LOG(INFO, TAG,
- "getReqCB received NULL clientResponse. \
- Invoking Provisioing Status Callback");
- PrepareProvisioingStatusCB(&provInfo, clientResponse,
- DEVICE_NOT_PROVISIONED);
- cbData(provInfo);
- return OC_STACK_DELETE_TRANSACTION;
- }
+ ProvisioningInfo *provInfo;
- if (clientResponse->rcvdVendorSpecificHeaderOptions
- && clientResponse->numRcvdVendorSpecificHeaderOptions) {
- OIC_LOG(INFO, TAG, "Received vendor specific options");
- uint8_t i = 0;
- OCHeaderOption * rcvdOptions =
- clientResponse->rcvdVendorSpecificHeaderOptions;
- for (i = 0; i < clientResponse->numRcvdVendorSpecificHeaderOptions;
- i++) {
- if (((OCHeaderOption) rcvdOptions[i]).protocolID == OC_COAP_ID) {
- OIC_LOG_V(INFO, TAG,
- "Received option with OC_COAP_ID and ID %u with",
- ((OCHeaderOption) rcvdOptions[i]).optionID);
-
- OIC_LOG_BUFFER(INFO, TAG,
- ((OCHeaderOption) rcvdOptions[i]).optionData,
- MAX_HEADER_OPTION_DATA_LENGTH);
- }
- }
+ if (!ValidateEnrolleResponse(clientResponse))
+ {
+ ErrorCallback( DEVICE_NOT_PROVISIONED);
+ ClearMemory();
+ return OC_STACK_DELETE_TRANSACTION;
}
- char sourceaddr[OIC_STRING_MAX_VALUE] = { '\0' };
- snprintf(sourceaddr, sizeof(sourceaddr), "%d.%d.%d.%d:%d%s",
- clientResponse->addr->addr[0], clientResponse->addr->addr[1],
- clientResponse->addr->addr[2], clientResponse->addr->addr[3],
- 6298, OIC_PROVISIONING_URI);
-
- if (clientResponse->resJSONPayload) {
- cJSON *observeJson = cJSON_CreateObject();
- observeJson = cJSON_Parse(clientResponse->resJSONPayload);
+ OCRepPayload* input = (OCRepPayload*) (clientResponse->payload);
- cJSON *ocArray = cJSON_GetObjectItem(observeJson, "oic");
- cJSON *ocArray_sub = cJSON_GetArrayItem(ocArray, 0);
+ char query[OIC_STRING_MAX_VALUE] =
+ { '\0' };
+ char resURI[MAX_URI_LENGTH] =
+ { '\0' };
- cJSON *representationArray = cJSON_GetObjectItem(ocArray_sub, "rep");
- char *ocArray_str = cJSON_PrintUnformatted(representationArray);
+ OIC_LOG_V(DEBUG, TAG, "resUri = %s", input->uri);
- if (strstr(ocArray_str, "[{}") == ocArray_str) {
- OIC_LOG_V(DEBUG, TAG, "invalid payload : %s", ocArray_str);
- cJSON_Delete(observeJson);
- return OC_STACK_DELETE_TRANSACTION;
- }
+ strncpy(resURI, input->uri, sizeof(resURI));
- int countofrep = cJSON_GetArraySize(representationArray);
-
- for (int i = 0; i < countofrep; ++i) {
- cJSON *arrayJSON = cJSON_GetArrayItem(representationArray, i);
- OIC_LOG_V(DEBUG, TAG, "rep#%d's name : %s", i, arrayJSON->string);
-
- switch (arrayJSON->type) {
- case cJSON_False:
- case cJSON_True:
- OIC_LOG_V(DEBUG, TAG, "rep#%d's value : %d", i,
- arrayJSON->valueint);
- break;
- case cJSON_Number:
- OIC_LOG_V(DEBUG, TAG, "rep#%d's value : %f", i,
- arrayJSON->valuedouble);
- break;
- case cJSON_String:
- OIC_LOG_V(DEBUG, TAG, "rep#%d's value : %s", i,
- arrayJSON->valuestring);
- break;
- case cJSON_NULL:
- default:
- OIC_LOG_V(DEBUG, TAG, "rep#%d's value : NULL", i);
- break;
- }
- }
- cJSON_Delete(observeJson);
+ snprintf(query, sizeof(query), UNICAST_PROV_STATUS_QUERY, clientResponse->addr->addr, IP_PORT,
+ resURI);
- if (ProvisionEnrollee(OC_HIGH_QOS, sourceaddr) != OC_STACK_OK) {
- OIC_LOG(INFO, TAG,
- "GetProvisioningStatusResponse received NULL clientResponse. \
- Invoking Provisioing Status Callback");
- PrepareProvisioingStatusCB(&provInfo, clientResponse,
- DEVICE_NOT_PROVISIONED);
- cbData(provInfo);
+ //OCPayloadLogRep(DEBUG,TAG,input);
- return OC_STACK_DELETE_TRANSACTION;
- }
- } else {
+ if (ProvisionEnrollee(OC_HIGH_QOS, query, OC_RSRVD_ES_URI_PROV, clientResponse->addr)
+ != OC_STACK_OK)
+ {
OIC_LOG(INFO, TAG,
- "GetProvisioningStatusResponse received NULL clientResponse. \
- Invoking Provisioing Status Callback");
- PrepareProvisioingStatusCB(&provInfo, clientResponse,
- DEVICE_NOT_PROVISIONED);
- cbData(provInfo);
+ "GetProvisioningStatusResponse received NULL clientResponse.Invoking Provisioing Status Callback");
+
+ ErrorCallback( DEVICE_NOT_PROVISIONED);
+ ClearMemory();
return OC_STACK_DELETE_TRANSACTION;
}
- return OC_STACK_DELETE_TRANSACTION;
+
+ return OC_STACK_KEEP_TRANSACTION;
+
}
-OCStackResult InvokeOCDoResource(const char* query, OCMethod method,
- OCQualityOfService qos, OCClientResponseHandler cb, const char* request,
- OCHeaderOption * options, uint8_t numOptions) {
+OCStackResult InvokeOCDoResource(const char* query, OCMethod method, const OCDevAddr *dest,
+ OCQualityOfService qos, OCClientResponseHandler cb, OCRepPayload* payload,
+ OCHeaderOption * options, uint8_t numOptions)
+{
OCStackResult ret;
OCCallbackData cbData;
cbData.context = (void*) DEFAULT_CONTEXT_VALUE;
cbData.cd = NULL;
- ret = OCDoResource(NULL, method, query, 0, request, OC_CONNTYPE, qos,
- &cbData, options, numOptions);
+ ret = OCDoResource(NULL, method, query, dest, (OCPayload*) payload, OC_CONNTYPE, qos, &cbData,
+ options, numOptions);
- if (ret != OC_STACK_OK) {
- OIC_LOG_V(ERROR, TAG, "OCDoResource returns error %d with method %d",
- ret, method);
+ if (ret != OC_STACK_OK)
+ {
+ OIC_LOG_V(ERROR, TAG, "OCDoResource returns error %d with method %d", ret, method);
}
return ret;
}
-OCStackResult GetProvisioningStatus(OCQualityOfService qos, const char* query) {
+OCStackResult GetProvisioningStatus(OCQualityOfService qos, const char* query,
+ const OCDevAddr *destination)
+{
OCStackResult ret = OC_STACK_ERROR;
OCHeaderOption options[MAX_HEADER_OPTIONS];
OIC_LOG_V(INFO, TAG, "\n\nExecuting %s", __func__);
- uint8_t option0[] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
- uint8_t option1[] = { 11, 12, 13, 14, 15, 16, 17, 18, 19, 20 };
+ uint8_t option0[] =
+ { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
+ uint8_t option1[] =
+ { 11, 12, 13, 14, 15, 16, 17, 18, 19, 20 };
memset(options, 0, sizeof(OCHeaderOption) * MAX_HEADER_OPTIONS);
options[0].protocolID = OC_COAP_ID;
options[0].optionID = 2048;
memcpy(options[1].optionData, option1, sizeof(option1));
options[1].optionLength = 10;
- ret = InvokeOCDoResource(query, OC_REST_GET, OC_HIGH_QOS,
+ ret = InvokeOCDoResource(query, OC_REST_GET, destination, OC_HIGH_QOS,
GetProvisioningStatusResponse, NULL, options, 2);
return ret;
}
OCStackResult StartProvisioningProcess(const EnrolleeNWProvInfo_t *netInfo,
- OCProvisioningStatusCB provisioningStatusCallback) {
+ OCProvisioningStatusCB provisioningStatusCallback)
+{
+
OCStackResult result = OC_STACK_ERROR;
- ProvisioningInfo provInfo;
- if (netInfo->netAddressInfo.WIFI.ipAddress == NULL) {
- OIC_LOG(ERROR, TAG, "Request URI is NULL");
- return result;
+ if (!ValidateEasySetupParams(netInfo, provisioningStatusCallback))
+ {
+ goto Error;
}
- if (provisioningStatusCallback == NULL) {
- OIC_LOG(ERROR, TAG, "ProvisioningStatusCallback is NULL");
- return result;
+ //Only basis test is done for below API
+ if (!SetProgress(provisioningStatusCallback))
+ {
+ // Device provisioning session is running already.
+ OIC_LOG(INFO, TAG, PCF("Device provisioning session is running already"));
+ goto Error;
}
- cbData = provisioningStatusCallback;
-
- //Copy Network Provisioning Information
- netProvInfo = (EnrolleeNWProvInfo_t *)OICCalloc(1, sizeof(EnrolleeNWProvInfo_t));
-
- if (NULL == netProvInfo)
+ if (!ConfigEnrolleeObject(netInfo))
{
- OIC_LOG(ERROR, TAG, "Invalid input..");
- return OC_STACK_ERROR;
+ goto Error;
}
- memcpy(netProvInfo, netInfo, sizeof(EnrolleeNWProvInfo_t));
-
- OIC_LOG_V(DEBUG, TAG, "Network Provisioning Info. SSID = %s",
- netProvInfo->netAddressInfo.WIFI.ssid);
-
- OIC_LOG_V(DEBUG, TAG, "Network Provisioning Info. PWD = %s",
- netProvInfo->netAddressInfo.WIFI.pwd);
-
- /* Start a discovery query*/
- char szQueryUri[64] = { 0 };
-
- snprintf(szQueryUri, sizeof(szQueryUri), UNICAST_PROVISIONING_QUERY,
- netProvInfo->netAddressInfo.WIFI.ipAddress, IP_PORT);
-
- OIC_LOG_V(DEBUG, TAG, "szQueryUri = %s", szQueryUri);
-
- if (FindProvisioningResource(OC_HIGH_QOS, szQueryUri) != OC_STACK_OK) {
- OIC_LOG(ERROR, TAG,
- "FindProvisioningResource failed. \
- Invoking Provisioing Status Callback");
-
- ProvDeviceInfo provDeviceIndo;
- OCDevAddr dst = { };
- dst.addr[0] = netProvInfo->netAddressInfo.WIFI.ipAddress[0];
- dst.addr[1] = netProvInfo->netAddressInfo.WIFI.ipAddress[1];
- dst.addr[2] = netProvInfo->netAddressInfo.WIFI.ipAddress[2];
- dst.addr[3] = netProvInfo->netAddressInfo.WIFI.ipAddress[3];
- dst.addr[4] = (uint8_t) IP_PORT;
- dst.addr[5] = (uint8_t)(IP_PORT >> 8);
+ if (CA_STATUS_OK != ca_thread_pool_add_task(g_threadPoolHandle, FindProvisioningResource,
+ (void *) ""))
+ {
+ goto Error;
+ }
- provInfo.provStatus = DEVICE_NOT_PROVISIONED;
- provDeviceIndo.addr = &dst;
- provDeviceIndo.connType = OC_IPV4;
- provInfo.provDeviceInfo = provDeviceIndo;
+ return OC_STACK_OK;
- cbData(provInfo);
- return result;
+ Error:
+ {
+ ErrorCallback( DEVICE_NOT_PROVISIONED);
+ ClearMemory();
+ return OC_STACK_ERROR;
}
- result = OC_STACK_OK;
- return result;
}
-void StopProvisioningProcess() {
- cbData = NULL;
+void StopProvisioningProcess()
+{
+ //Only basis test is done for below API
+ ResetProgress();
}
// This is a function called back when a device is discovered
-OCStackApplicationResult FindProvisioningResourceResponse(void* ctx,
- OCDoHandle handle, OCClientResponse * clientResponse) {
+OCStackApplicationResult FindProvisioningResourceResponse(void* ctx, OCDoHandle handle,
+ OCClientResponse * clientResponse)
+{
+
OIC_LOG(INFO, TAG, PCF("Entering FindProvisioningResourceResponse"));
- OCStackApplicationResult response = OC_STACK_DELETE_TRANSACTION;
+ if (!ValidateFinddResourceResponse(clientResponse))
+ {
+ ErrorCallback( DEVICE_NOT_PROVISIONED);
+ return OC_STACK_DELETE_TRANSACTION;
+ }
- ProvisioningInfo provInfo;
+ OCStackApplicationResult response = OC_STACK_DELETE_TRANSACTION;
- if (clientResponse->result != OC_STACK_OK) {
- OIC_LOG(ERROR, TAG,
- "OCStack stop error. Calling Provisioing Status Callback");
+ ProvisioningInfo *provInfo;
+ char szQueryUri[64] =
+ { 0 };
- PrepareProvisioingStatusCB(&provInfo, clientResponse,
- DEVICE_NOT_PROVISIONED);
+ OCDiscoveryPayload* discoveryPayload = (OCDiscoveryPayload*) (clientResponse->payload);
- cbData(provInfo);
- return response;
+ // Need to conform if below check is required or not. As Null check of clientResponse->payload is already performed above
+ if (!discoveryPayload)
+ {
+ OIC_LOG_V(DEBUG, TAG, "Failed To parse");
+ ErrorCallback( DEVICE_NOT_PROVISIONED);
+ return OC_STACK_DELETE_TRANSACTION;
}
- if (clientResponse) {
- // Parse header options from server
- uint16_t optionID;
- uint8_t* optionData;
- const char* payload;
+ OIC_LOG_V(DEBUG, TAG, "resUri = %s", discoveryPayload->resources->uri);
- for (int i = 0; i < clientResponse->numRcvdVendorSpecificHeaderOptions;
- i++) {
- optionID =
- clientResponse->rcvdVendorSpecificHeaderOptions[i].optionID;
- optionData =
- clientResponse->rcvdVendorSpecificHeaderOptions[i].optionData;
- payload = clientResponse->resJSONPayload;
- }
-
- cJSON *discoveryJson = cJSON_CreateObject();
- discoveryJson = cJSON_Parse((char *) clientResponse->resJSONPayload);
+ snprintf(szQueryUri, sizeof(szQueryUri), UNICAST_PROV_STATUS_QUERY,
+ clientResponse->devAddr.addr, IP_PORT, discoveryPayload->resources->uri);
- cJSON *ocArray = cJSON_GetObjectItem(discoveryJson, "oic");
- char *ocArray_str = cJSON_PrintUnformatted(ocArray);
+ OIC_LOG_V(DEBUG, TAG, "query before GetProvisioningStatus call = %s", szQueryUri);
- if (strstr(ocArray_str, "[{}") == ocArray_str) {
- OIC_LOG_V(DEBUG, TAG, "invalid payload : %s", ocArray_str);
- cJSON_Delete(discoveryJson);
+ if (GetProvisioningStatus(OC_HIGH_QOS, szQueryUri, &clientResponse->devAddr) != OC_STACK_OK)
+ {
+ ErrorCallback( DEVICE_NOT_PROVISIONED);
+ return OC_STACK_DELETE_TRANSACTION;
+ }
- PrepareProvisioingStatusCB(&provInfo, clientResponse,
- DEVICE_NOT_PROVISIONED);
- cbData(provInfo);
- return response;
- }
+ return OC_STACK_KEEP_TRANSACTION;
- char sourceaddr[OIC_STRING_MAX_VALUE] = { '\0' };
- snprintf(sourceaddr, sizeof(sourceaddr), "%d.%d.%d.%d:%d%s",
- clientResponse->addr->addr[0], clientResponse->addr->addr[1],
- clientResponse->addr->addr[2], clientResponse->addr->addr[3],
- IP_PORT, OIC_PROVISIONING_URI);
+}
- OIC_LOG_V(DEBUG, TAG, "Discovered %s @ %s",
- clientResponse->resJSONPayload, sourceaddr);
+void FindProvisioningResource(void *data)
+{
+ OCStackResult ret = OC_STACK_ERROR;
- if (GetProvisioningStatus(OC_HIGH_QOS, sourceaddr) != OC_STACK_OK) {
- OIC_LOG(INFO, TAG,
- "GetProvisioningStatus returned error. \
- Invoking Provisioing Status Callback");
- PrepareProvisioingStatusCB(&provInfo, clientResponse,
- DEVICE_NOT_PROVISIONED);
- cbData(provInfo);
+ /* Start a discovery query*/
+ char szQueryUri[64] =
+ { 0 };
- return OC_STACK_DELETE_TRANSACTION;
- }
- } else {
- // clientResponse is invalid
- OIC_LOG(ERROR, TAG,
- "Invalid response for Provisioning Discovery request. \
- Invoking Provisioing Status Callback");
- PrepareProvisioingStatusCB(&provInfo, clientResponse,
- DEVICE_NOT_PROVISIONED);
- cbData(provInfo);
- return response;
- }
- return OC_STACK_KEEP_TRANSACTION;
-}
+ snprintf(szQueryUri, sizeof(szQueryUri), UNICAST_PROVISIONING_QUERY,
+ netProvInfo->netAddressInfo.WIFI.ipAddress, IP_PORT);
-OCStackResult FindProvisioningResource(OCQualityOfService qos,
- const char* requestURI) {
- OCStackResult ret = OC_STACK_ERROR;
+ OIC_LOG_V(DEBUG, TAG, "szQueryUri = %s", szQueryUri);
- OCCallbackData cbData;
+ OCCallbackData ocCBData;
- cbData.cb = FindProvisioningResourceResponse;
- cbData.context = (void*) DEFAULT_CONTEXT_VALUE;
- cbData.cd = NULL;
+ ocCBData.cb = FindProvisioningResourceResponse;
+ ocCBData.context = (void*) DEFAULT_CONTEXT_VALUE;
+ ocCBData.cd = NULL;
- ret = OCDoResource(NULL, OC_REST_GET, requestURI, 0, 0, OC_CONNTYPE,
- OC_LOW_QOS, &cbData, NULL, 0);
+ ret = OCDoResource(NULL, OC_REST_DISCOVER, szQueryUri, NULL, NULL, OC_CONNTYPE, OC_LOW_QOS,
+ &ocCBData, NULL, 0);
- if (ret != OC_STACK_OK) {
- OIC_LOG(ERROR, TAG, "OCStack resource error");
+ if (ret != OC_STACK_OK)
+ {
+ ErrorCallback( DEVICE_NOT_PROVISIONED);
+ ClearMemory();
}
-
- return ret;
}
OCStackApplicationResult SubscribeProvPresenceCallback(void* ctx, OCDoHandle handle,
- OCClientResponse* clientResponse) {
+ OCClientResponse* clientResponse)
+{
OIC_LOG(INFO, TAG, PCF("Entering SubscribeProvPresenceCallback"));
OCStackApplicationResult response = OC_STACK_DELETE_TRANSACTION;
- if (clientResponse->result != OC_STACK_OK) {
+ if (clientResponse->result != OC_STACK_OK)
+ {
OIC_LOG(ERROR, TAG, "OCStack stop error");
return response;
}
- if (clientResponse) {
+ if (clientResponse)
+ {
OIC_LOG(INFO, TAG, PCF("Client Response exists"));
- // Parse header options from server
- uint16_t optionID;
- uint8_t* optionData;
- const char* payload;
-
- for (int i = 0; i < clientResponse->numRcvdVendorSpecificHeaderOptions;
- i++) {
- optionID =
- clientResponse->rcvdVendorSpecificHeaderOptions[i].optionID;
- optionData =
- clientResponse->rcvdVendorSpecificHeaderOptions[i].optionData;
- payload = clientResponse->resJSONPayload;
- }
- cJSON *discoveryJson = cJSON_CreateObject();
- discoveryJson = cJSON_Parse((char *) clientResponse->resJSONPayload);
-
- cJSON *ocArray = cJSON_GetObjectItem(discoveryJson, "oic");
- char *ocArray_str = cJSON_PrintUnformatted(ocArray);
+ if (clientResponse->payload && clientResponse->payload->type != PAYLOAD_TYPE_REPRESENTATION)
+ {
+ OIC_LOG_V(DEBUG, TAG, "Incoming payload not a representation");
+ return response;
+ }
- if (strstr(ocArray_str, "[{}") == ocArray_str) {
- OIC_LOG_V(DEBUG, TAG, "invalid payload : %s", ocArray_str);
- cJSON_Delete(discoveryJson);
+ OCRepPayload* discoveryPayload = (OCRepPayload*) (clientResponse->payload);
+ if (!discoveryPayload)
+ {
+ OIC_LOG_V(DEBUG, TAG, "invalid payload");
return response;
}
- char sourceIPAddr[OIC_STRING_MAX_VALUE] = { '\0' };
- snprintf(sourceIPAddr, sizeof(sourceIPAddr), "%d.%d.%d.%d",
- clientResponse->addr->addr[0], clientResponse->addr->addr[1],
- clientResponse->addr->addr[2], clientResponse->addr->addr[3]);
+ char sourceIPAddr[OIC_STRING_MAX_VALUE] =
+ { '\0' };
+ snprintf(sourceIPAddr, sizeof(sourceIPAddr), "%s", clientResponse->addr->addr);
- OIC_LOG_V(DEBUG, TAG, "Discovered %s @ %s",
- clientResponse->resJSONPayload, sourceIPAddr);
+ OIC_LOG_V(DEBUG, TAG, "Discovered %s @ %s", discoveryPayload->uri, sourceIPAddr);
/* Start a discovery query*/
- char szQueryUri[64] = { 0 };
- OCQualityOfService qos = OC_NA_QOS;
+ char szQueryUri[64] =
+ { 0 };
- snprintf(szQueryUri, sizeof(szQueryUri), UNICAST_PROVISIONING_QUERY,
- sourceIPAddr, IP_PORT);
+ snprintf(szQueryUri, sizeof(szQueryUri), UNICAST_PROVISIONING_QUERY, sourceIPAddr, IP_PORT);
- if (FindProvisioningResource(qos, szQueryUri) != OC_STACK_OK) {
- OIC_LOG(ERROR, TAG, "FindProvisioningResource failed");
- return OC_STACK_KEEP_TRANSACTION;
- }
- } else {
+ /*if (FindProvisioningResource(qos, szQueryUri) != OC_STACK_OK) {
+ OIC_LOG(ERROR, TAG, "FindProvisioningResource failed");
+ return OC_STACK_KEEP_TRANSACTION;
+ }*/
+ }
+ else
+ {
// clientResponse is invalid
OIC_LOG(ERROR, TAG, PCF("Client Response is NULL!"));
}
return OC_STACK_KEEP_TRANSACTION;
}
-OCStackResult SubscribeProvPresence(OCQualityOfService qos,
- const char* requestURI) {
+OCStackResult SubscribeProvPresence(OCQualityOfService qos, const char* requestURI)
+{
OCStackResult ret = OC_STACK_ERROR;
OCCallbackData cbData;
cbData.context = (void*) DEFAULT_CONTEXT_VALUE;
cbData.cd = NULL;
- ret = OCDoResource(NULL, OC_REST_PRESENCE, requestURI, 0, 0, OC_CONNTYPE,
- OC_LOW_QOS, &cbData, NULL, 0);
+ ret = OCDoResource(NULL, OC_REST_PRESENCE, requestURI, 0, 0, OC_CONNTYPE, OC_LOW_QOS, &cbData,
+ NULL, 0);
- if (ret != OC_STACK_OK) {
+ if (ret != OC_STACK_OK)
+ {
OIC_LOG(ERROR, TAG, "OCStack resource error");
}
return ret;
}
-OCStackResult FindNetworkResource() {
+OCStackResult FindNetworkResource()
+{
OCStackResult ret = OC_STACK_ERROR;
- if (OCStop() != OC_STACK_OK) {
+ if (OCStop() != OC_STACK_OK)
+ {
OIC_LOG(ERROR, TAG, "OCStack stop error");
}
return ret;
}
-void PrepareProvisioingStatusCB(ProvisioningInfo *provInfo,
- OCClientResponse * clientResponse, ProvStatus provStatus) {
- ProvDeviceInfo provDeviceIndo;
- OCDevAddr dst = { };
+ProvisioningInfo* PrepareProvisioingStatusCB(OCClientResponse * clientResponse,
+ ProvStatus provStatus)
+{
+
+ ProvisioningInfo *provInfo = (ProvisioningInfo *) OICCalloc(1, sizeof(ProvisioningInfo));
+
+ if (provInfo == NULL)
+ {
+ OIC_LOG_V(ERROR, TAG, "Failed to allocate memory");
+ return NULL;
+ }
+
+ OCDevAddr *devAddr = (OCDevAddr *) OICCalloc(1, sizeof(OCDevAddr));
+
+ if (devAddr == NULL)
+ {
+ OIC_LOG_V(ERROR, TAG, "Failed to allocate memory");
+ return NULL;
+ }
+
+ strncpy(devAddr->addr, clientResponse->addr->addr, sizeof(devAddr->addr));
+ devAddr->port = clientResponse->addr->port;
+
+ provInfo->provDeviceInfo.addr = devAddr;
+
+ provInfo->provStatus = provStatus;
+
+ return provInfo;
+}
+
+bool ValidateEasySetupParams(const EnrolleeNWProvInfo_t *netInfo,
+ OCProvisioningStatusCB provisioningStatusCallback)
+{
+
+ if (netInfo == NULL || netInfo->netAddressInfo.WIFI.ipAddress == NULL)
+ {
+ OIC_LOG(ERROR, TAG, "Request URI is NULL");
+ return false;
+ }
+
+ if (provisioningStatusCallback == NULL)
+ {
+ OIC_LOG(ERROR, TAG, "ProvisioningStatusCallback is NULL");
+ return false;
+ }
+
+ return true;
+
+}
+
+bool InProgress()
+{
+
+ // It means already Easy Setup provisioning session is going on.
+ if (NULL != cbData)
+ {
+ OIC_LOG(ERROR, TAG, "Easy setup session is already in progress");
+ return true;
+ }
+
+ return false;
+}
+
+bool SetProgress(OCProvisioningStatusCB provisioningStatusCallback)
+{
+ ca_mutex_lock(g_provisioningMutex);
+
+ if (InProgress())
+ return false;
+
+ cbData = provisioningStatusCallback;
+
+ ca_mutex_unlock(g_provisioningMutex);
+
+ return true;
+}
+
+bool ResetProgress()
+{
+ ca_mutex_lock(g_provisioningMutex);
+
+ cbData = NULL;
+
+ ca_mutex_unlock(g_provisioningMutex);
+}
+
+ProvisioningInfo* CreateCallBackObject()
+{
+
+ ProvisioningInfo *provInfo = (ProvisioningInfo *) OICCalloc(1, sizeof(ProvisioningInfo));
+
+ if (provInfo == NULL)
+ {
+ OIC_LOG_V(ERROR, TAG, "Failed to allocate memory");
+ return NULL;
+ }
+
+ OCDevAddr *devAddr = (OCDevAddr *) OICCalloc(1, sizeof(OCDevAddr));
- uint16_t remotePortNum;
- OCDevAddrToPort((OCDevAddr *) clientResponse->addr, &remotePortNum);
+ if (devAddr == NULL)
+ {
+ OIC_LOG_V(ERROR, TAG, "Failed to allocate memory");
+ return NULL;
+ }
+
+ provInfo->provDeviceInfo.addr = devAddr;
+
+ return provInfo;
- dst.addr[0] = clientResponse->addr->addr[0];
- dst.addr[1] = clientResponse->addr->addr[1];
- dst.addr[2] = clientResponse->addr->addr[2];
- dst.addr[3] = clientResponse->addr->addr[3];
- dst.addr[4] = (uint8_t) remotePortNum;
- dst.addr[5] = (uint8_t)(remotePortNum >> 8);
+}
+
+ProvisioningInfo* GetCallbackObjectOnError(ProvStatus status)
+{
+
+ ProvisioningInfo *provInfo = CreateCallBackObject();
+ strncpy(provInfo->provDeviceInfo.addr->addr, netProvInfo->netAddressInfo.WIFI.ipAddress,
+ sizeof(provInfo->provDeviceInfo.addr->addr));
+ provInfo->provDeviceInfo.addr->port = IP_PORT;
+ provInfo->provStatus = status;
+ return provInfo;
+}
+ProvisioningInfo* GetCallbackObjectOnSuccess(OCClientResponse * clientResponse,
+ ProvStatus provStatus)
+{
+ ProvisioningInfo *provInfo = CreateCallBackObject();
+ strncpy(provInfo->provDeviceInfo.addr->addr, clientResponse->addr->addr,
+ sizeof(provInfo->provDeviceInfo.addr->addr));
+ provInfo->provDeviceInfo.addr->port = clientResponse->addr->port;
provInfo->provStatus = provStatus;
+ return provInfo;
+}
+
+bool ValidateFinddResourceResponse(OCClientResponse * clientResponse)
+{
+
+ if (!(clientResponse) || !(clientResponse->payload))
+ {
+
+ OIC_LOG_V(INFO, TAG, "ProvisionEnrolleeResponse received Null clientResponse");
+
+ return false;
+
+ }
+return true;
+}
+
+bool ValidateEnrolleResponse(OCClientResponse * clientResponse)
+{
+
+ if (!(clientResponse) || !(clientResponse->payload))
+ {
+
+ OIC_LOG_V(INFO, TAG, "ProvisionEnrolleeResponse received Null clientResponse");
+
+ return false;
+
+ }
+
+ if (clientResponse->payload->type != PAYLOAD_TYPE_REPRESENTATION)
+ {
+
+ OIC_LOG_V(DEBUG, TAG, "Incoming payload not a representation");
+ return false;
+
+ }
+
+ // If flow reachese here means no error condition hit.
+ return true;
+
+}
+
+
+void SuccessCallback(OCClientResponse * clientResponse)
+{
+ ProvisioningInfo *provInfo = GetCallbackObjectOnSuccess(clientResponse, DEVICE_PROVISIONED);
+ cbData(provInfo);
+ ResetProgress();
+}
+
+bool ClearMemory()
+{
+
+ OIC_LOG(DEBUG, TAG, "thread_pool_add_task of FindProvisioningResource failed");
+ ca_thread_pool_free(g_threadPoolHandle);
+ ca_mutex_unlock(g_provisioningMutex);
+ ca_mutex_free(g_provisioningMutex);
+ ca_cond_free(g_provisioningCond);
+
+ return true;
+
+}
- provDeviceIndo.addr = &dst;
- provDeviceIndo.connType = OC_IPV4;
+bool ConfigEnrolleeObject(const EnrolleeNWProvInfo_t *netInfo)
+{
- provInfo->provDeviceInfo = provDeviceIndo;
+ //Copy Network Provisioning Information
+ netProvInfo = (EnrolleeNWProvInfo_t *) OICCalloc(1, sizeof(EnrolleeNWProvInfo_t));
+
+ if (netProvInfo == NULL)
+ {
+ OIC_LOG(ERROR, TAG, "Invalid input..");
+ return false;
+ }
+
+ memcpy(netProvInfo, netInfo, sizeof(EnrolleeNWProvInfo_t));
+
+ OIC_LOG_V(DEBUG, TAG, "Network Provisioning Info. SSID = %s",
+ netProvInfo->netAddressInfo.WIFI.ssid);
+
+ OIC_LOG_V(DEBUG, TAG, "Network Provisioning Info. PWD = %s",
+ netProvInfo->netAddressInfo.WIFI.pwd);
+
+ return true;
+
+}
+
+void LogProvisioningResponse(OCRepPayloadValue* val)
+{
+
+ switch (val->type)
+ {
+ case OCREP_PROP_NULL:
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s: NULL", val->name);
+ break;
+ case OCREP_PROP_INT:
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s(int):%lld", val->name, val->i);
+ break;
+ case OCREP_PROP_DOUBLE:
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s(double):%f", val->name, val->d);
+ break;
+ case OCREP_PROP_BOOL:
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s(bool):%s", val->name, val->b ? "true" : "false");
+ break;
+ case OCREP_PROP_STRING:
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s(string):%s", val->name, val->str);
+ break;
+ case OCREP_PROP_OBJECT:
+ // Note: Only prints the URI (if available), to print further, you'll
+ // need to dig into the object better!
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s(OCRep):%s", val->name, val->obj->uri);
+ break;
+ case OCREP_PROP_ARRAY:
+ switch (val->arr.type)
+ {
+ case OCREP_PROP_INT:
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s(int array):%lld x %lld x %lld", val->name,
+ val->arr.dimensions[0], val->arr.dimensions[1], val->arr.dimensions[2]);
+ break;
+ case OCREP_PROP_DOUBLE:
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s(double array):%lld x %lld x %lld", val->name,
+ val->arr.dimensions[0], val->arr.dimensions[1], val->arr.dimensions[2]);
+ break;
+ case OCREP_PROP_BOOL:
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s(bool array):%lld x %lld x %lld", val->name,
+ val->arr.dimensions[0], val->arr.dimensions[1], val->arr.dimensions[2]);
+ break;
+ case OCREP_PROP_STRING:
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s(string array):%lld x %lld x %lld", val->name,
+ val->arr.dimensions[0], val->arr.dimensions[1], val->arr.dimensions[2]);
+ break;
+ case OCREP_PROP_OBJECT:
+ OIC_LOG_V(DEBUG, TAG, "\t\t%s(OCRep array):%lld x %lld x %lld", val->name,
+ val->arr.dimensions[0], val->arr.dimensions[1], val->arr.dimensions[2]);
+ break;
+ default:
+ //OIC_LOG_V(ERROR, TAG, "\t\t%s <-- Unknown/unsupported array type!",
+ // val->name);
+ break;
+ }
+ break;
+ default:
+ /*OC_LOG_V(ERROR, TAG
+ , "\t\t%s <-- Unknown type!", val->name);*/
+ break;
+ }
}