#define __STDC_LIMIT_MACROS
+#include "iotivity_config.h"
#include <stdlib.h>
#ifdef HAVE_STRING_H
#include <string.h>
#include <strings.h>
#endif
#include <stdint.h>
+#include <stdbool.h>
#include "cainterface.h"
#include "payload_logging.h"
#include "base64.h"
#include "ocserverrequest.h"
#include "oic_malloc.h"
+#include "oic_string.h"
#include "ocpayload.h"
+#include "ocpayloadcbor.h"
#include "utlist.h"
#include "credresource.h"
#include "doxmresource.h"
#include "psinterface.h"
#include "pinoxmcommon.h"
+#ifdef __unix__
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <unistd.h>
+#endif
+
#ifdef __WITH_DTLS__
#include "global.h"
#endif
-#define TAG "SRM-CREDL"
+#define TAG "OIC_SRM_CREDL"
+/** Max credential types number used for TLS */
+#define MAX_TYPE 2
/** Default cbor payload size. This value is increased in case of CborErrorOutOfMemory.
* The value of payload size is increased until reaching belox max cbor size. */
static const uint16_t CBOR_SIZE = 2048;
static const uint16_t CBOR_MAX_SIZE = 4400;
/** CRED size - Number of mandatory items. */
-static const uint8_t CRED_ROOT_MAP_SIZE = 2;
+static const uint8_t CRED_ROOT_MAP_SIZE = 4;
static const uint8_t CRED_MAP_SIZE = 3;
static OicSecCred_t *gCred = NULL;
static OCResourceHandle gCredHandle = NULL;
+typedef enum CredCompareResult{
+ CRED_CMP_EQUAL = 0,
+ CRED_CMP_NOT_EQUAL = 1,
+ CRED_CMP_ERROR = 2
+}CredCompareResult_t;
+
+/**
+ * Internal function to check credential
+ */
+static bool IsVaildCredential(const OicSecCred_t* cred)
+{
+ OicUuid_t emptyUuid = {.id={0}};
+
+
+ OIC_LOG(DEBUG, TAG, "IN IsVaildCredential");
+
+ VERIFY_NON_NULL(TAG, cred, ERROR);
+ VERIFY_SUCCESS(TAG, 0 != cred->credId, ERROR);
+ OIC_LOG_V(DEBUG, TAG, "Cred ID = %d", cred->credId);
+
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+ OIC_LOG_V(DEBUG, TAG, "Cred Type = %d", cred->credType);
+
+ switch(cred->credType)
+ {
+ case SYMMETRIC_PAIR_WISE_KEY:
+ case SYMMETRIC_GROUP_KEY:
+ case PIN_PASSWORD:
+ {
+ VERIFY_NON_NULL(TAG, cred->privateData.data, ERROR);
+ VERIFY_SUCCESS(TAG, 0 != cred->privateData.len, ERROR);
+ VERIFY_SUCCESS(TAG, \
+ (OIC_ENCODING_RAW == cred->privateData.encoding || \
+ OIC_ENCODING_BASE64 == cred->privateData.encoding), \
+ ERROR);
+ break;
+ }
+ case ASYMMETRIC_KEY:
+ {
+ VERIFY_NON_NULL(TAG, cred->publicData.data, ERROR);
+ VERIFY_SUCCESS(TAG, 0 != cred->publicData.len, ERROR);
+ break;
+ }
+ case SIGNED_ASYMMETRIC_KEY:
+ {
+ VERIFY_SUCCESS(TAG, (NULL != cred->publicData.data ||NULL != cred->optionalData.data) , ERROR);
+ VERIFY_SUCCESS(TAG, (0 != cred->publicData.len || 0 != cred->optionalData.len), ERROR);
+
+ if(NULL != cred->optionalData.data)
+ {
+ VERIFY_SUCCESS(TAG, \
+ (OIC_ENCODING_RAW == cred->optionalData.encoding ||\
+ OIC_ENCODING_BASE64 == cred->optionalData.encoding || \
+ OIC_ENCODING_PEM == cred->optionalData.encoding || \
+ OIC_ENCODING_DER == cred->optionalData.encoding), \
+ ERROR);
+ }
+ break;
+ }
+ case ASYMMETRIC_ENCRYPTION_KEY:
+ {
+ VERIFY_NON_NULL(TAG, cred->privateData.data, ERROR);
+ VERIFY_SUCCESS(TAG, 0 != cred->privateData.len, ERROR);
+ VERIFY_SUCCESS(TAG, \
+ (OIC_ENCODING_RAW == cred->privateData.encoding ||\
+ OIC_ENCODING_BASE64 == cred->privateData.encoding || \
+ OIC_ENCODING_PEM == cred->privateData.encoding || \
+ OIC_ENCODING_DER == cred->privateData.encoding), \
+ ERROR);
+ break;
+ }
+ default:
+ {
+ OIC_LOG(WARNING, TAG, "Unknown credential type");
+ return false;
+ }
+ }
+#endif
+
+ VERIFY_SUCCESS(TAG, 0 != memcmp(emptyUuid.id, cred->subject.id, sizeof(cred->subject.id)), ERROR);
+
+ OIC_LOG(DEBUG, TAG, "OUT IsVaildCredential");
+ return true;
+exit:
+ OIC_LOG(WARNING, TAG, "OUT IsVaildCredential : Invalid Credential detected.");
+ return false;
+}
+
+static bool IsEmptyCred(const OicSecCred_t* cred)
+{
+ OicUuid_t emptyUuid = {.id={0}};
+
+ VERIFY_SUCCESS(TAG, (0 == memcmp(cred->subject.id, emptyUuid.id, sizeof(emptyUuid))), ERROR);
+ VERIFY_SUCCESS(TAG, (0 == cred->credId), ERROR);
+ VERIFY_SUCCESS(TAG, (0 == cred->credType), ERROR);
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+ VERIFY_SUCCESS(TAG, (NULL == cred->privateData.data), ERROR);
+ VERIFY_SUCCESS(TAG, (NULL == cred->publicData.data), ERROR);
+ VERIFY_SUCCESS(TAG, (NULL == cred->optionalData.data), ERROR);
+ VERIFY_SUCCESS(TAG, (NULL == cred->credUsage), ERROR);
+#endif
+ return true;
+exit:
+ return false;
+}
+
/**
* This function frees OicSecCred_t object's fields and object itself.
*/
OICFree(cred->roleIds);
#endif
- //Clean PublicData
-#ifdef __WITH_X509__
+ //Clean PublicData/OptionalData/Credusage
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+ // TODO: Need to check credUsage.
OICFree(cred->publicData.data);
-#endif
+ OICFree(cred->optionalData.data);
+ OICFree(cred->credUsage);
+
+#endif /* __WITH_DTLS__ || __WITH_TLS__*/
//Clean PrivateData
OICFree(cred->privateData.data);
//Clean Period
OICFree(cred->period);
+#ifdef _ENABLE_MULTIPLE_OWNER_
+ //Clean eowner
+ OICFree(cred->eownerID);
+#endif
+
//Clean Cred node itself
OICFree(cred);
}
}
}
+size_t GetCredKeyDataSize(const OicSecCred_t* cred)
+{
+ size_t size = 0;
+ if (cred)
+ {
+ OicSecCred_t *credPtr = NULL, *credTmp = NULL;
+ LL_FOREACH_SAFE((OicSecCred_t*)cred, credPtr, credTmp)
+ {
+ if (credPtr->privateData.data && 0 < credPtr->privateData.len)
+ {
+ size += credPtr->privateData.len;
+ }
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+ if (credPtr->publicData.data && 0 < credPtr->publicData.len)
+ {
+ size += credPtr->publicData.len;
+ }
+ if (credPtr->optionalData.data && 0 < credPtr->optionalData.len)
+ {
+ size += credPtr->optionalData.len;
+ }
+#endif
+ }
+ }
+ OIC_LOG_V(DEBUG, TAG, "Cred Key Data Size : %zd\n", size);
+ return size;
+}
+
static size_t OicSecCredCount(const OicSecCred_t *secCred)
{
size_t size = 0;
{
CborEncoder credMap;
size_t mapSize = CRED_MAP_SIZE;
- char *subject = NULL;
+ size_t inLen = 0;
if (cred->period)
{
mapSize++;
}
-#ifdef __WITH_X509__
+
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+#ifdef _ENABLE_MULTIPLE_OWNER_
+ if(cred->eownerID)
+ {
+ mapSize++;
+ }
+#endif //_ENABLE_MULTIPLE_OWNER_
+
if (SIGNED_ASYMMETRIC_KEY == cred->credType && cred->publicData.data)
{
mapSize++;
}
-#endif /* __WITH_X509__ */
+ if (SIGNED_ASYMMETRIC_KEY == cred->credType && cred->optionalData.data)
+ {
+ mapSize++;
+ }
+ if (cred->credUsage)
+ {
+ mapSize++;
+ }
+#endif /* __WITH_DTLS__ || __WITH_TLS__*/
if (!secureFlag && cred->privateData.data)
{
mapSize++;
cborEncoderResult = cbor_encode_text_string(&credMap, OIC_JSON_SUBJECTID_NAME,
strlen(OIC_JSON_SUBJECTID_NAME));
VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Subject Tag.");
- ret = ConvertUuidToStr(&cred->subject, &subject);
- VERIFY_SUCCESS(TAG, ret == OC_STACK_OK, ERROR);
- cborEncoderResult = cbor_encode_text_string(&credMap, subject, strlen(subject));
- VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Addding Subject Id Value.");
- OICFree(subject);
+ inLen = (memcmp(&(cred->subject), &WILDCARD_SUBJECT_ID, WILDCARD_SUBJECT_ID_LEN) == 0) ?
+ WILDCARD_SUBJECT_ID_LEN : sizeof(OicUuid_t);
+ if(inLen == WILDCARD_SUBJECT_ID_LEN)
+ {
+ cborEncoderResult = cbor_encode_text_string(&credMap, WILDCARD_RESOURCE_URI,
+ strlen(WILDCARD_RESOURCE_URI));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Addding Subject Id wildcard Value.");
+ }
+ else
+ {
+ char *subject = NULL;
+ ret = ConvertUuidToStr(&cred->subject, &subject);
+ VERIFY_SUCCESS(TAG, ret == OC_STACK_OK, ERROR);
+ cborEncoderResult = cbor_encode_text_string(&credMap, subject, strlen(subject));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Addding Subject Id Value.");
+ OICFree(subject);
+ }
//CredType -- Mandatory
cborEncoderResult = cbor_encode_text_string(&credMap, OIC_JSON_CREDTYPE_NAME,
cborEncoderResult = cbor_encode_int(&credMap, cred->credType);
VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Cred Type Value.");
-#ifdef __WITH_X509__
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
//PublicData -- Not Mandatory
if (SIGNED_ASYMMETRIC_KEY == cred->credType && cred->publicData.data)
{
cborEncoderResult = cbor_encode_text_string(&publicMap, OIC_JSON_ENCODING_NAME,
strlen(OIC_JSON_ENCODING_NAME));
VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Public Encoding Tag.");
- cborEncoderResult = cbor_encode_text_string(&publicMap, OIC_SEC_ENCODING_RAW,
- strlen(OIC_SEC_ENCODING_RAW));
+ cborEncoderResult = cbor_encode_text_string(&publicMap, OIC_SEC_ENCODING_DER,
+ strlen(OIC_SEC_ENCODING_DER));
VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Public Encoding Value.");
cborEncoderResult = cbor_encoder_close_container(&credMap, &publicMap);
VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Closing PublicData Map.");
}
-#endif /*__WITH_X509__*/
+ //OptionalData -- Not Mandatory
+ if (SIGNED_ASYMMETRIC_KEY == cred->credType && cred->optionalData.data)
+ {
+ CborEncoder optionalMap;
+ const size_t optionalMapSize = 2;
+
+ cborEncoderResult = cbor_encode_text_string(&credMap, OIC_JSON_OPTDATA_NAME,
+ strlen(OIC_JSON_OPTDATA_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding OptionalData Tag.");
+
+ cborEncoderResult = cbor_encoder_create_map(&credMap, &optionalMap, optionalMapSize);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding OptionalData Map");
+
+ // TODO: Need to data strucure modification for OicSecCert_t.
+ if(OIC_ENCODING_RAW == cred->optionalData.encoding)
+ {
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_JSON_ENCODING_NAME,
+ strlen(OIC_JSON_ENCODING_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Encoding Tag.");
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_SEC_ENCODING_RAW,
+ strlen(OIC_SEC_ENCODING_RAW));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Encoding Value.");
+
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_JSON_DATA_NAME,
+ strlen(OIC_JSON_DATA_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Tag.");
+ cborEncoderResult = cbor_encode_byte_string(&optionalMap, cred->optionalData.data,
+ cred->optionalData.len);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Value.");
+ }
+ else if(OIC_ENCODING_BASE64 == cred->optionalData.encoding)
+ {
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_JSON_ENCODING_NAME,
+ strlen(OIC_JSON_ENCODING_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Encoding Tag.");
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_SEC_ENCODING_BASE64,
+ strlen(OIC_SEC_ENCODING_BASE64));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Encoding Value.");
+
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_JSON_DATA_NAME,
+ strlen(OIC_JSON_DATA_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Tag.");
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, (char*)(cred->optionalData.data),
+ cred->optionalData.len);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Value.");
+ }
+ else if(OIC_ENCODING_PEM == cred->optionalData.encoding)
+ {
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_JSON_ENCODING_NAME,
+ strlen(OIC_JSON_ENCODING_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Encoding Tag.");
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_SEC_ENCODING_PEM,
+ strlen(OIC_SEC_ENCODING_PEM));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Encoding Value.");
+
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_JSON_DATA_NAME,
+ strlen(OIC_JSON_DATA_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Tag.");
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, (char*)(cred->optionalData.data),
+ cred->optionalData.len);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Value.");
+ }
+ else if(OIC_ENCODING_DER == cred->optionalData.encoding)
+ {
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_JSON_ENCODING_NAME,
+ strlen(OIC_JSON_ENCODING_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Encoding Tag.");
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_SEC_ENCODING_DER,
+ strlen(OIC_SEC_ENCODING_DER));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Encoding Value.");
+
+ cborEncoderResult = cbor_encode_text_string(&optionalMap, OIC_JSON_DATA_NAME,
+ strlen(OIC_JSON_DATA_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Tag.");
+ cborEncoderResult = cbor_encode_byte_string(&optionalMap, cred->optionalData.data,
+ cred->optionalData.len);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding optional Value.");
+ }
+ else
+ {
+ OIC_LOG(ERROR, TAG, "Unknown encoding type for optional data.");
+ VERIFY_CBOR_SUCCESS(TAG, CborErrorUnknownType, "Failed Adding optional Encoding Value.");
+ }
+
+ cborEncoderResult = cbor_encoder_close_container(&credMap, &optionalMap);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Closing OptionalData Map.");
+ }
+ //CredUsage -- Not Mandatory
+ if(cred->credUsage)
+ {
+ cborEncoderResult = cbor_encode_text_string(&credMap, OIC_JSON_CREDUSAGE_NAME,
+ strlen(OIC_JSON_CREDUSAGE_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Credusage Name Tag.");
+ cborEncoderResult = cbor_encode_text_string(&credMap, cred->credUsage,
+ strlen(cred->credUsage));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Credusage Name Value.");
+ }
+#endif /* __WITH_DTLS__ || __WITH_TLS__*/
//PrivateData -- Not Mandatory
if(!secureFlag && cred->privateData.data)
{
cred->privateData.len);
VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Priv Value.");
}
+ else if(OIC_ENCODING_DER == cred->privateData.encoding)
+ {
+ cborEncoderResult = cbor_encode_text_string(&privateMap, OIC_JSON_ENCODING_NAME,
+ strlen(OIC_JSON_ENCODING_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Private Encoding Tag.");
+ cborEncoderResult = cbor_encode_text_string(&privateMap, OIC_SEC_ENCODING_DER,
+ strlen(OIC_SEC_ENCODING_DER));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Private Encoding Value.");
+
+ cborEncoderResult = cbor_encode_text_string(&privateMap, OIC_JSON_DATA_NAME,
+ strlen(OIC_JSON_DATA_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Priv Tag.");
+ cborEncoderResult = cbor_encode_byte_string(&privateMap, cred->privateData.data,
+ cred->privateData.len);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Priv Value.");
+ }
else
{
- OIC_LOG(ERROR, TAG, "Unknow encoding type for private data.");
+ OIC_LOG(ERROR, TAG, "Unknown encoding type for private data.");
VERIFY_CBOR_SUCCESS(TAG, CborErrorUnknownType, "Failed Adding Private Encoding Value.");
}
VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding Period Name Value.");
}
+#ifdef _ENABLE_MULTIPLE_OWNER_
+ // Eownerid -- Not Mandatory
+ if(cred->eownerID)
+ {
+ char *eowner = NULL;
+ cborEncoderResult = cbor_encode_text_string(&credMap, OIC_JSON_EOWNERID_NAME,
+ strlen(OIC_JSON_EOWNERID_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding eownerId Name Tag.");
+ ret = ConvertUuidToStr(cred->eownerID, &eowner);
+ VERIFY_SUCCESS(TAG, ret == OC_STACK_OK, ERROR);
+ cborEncoderResult = cbor_encode_text_string(&credMap, eowner, strlen(eowner));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Addding eownerId Value.");
+ OICFree(eowner);
+ }
+#endif //_ENABLE_MULTIPLE_OWNER_
cborEncoderResult = cbor_encoder_close_container(&credArray, &credMap);
VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Closing Cred Map.");
OICFree(rowner);
}
+ //RT -- Mandatory
+ CborEncoder rtArray;
+ cborEncoderResult = cbor_encode_text_string(&credRootMap, OIC_JSON_RT_NAME,
+ strlen(OIC_JSON_RT_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Addding RT Name Tag.");
+ cborEncoderResult = cbor_encoder_create_array(&credRootMap, &rtArray, 1);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Addding RT Value.");
+ for (size_t i = 0; i < 1; i++)
+ {
+ cborEncoderResult = cbor_encode_text_string(&rtArray, OIC_RSRC_TYPE_SEC_CRED,
+ strlen(OIC_RSRC_TYPE_SEC_CRED));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding RT Value.");
+ }
+ cborEncoderResult = cbor_encoder_close_container(&credRootMap, &rtArray);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Closing RT.");
+
+ //IF-- Mandatory
+ CborEncoder ifArray;
+ cborEncoderResult = cbor_encode_text_string(&credRootMap, OIC_JSON_IF_NAME,
+ strlen(OIC_JSON_IF_NAME));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Addding IF Name Tag.");
+ cborEncoderResult = cbor_encoder_create_array(&credRootMap, &ifArray, 1);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Addding IF Value.");
+ for (size_t i = 0; i < 1; i++)
+ {
+ cborEncoderResult = cbor_encode_text_string(&ifArray, OC_RSRVD_INTERFACE_DEFAULT,
+ strlen(OC_RSRVD_INTERFACE_DEFAULT));
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Adding IF Value.");
+ }
+ cborEncoderResult = cbor_encoder_close_container(&credRootMap, &ifArray);
+ VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Closing IF.");
+
+
// Close CRED Root Map
cborEncoderResult = cbor_encoder_close_container(&encoder, &credRootMap);
VERIFY_CBOR_SUCCESS(TAG, cborEncoderResult, "Failed Closing CRED Root Map.");
{
OIC_LOG(DEBUG, TAG, "CredToCBORPayload Successed");
*cborPayload = outPayload;
- *cborSize = encoder.ptr - outPayload;
+ *cborSize = cbor_encoder_get_buffer_size(&encoder, outPayload);
ret = OC_STACK_OK;
}
OIC_LOG(DEBUG, TAG, "CredToCBORPayload OUT");
// reallocate and try again!
OICFree(outPayload);
// Since the allocated initial memory failed, double the memory.
- cborLen += encoder.ptr - encoder.end;
+ cborLen += cbor_encoder_get_buffer_size(&encoder, encoder.end);
cborEncoderResult = CborNoError;
ret = CredToCBORPayload(credS, cborPayload, &cborLen, secureFlag);
*cborSize = cborLen;
char *subjectid = NULL;
cborFindResult = cbor_value_dup_text_string(&credMap, &subjectid, &len, NULL);
VERIFY_CBOR_SUCCESS(TAG, cborFindResult, "Failed Finding subjectid Value.");
- ret = ConvertStrToUuid(subjectid, &cred->subject);
- VERIFY_SUCCESS(TAG, ret == OC_STACK_OK, ERROR);
+ if(strcmp(subjectid, WILDCARD_RESOURCE_URI) == 0)
+ {
+ cred->subject.id[0] = '*';
+ }
+ else
+ {
+ ret = ConvertStrToUuid(subjectid, &cred->subject);
+ VERIFY_SUCCESS(TAG, ret == OC_STACK_OK, ERROR);
+ }
OICFree(subjectid);
}
// credtype
else
{
cborFindResult = CborErrorUnknownType;
- OIC_LOG(ERROR, TAG, "Unknow type for private data.");
+ OIC_LOG(ERROR, TAG, "Unknown type for private data.");
}
VERIFY_CBOR_SUCCESS(TAG, cborFindResult, "Failed Finding PrivateData.");
}
{
//For unit test
cred->privateData.encoding = OIC_ENCODING_RAW;
- OIC_LOG(WARNING, TAG, "Unknow encoding type dectected for private data.");
+ OIC_LOG(WARNING, TAG, "Unknown encoding type dectected for private data.");
}
OICFree(strEncoding);
}
}
-#ifdef __WITH_X509__
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+ //PublicData -- Not Mandatory
if (strcmp(name, OIC_JSON_PUBLICDATA_NAME) == 0)
{
CborValue pubMap = { .parser = NULL };
OICFree(pubname);
}
}
-#endif //__WITH_X509__
+ //OptionalData -- Not Mandatory
+ if (strcmp(name, OIC_JSON_OPTDATA_NAME) == 0)
+ {
+ CborValue optMap = { .parser = NULL };
+ cborFindResult = cbor_value_enter_container(&credMap, &optMap);
+
+ while (cbor_value_is_valid(&optMap))
+ {
+ char* optname = NULL;
+ CborType type = cbor_value_get_type(&optMap);
+ if (type == CborTextStringType && cbor_value_is_text_string(&optMap))
+ {
+ cborFindResult = cbor_value_dup_text_string(&optMap, &optname,
+ &len, NULL);
+ VERIFY_CBOR_SUCCESS(TAG, cborFindResult, "Failed to get text");
+ cborFindResult = cbor_value_advance(&optMap);
+ VERIFY_CBOR_SUCCESS(TAG, cborFindResult, "Failed to advance value");
+ }
+ if (optname)
+ {
+ // OptionalData::optdata -- Mandatory
+ if (strcmp(optname, OIC_JSON_DATA_NAME) == 0)
+ {
+ if(cbor_value_is_byte_string(&optMap))
+ {
+ cborFindResult = cbor_value_dup_byte_string(&optMap, &cred->optionalData.data,
+ &cred->optionalData.len, NULL);
+ }
+ else if(cbor_value_is_text_string(&optMap))
+ {
+ cborFindResult = cbor_value_dup_text_string(&optMap, (char**)(&cred->optionalData.data),
+ &cred->optionalData.len, NULL);
+ }
+ else
+ {
+ cborFindResult = CborErrorUnknownType;
+ OIC_LOG(ERROR, TAG, "Unknown type for optional data.");
+ }
+ VERIFY_CBOR_SUCCESS(TAG, cborFindResult, "Failed Finding OptionalData.");
+ }
+ // OptionalData::encoding -- Mandatory
+ if (strcmp(optname, OIC_JSON_ENCODING_NAME) == 0)
+ {
+ // TODO: Added as workaround. Will be replaced soon.
+ char* strEncoding = NULL;
+ cborFindResult = cbor_value_dup_text_string(&optMap, &strEncoding, &len, NULL);
+ VERIFY_CBOR_SUCCESS(TAG, cborFindResult, "Failed Finding EncodingType");
+
+ if(strcmp(strEncoding, OIC_SEC_ENCODING_RAW) == 0)
+ {
+ OIC_LOG(INFO,TAG,"cbor_value_is_byte_string");
+ cred->optionalData.encoding = OIC_ENCODING_RAW;
+ }
+ else if(strcmp(strEncoding, OIC_SEC_ENCODING_BASE64) == 0)
+ {
+ cred->optionalData.encoding = OIC_ENCODING_BASE64;
+ }
+ else if(strcmp(strEncoding, OIC_SEC_ENCODING_PEM) == 0)
+ {
+ cred->optionalData.encoding = OIC_ENCODING_PEM;
+ }
+ else if(strcmp(strEncoding, OIC_SEC_ENCODING_DER) == 0)
+ {
+ cred->optionalData.encoding = OIC_ENCODING_DER;
+ }
+ else
+ {
+ //For unit test
+ cred->optionalData.encoding = OIC_ENCODING_RAW;
+ OIC_LOG(WARNING, TAG, "Unknown encoding type dectected for optional data.");
+ }
+ OICFree(strEncoding);
+ }
+ }
+ if (cbor_value_is_valid(&optMap))
+ {
+ cborFindResult = cbor_value_advance(&optMap);
+ VERIFY_CBOR_SUCCESS(TAG, cborFindResult, "Failed Advancing optdata Map.");
+ }
+ OICFree(optname);
+ }
+ }
+ //Credusage -- Not Mandatory
+ if (0 == strcmp(OIC_JSON_CREDUSAGE_NAME, name))
+ {
+ cborFindResult = cbor_value_dup_text_string(&credMap, &cred->credUsage, &len, NULL);
+ VERIFY_CBOR_SUCCESS(TAG, cborFindResult, "Failed Finding Period.");
+ }
+#endif //__WITH_DTLS__ || __WITH_TLS__
if (0 == strcmp(OIC_JSON_PERIOD_NAME, name))
{
VERIFY_CBOR_SUCCESS(TAG, cborFindResult, "Failed Finding Period.");
}
+#ifdef _ENABLE_MULTIPLE_OWNER_
+ // Eowner uuid -- Not Mandatory
+ if (strcmp(OIC_JSON_EOWNERID_NAME, name) == 0 && cbor_value_is_text_string(&credMap))
+ {
+ char *eowner = NULL;
+ cborFindResult = cbor_value_dup_text_string(&credMap, &eowner, &len, NULL);
+ VERIFY_CBOR_SUCCESS(TAG, cborFindResult, "Failed Finding eownerId Value.");
+ if(NULL == cred->eownerID)
+ {
+ cred->eownerID = (OicUuid_t*)OICCalloc(1, sizeof(OicUuid_t));
+ VERIFY_NON_NULL(TAG, cred->eownerID, ERROR);
+ }
+ ret = ConvertStrToUuid(eowner, cred->eownerID);
+ OICFree(eowner);
+ VERIFY_SUCCESS(TAG, OC_STACK_OK == ret , ERROR);
+ }
+#endif //_ENABLE_MULTIPLE_OWNER_
+
if (cbor_value_is_valid(&credMap))
{
cborFindResult = cbor_value_advance(&credMap);
VERIFY_SUCCESS(TAG, ret == OC_STACK_OK, ERROR);
OICFree(stRowner);
}
+ else if (NULL != gCred)
+ {
+ memcpy(&(headCred->rownerID), &(gCred->rownerID), sizeof(OicUuid_t));
+ }
OICFree(tagName);
}
if (cbor_value_is_valid(&CredRootMap))
return ret;
}
+#ifdef _ENABLE_MULTIPLE_OWNER_
+bool IsValidCredentialAccessForSubOwner(const OicUuid_t* uuid, const uint8_t *cborPayload, size_t size)
+{
+ OicSecCred_t* cred = NULL;
+ bool isValidCred = false;
+
+ OIC_LOG_BUFFER(DEBUG, TAG, cborPayload, size);
+
+ VERIFY_NON_NULL(TAG, uuid, ERROR);
+ VERIFY_NON_NULL(TAG, cborPayload, ERROR);
+ VERIFY_SUCCESS(TAG, 0 != size, ERROR);
+ VERIFY_SUCCESS(TAG, OC_STACK_OK == CBORPayloadToCred(cborPayload, size, &cred), ERROR);
+ VERIFY_NON_NULL(TAG, cred, ERROR);
+ VERIFY_NON_NULL(TAG, cred->eownerID, ERROR);
+ VERIFY_SUCCESS(TAG, (memcmp(cred->eownerID->id, uuid->id, sizeof(uuid->id)) == 0), ERROR);
+
+ isValidCred = true;
+
+exit:
+ DeleteCredList(cred);
+
+ return isValidCred;
+
+}
+#endif //_ENABLE_MULTIPLE_OWNER_
+
OicSecCred_t * GenerateCredential(const OicUuid_t * subject, OicSecCredType_t credType,
const OicSecCert_t * publicData, const OicSecKey_t* privateData,
- const OicUuid_t * rownerID)
+ const OicUuid_t * rownerID, const OicUuid_t * eownerID)
{
+ OIC_LOG(DEBUG, TAG, "IN GenerateCredential");
+
(void)publicData;
OCStackResult ret = OC_STACK_ERROR;
SYMMETRIC_GROUP_KEY | ASYMMETRIC_KEY | SIGNED_ASYMMETRIC_KEY | PIN_PASSWORD), ERROR);
cred->credType = credType;
-#ifdef __WITH_X509__
+#ifdef __WITH_DTLS__
if (publicData && publicData->data)
{
cred->publicData.data = (uint8_t *)OICCalloc(1, publicData->len);
memcpy(cred->publicData.data, publicData->data, publicData->len);
cred->publicData.len = publicData->len;
}
-#endif // __WITH_X509__
+#endif // __WITH_DTLS__
if (privateData && privateData->data)
{
VERIFY_NON_NULL(TAG, rownerID, ERROR);
memcpy(&cred->rownerID, rownerID, sizeof(OicUuid_t));
+#ifdef _ENABLE_MULTIPLE_OWNER_
+ if(eownerID)
+ {
+ cred->eownerID = (OicUuid_t*)OICCalloc(1, sizeof(OicUuid_t));
+ VERIFY_NON_NULL(TAG, cred->eownerID, ERROR);
+ memcpy(cred->eownerID->id, eownerID->id, sizeof(eownerID->id));
+ }
+#endif //_ENABLE_MULTIPLE_OWNER_
+
ret = OC_STACK_OK;
+
+ OIC_LOG_V(DEBUG, TAG, "GenerateCredential : result: %d", ret);
+ OIC_LOG_V(DEBUG, TAG, "GenerateCredential : credId: %d", cred->credId);
+ OIC_LOG_V(DEBUG, TAG, "GenerateCredential : credType: %d", cred->credType);
+ OIC_LOG_BUFFER(DEBUG, TAG, cred->subject.id, sizeof(cred->subject.id));
+ if (cred->privateData.data)
+ {
+ OIC_LOG_V(DEBUG, TAG, "GenerateCredential : privateData len: %d", cred->privateData.len);
+ OIC_LOG_BUFFER(DEBUG, TAG, cred->privateData.data, cred->privateData.len);
+ }
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+ if(cred->credUsage)
+ {
+ OIC_LOG_V(DEBUG, TAG, "GenerateCredential : credUsage: %s", cred->credUsage);
+ }
+ if (cred->publicData.data)
+ {
+ OIC_LOG_V(DEBUG, TAG, "GenerateCredential : publicData len: %d", cred->publicData.len);
+ OIC_LOG_BUFFER(DEBUG, TAG, cred->publicData.data, cred->publicData.len);
+
+ }
+ if (cred->optionalData.data)
+ {
+ OIC_LOG_V(DEBUG, TAG, "GenerateCredential : optionalData len: %d", cred->optionalData.len);
+ OIC_LOG_BUFFER(DEBUG, TAG, cred->optionalData.data, cred->optionalData.len);
+
+ }
+#endif //defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+
exit:
if (OC_STACK_OK != ret)
{
DeleteCredList(cred);
cred = NULL;
}
+ OIC_LOG(DEBUG, TAG, "OUT GenerateCredential");
return cred;
}
static bool UpdatePersistentStorage(const OicSecCred_t *cred)
{
bool ret = false;
+ OIC_LOG(DEBUG, TAG, "IN Cred UpdatePersistentStorage");
// Convert Cred data into JSON for update to persistent storage
if (cred)
{
uint8_t *payload = NULL;
- size_t size = 0;
+ // This added '512' is arbitrary value that is added to cover the name of the resource, map addition and ending
+ size_t size = GetCredKeyDataSize(cred);
+ size += (512 * OicSecCredCount(cred));
+ OIC_LOG_V(DEBUG, TAG, "cred size: %" PRIu64, size);
+
int secureFlag = 0;
OCStackResult res = CredToCBORPayload(cred, &payload, &size, secureFlag);
if ((OC_STACK_OK == res) && payload)
ret = true;
}
}
+ OIC_LOG(DEBUG, TAG, "OUT Cred UpdatePersistentStorage");
return ret;
}
return NULL;
}
-OCStackResult AddCredential(OicSecCred_t * newCred)
+static bool IsSameSecKey(const OicSecKey_t* sk1, const OicSecKey_t* sk2)
{
- OCStackResult ret = OC_STACK_ERROR;
- VERIFY_SUCCESS(TAG, NULL != newCred, ERROR);
-
- //Assigning credId to the newCred
- newCred->credId = GetCredId();
- VERIFY_SUCCESS(TAG, newCred->credId != 0, ERROR);
+ VERIFY_NON_NULL(TAG, sk1, WARNING);
+ VERIFY_NON_NULL(TAG, sk2, WARNING);
- //Append the new Cred to existing list
- LL_APPEND(gCred, newCred);
+ VERIFY_SUCCESS(TAG, (sk1->len == sk2->len), INFO);
+ VERIFY_SUCCESS(TAG, (sk1->encoding == sk2->encoding), INFO);
+ VERIFY_SUCCESS(TAG, (0 == memcmp(sk1->data, sk2->data, sk1->len)), INFO);
+ return true;
+exit:
+ return false;
+}
- if (UpdatePersistentStorage(gCred))
- {
- ret = OC_STACK_OK;
- }
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+static bool IsSameCert(const OicSecCert_t* cert1, const OicSecCert_t* cert2)
+{
+ VERIFY_NON_NULL(TAG, cert1, WARNING);
+ VERIFY_NON_NULL(TAG, cert2, WARNING);
+ VERIFY_SUCCESS(TAG, (cert1->len == cert2->len), INFO);
+ VERIFY_SUCCESS(TAG, (0 == memcmp(cert1->data, cert2->data, cert1->len)), INFO);
+ return true;
exit:
- return ret;
+ return false;
}
+#endif //#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
-OCStackResult RemoveCredential(const OicUuid_t *subject)
+/**
+ * Compares credential
+ *
+ * @return CRED_CMP_EQUAL if credentials are equal
+ * CRED_CMP_NOT_EQUAL if not equal
+ * otherwise error.
+ */
+
+static CredCompareResult_t CompareCredential(const OicSecCred_t * l, const OicSecCred_t * r)
{
- OCStackResult ret = OC_STACK_ERROR;
- OicSecCred_t *cred = NULL;
- OicSecCred_t *tempCred = NULL;
- bool deleteFlag = false;
+ CredCompareResult_t cmpResult = CRED_CMP_ERROR;
+ bool isCompared = false;
+ OIC_LOG(DEBUG, TAG, "IN CompareCredetial");
- LL_FOREACH_SAFE(gCred, cred, tempCred)
+ VERIFY_NON_NULL(TAG, l, ERROR);
+ VERIFY_NON_NULL(TAG, r, ERROR);
+
+ cmpResult = CRED_CMP_NOT_EQUAL;
+
+ VERIFY_SUCCESS(TAG, (l->credType == r->credType), INFO);
+ VERIFY_SUCCESS(TAG, (0 == memcmp(l->subject.id, r->subject.id, sizeof(l->subject.id))), INFO);
+
+ switch(l->credType)
+ {
+ case SYMMETRIC_PAIR_WISE_KEY:
+ case SYMMETRIC_GROUP_KEY:
+ case PIN_PASSWORD:
+ {
+ if(l->privateData.data && r->privateData.data)
+ {
+ VERIFY_SUCCESS(TAG, IsSameSecKey(&l->privateData, &r->privateData), INFO);
+ isCompared = true;
+ }
+ break;
+ }
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+ case ASYMMETRIC_KEY:
+ case SIGNED_ASYMMETRIC_KEY:
+ {
+ if(l->publicData.data && r->publicData.data)
+ {
+ VERIFY_SUCCESS(TAG, IsSameCert(&l->publicData, &r->publicData), INFO);
+ isCompared = true;
+ }
+
+ if(l->optionalData.data && r->optionalData.data)
+ {
+ VERIFY_SUCCESS(TAG, IsSameSecKey(&l->optionalData, &r->optionalData), INFO);
+ isCompared = true;
+ }
+
+ if(l->credUsage && r->credUsage)
+ {
+ VERIFY_SUCCESS(TAG, (strlen(l->credUsage) == strlen(r->credUsage)), INFO);
+ VERIFY_SUCCESS(TAG, (0 == strncmp(l->credUsage, r->credUsage, strlen(l->credUsage))), INFO);
+ isCompared = true;
+ }
+ break;
+ }
+ case ASYMMETRIC_ENCRYPTION_KEY:
+ {
+ if(l->privateData.data && r->privateData.data)
+ {
+ VERIFY_SUCCESS(TAG, IsSameSecKey(&l->privateData, &r->privateData), INFO);
+ isCompared = true;
+ }
+
+ if(l->publicData.data && r->publicData.data)
+ {
+ VERIFY_SUCCESS(TAG, IsSameCert(&l->publicData, &r->publicData), INFO);
+ isCompared = true;
+ }
+
+ if(l->optionalData.data && r->optionalData.data)
+ {
+ VERIFY_SUCCESS(TAG, IsSameSecKey(&l->optionalData, &r->optionalData), INFO);
+ isCompared = true;
+ }
+
+ break;
+ }
+#endif //__WITH_DTLS__ or __WITH_TLS__
+ default:
+ {
+ cmpResult = CRED_CMP_ERROR;
+ break;
+ }
+ }
+
+ if(isCompared)
+ {
+ OIC_LOG(DEBUG, TAG, "Same Credentials");
+ cmpResult = CRED_CMP_EQUAL;
+ }
+ else
+ {
+ OIC_LOG(DEBUG, TAG, "Can not find the key data in credential");
+ cmpResult = CRED_CMP_ERROR;
+ }
+exit:
+ OIC_LOG(DEBUG, TAG, "OUT CompareCredetial");
+
+ return cmpResult;
+}
+
+OCStackResult AddCredential(OicSecCred_t * newCred)
+{
+ OCStackResult ret = OC_STACK_ERROR;
+ OicSecCred_t * temp = NULL;
+ bool validFlag = true;
+ OicUuid_t emptyOwner = { .id = {0} };
+
+ OIC_LOG(DEBUG, TAG, "IN AddCredential");
+
+ VERIFY_SUCCESS(TAG, NULL != newCred, ERROR);
+ //Assigning credId to the newCred
+ newCred->credId = GetCredId();
+ VERIFY_SUCCESS(TAG, true == IsVaildCredential(newCred), ERROR);
+
+ //the newCred is not valid if it is empty
+
+ if (memcmp(&(newCred->subject), &emptyOwner, sizeof(OicUuid_t)) == 0)
+ {
+ validFlag = false;
+ }
+ else
+ {
+ LL_FOREACH(gCred, temp)
+ {
+ CredCompareResult_t cmpRes = CompareCredential(temp, newCred);
+ if(CRED_CMP_EQUAL == cmpRes)
+ {
+ OIC_LOG_V(WARNING, TAG, "Detected same credential ID(%d)" \
+ "new credential's ID will be replaced.", temp->credId);
+ newCred->credId = temp->credId;
+ ret = OC_STACK_OK;
+ validFlag = false;
+ break;
+ }
+
+ if (CRED_CMP_ERROR == cmpRes)
+ {
+ OIC_LOG_V(WARNING, TAG, "Credential skipped : %d", cmpRes);
+ ret = OC_STACK_ERROR;
+ validFlag = false;
+ break;
+ }
+ }
+ }
+
+ //Append the new Cred to existing list if new Cred is valid
+ if (validFlag)
+ {
+ LL_APPEND(gCred, newCred);
+ }
+ if (memcmp(&(newCred->rownerID), &emptyOwner, sizeof(OicUuid_t)) != 0)
+ {
+ memcpy(&(gCred->rownerID), &(newCred->rownerID), sizeof(OicUuid_t));
+ }
+ if (UpdatePersistentStorage(gCred))
+ {
+ ret = OC_STACK_OK;
+ }
+
+exit:
+ OIC_LOG(DEBUG, TAG, "OUT AddCredential");
+ return ret;
+}
+
+OCStackResult RemoveCredential(const OicUuid_t *subject)
+{
+ OCStackResult ret = OC_STACK_ERROR;
+ OicSecCred_t *cred = NULL;
+ OicSecCred_t *tempCred = NULL;
+ bool deleteFlag = false;
+
+ LL_FOREACH_SAFE(gCred, cred, tempCred)
{
if (memcmp(cred->subject.id, subject->id, sizeof(subject->id)) == 0)
{
}
+OCStackResult RemoveCredentialByCredId(uint16_t credId)
+{
+ OCStackResult ret = OC_STACK_ERROR;
+ OicSecCred_t *cred = NULL;
+ OicSecCred_t *tempCred = NULL;
+ bool deleteFlag = false;
+
+ OIC_LOG(INFO, TAG, "IN RemoveCredentialByCredId");
+
+ if ( 0 == credId)
+ {
+ return OC_STACK_INVALID_PARAM;
+ }
+
+
+ LL_FOREACH_SAFE(gCred, cred, tempCred)
+ {
+ if (cred->credId == credId)
+ {
+ OIC_LOG_V(DEBUG, TAG, "Credential(ID=%d) will be removed.", credId);
+
+ LL_DELETE(gCred, cred);
+ FreeCred(cred);
+ deleteFlag = true;
+ }
+ }
+
+ if (deleteFlag)
+ {
+ if (UpdatePersistentStorage(gCred))
+ {
+ ret = OC_STACK_RESOURCE_DELETED;
+ }
+ }
+ OIC_LOG(INFO, TAG, "OUT RemoveCredentialByCredId");
+
+ return ret;
+
+}
+
/**
* Remove all credential data on credential resource and persistent storage
*
return OC_STACK_OK;
}
-#ifdef __WITH_DTLS__
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
/**
* Internal function to fill private data of owner PSK.
*
}
else
{
- // TODO: error
VERIFY_SUCCESS(TAG, OIC_ENCODING_UNKNOW, ERROR);
}
return false;
}
-#endif //__WITH_DTLS__
+
+#ifdef _ENABLE_MULTIPLE_OWNER_
+/**
+ * Internal function to fill private data of SubOwner PSK.
+ *
+ * @param receviedCred recevied owner credential from SubOwner
+ * @param ownerAdd address of SubOwner
+ * @param doxm current device's doxm resource
+ *
+ * @return
+ * true successfully done and valid subower psk information
+ * false Invalid subowner psk information or failed to subowner psk generation
+ */
+static bool FillPrivateDataOfSubOwnerPSK(OicSecCred_t* receivedCred, const CAEndpoint_t* ownerAddr,
+ const OicSecDoxm_t* doxm, const OicUuid_t* subOwner)
+{
+ char* b64Buf = NULL;
+ //Derive OwnerPSK locally
+ const char* oxmLabel = GetOxmString(doxm->oxmSel);
+ VERIFY_NON_NULL(TAG, oxmLabel, ERROR);
+
+ uint8_t subOwnerPSK[OWNER_PSK_LENGTH_128] = {0};
+ CAResult_t pskRet = CAGenerateOwnerPSK(ownerAddr,
+ (uint8_t*)oxmLabel, strlen(oxmLabel),
+ subOwner->id, sizeof(subOwner->id),
+ doxm->deviceID.id, sizeof(doxm->deviceID.id),
+ subOwnerPSK, OWNER_PSK_LENGTH_128);
+ VERIFY_SUCCESS(TAG, pskRet == CA_STATUS_OK, ERROR);
+
+ OIC_LOG(DEBUG, TAG, "SubOwnerPSK dump :");
+ OIC_LOG_BUFFER(DEBUG, TAG, subOwnerPSK, OWNER_PSK_LENGTH_128);
+
+ //Generate owner credential based on received credential information
+
+ if(OIC_ENCODING_RAW == receivedCred->privateData.encoding)
+ {
+ receivedCred->privateData.data = (uint8_t *)OICCalloc(1, OWNER_PSK_LENGTH_128);
+ VERIFY_NON_NULL(TAG, receivedCred->privateData.data, ERROR);
+ receivedCred->privateData.len = OWNER_PSK_LENGTH_128;
+ memcpy(receivedCred->privateData.data, subOwnerPSK, OWNER_PSK_LENGTH_128);
+ }
+ else if(OIC_ENCODING_BASE64 == receivedCred->privateData.encoding)
+ {
+ uint32_t b64OutSize = 0;
+ size_t b64BufSize = B64ENCODE_OUT_SAFESIZE((OWNER_PSK_LENGTH_128 + 1));
+ b64Buf = OICCalloc(1, b64BufSize);
+ VERIFY_NON_NULL(TAG, b64Buf, ERROR);
+
+ VERIFY_SUCCESS(TAG, \
+ B64_OK == b64Encode(subOwnerPSK, OWNER_PSK_LENGTH_128, b64Buf, b64BufSize, &b64OutSize), \
+ ERROR);
+
+ receivedCred->privateData.data = (uint8_t *)OICCalloc(1, b64OutSize + 1);
+ VERIFY_NON_NULL(TAG, receivedCred->privateData.data, ERROR);
+ receivedCred->privateData.len = b64OutSize;
+ strncpy((char*)receivedCred->privateData.data, b64Buf, b64OutSize);
+ receivedCred->privateData.data[b64OutSize] = '\0';
+ }
+ else
+ {
+ OIC_LOG(INFO, TAG, "Unknown credential encoding type.");
+ VERIFY_SUCCESS(TAG, OIC_ENCODING_UNKNOW, ERROR);
+ }
+
+ OIC_LOG(INFO, TAG, "PrivateData of SubOwnerPSK was calculated successfully");
+ OICFree(b64Buf);
+ return true;
+exit:
+ //receivedCred->privateData.data will be deallocated when deleting credential.
+ OICFree(b64Buf);
+ return false;
+}
+#endif //_ENABLE_MULTIPLE_OWNER_
+#endif // __WITH_DTLS__ or __WITH_TLS__
static OCEntityHandlerResult HandlePostRequest(const OCEntityHandlerRequest * ehRequest)
{
OCStackResult res = CBORPayloadToCred(payload, size, &cred);
if (res == OC_STACK_OK)
{
-#ifdef __WITH_DTLS__
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
OicUuid_t emptyUuid = {.id={0}};
const OicSecDoxm_t* doxm = GetDoxmResourceData();
if(doxm && false == doxm->owned && memcmp(&(doxm->owner), &emptyUuid, sizeof(OicUuid_t)) != 0)
OIC_LOG(ERROR, TAG, "OwnerPSK was generated successfully.");
if(OC_STACK_OK == AddCredential(cred))
{
- ret = OC_EH_RESOURCE_CREATED;
+ ret = OC_EH_CHANGED;
}
else
{
ret = OC_EH_ERROR;
}
- if(OC_EH_RESOURCE_CREATED == ret)
+ if(OC_EH_CHANGED == ret)
{
/**
* in case of random PIN based OxM,
*/
if(OIC_RANDOM_DEVICE_PIN == doxm->oxmSel)
{
- OicUuid_t emptyUuid = { .id={0}};
- SetUuidForRandomPinOxm(&emptyUuid);
+ SetUuidForPinBasedOxm(&emptyUuid);
- if(CA_STATUS_OK != CARegisterDTLSCredentialsHandler(GetDtlsPskCredentials))
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
+ if(CA_STATUS_OK != CAregisterPskCredentialsHandler(GetDtlsPskCredentials))
{
- OIC_LOG(ERROR, TAG, "Failed to revert DTLS credential handler.");
+ OIC_LOG(ERROR, TAG, "Failed to revert TLS credential handler.");
ret = OC_EH_ERROR;
break;
}
+#endif // __WITH_DTLS__ or __WITH_TLS__
}
//Select cipher suite to use owner PSK
}
if(CA_STATUS_OK !=
- CASelectCipherSuite(TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA_256))
+ CASelectCipherSuite(TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA_256, ehRequest->devAddr.adapter))
{
OIC_LOG(ERROR, TAG, "Failed to select cipher suite");
ret = OC_EH_ERROR;
}
default:
{
- OIC_LOG(WARNING, TAG, "Unknow credential type for owner credential.");
+ OIC_LOG(WARNING, TAG, "Unknown credential type for owner credential.");
ret = OC_EH_ERROR;
break;
}
}
- if(OC_EH_RESOURCE_CREATED != ret)
+ if(OC_EH_CHANGED != ret)
{
/*
* If some error is occured while ownership transfer,
}
}
}
+#ifdef _ENABLE_MULTIPLE_OWNER_
+ // In case SubOwner Credential
+ else if(doxm && doxm->owned && doxm->mom &&
+ OIC_MULTIPLE_OWNER_DISABLE != doxm->mom->mode &&
+ 0 == cred->privateData.len)
+ {
+ switch(cred->credType)
+ {
+ case SYMMETRIC_PAIR_WISE_KEY:
+ {
+ OCServerRequest *request = (OCServerRequest *)ehRequest->requestHandle;
+ if(FillPrivateDataOfSubOwnerPSK(cred, (CAEndpoint_t *)&request->devAddr, doxm, &cred->subject))
+ {
+ if(OC_STACK_RESOURCE_DELETED == RemoveCredential(&cred->subject))
+ {
+ OIC_LOG(WARNING, TAG, "The credential with the same subject ID was detected!");
+ }
+
+ OIC_LOG(ERROR, TAG, "SubOwnerPSK was generated successfully.");
+ if(OC_STACK_OK == AddCredential(cred))
+ {
+ ret = OC_EH_CHANGED;
+ }
+ else
+ {
+ OIC_LOG(ERROR, TAG, "Failed to save the SubOwnerPSK as cred resource");
+ ret = OC_EH_ERROR;
+ }
+ }
+ else
+ {
+ OIC_LOG(ERROR, TAG, "Failed to verify receviced SubOwner PSK.");
+ ret = OC_EH_ERROR;
+ }
+ }
+ break;
+
+ case SYMMETRIC_GROUP_KEY:
+ case ASYMMETRIC_KEY:
+ case SIGNED_ASYMMETRIC_KEY:
+ case PIN_PASSWORD:
+ case ASYMMETRIC_ENCRYPTION_KEY:
+ {
+ OIC_LOG(WARNING, TAG, "Unsupported credential type for SubOwner credential.");
+ ret = OC_EH_ERROR;
+ break;
+ }
+ default:
+ {
+ OIC_LOG(WARNING, TAG, "Unknown credential type for SubOwner credential.");
+ ret = OC_EH_ERROR;
+ break;
+ }
+ }
+ }
+#endif //_ENABLE_MULTIPLE_OWNER_
else
{
- /*
- * If the post request credential has credId, it will be
- * discarded and the next available credId will be assigned
- * to it before getting appended to the existing credential
- * list and updating svr database.
- */
- ret = (OC_STACK_OK == AddCredential(cred))? OC_EH_RESOURCE_CREATED : OC_EH_ERROR;
+ if(IsEmptyCred(cred))
+ {
+ OicUuid_t emptyUuid = {.id={0}};
+ if(memcmp(cred->rownerID.id, emptyUuid.id, sizeof(emptyUuid.id)) != 0)
+ {
+ OIC_LOG(INFO, TAG, "CRED's rowner will be updated.");
+ memcpy(gCred->rownerID.id, cred->rownerID.id, sizeof(cred->rownerID.id));
+ if (UpdatePersistentStorage(gCred))
+ {
+ ret = OC_EH_CHANGED;
+ }
+ else
+ {
+ ret = OC_EH_ERROR;
+ }
+ }
+ else
+ {
+ ret = OC_EH_ERROR;
+ }
+ }
+ else
+ {
+ /*
+ * If the post request credential has credId, it will be
+ * discarded and the next available credId will be assigned
+ * to it before getting appended to the existing credential
+ * list and updating svr database.
+ */
+ ret = (OC_STACK_OK == AddCredential(cred))? OC_EH_CHANGED : OC_EH_ERROR;
+ }
}
#else //not __WITH_DTLS__
/*
* to it before getting appended to the existing credential
* list and updating svr database.
*/
- ret = (OC_STACK_OK == AddCredential(cred))? OC_EH_RESOURCE_CREATED : OC_EH_ERROR;
+ ret = (OC_STACK_OK == AddCredential(cred))? OC_EH_CHANGED : OC_EH_ERROR;
+ OC_UNUSED(previousMsgId);
#endif//__WITH_DTLS__
}
- if (OC_EH_RESOURCE_CREATED != ret)
+ if (OC_EH_CHANGED != ret)
{
if(OC_STACK_OK != RemoveCredential(&cred->subject))
{
int secureFlag = 1;
const OicSecCred_t *cred = gCred;
+
+ // This added '256' is arbitrary value that is added to cover the name of the resource, map addition and ending
+ size = GetCredKeyDataSize(cred);
+ size += (256 * OicSecCredCount(cred));
OCStackResult res = CredToCBORPayload(cred, &payload, &size, secureFlag);
// A device should always have a default cred. Therefore, payload should never be NULL.
OCStackResult InitCredResource()
{
OCStackResult ret = OC_STACK_ERROR;
+ OicSecCred_t* cred = NULL;
//Read Cred resource from PS
uint8_t *data = NULL;
{
gCred = GetCredDefault();
}
+
+ //Add a log to track the invalid credential.
+ LL_FOREACH(gCred, cred)
+ {
+ if (false == IsVaildCredential(cred))
+ {
+ OIC_LOG(WARNING, TAG, "Invalid credential data was dectected while InitCredResource");
+ OIC_LOG_V(WARNING, TAG, "Invalid credential ID = %d", cred->credId);
+ }
+ }
+
//Instantiate 'oic.sec.cred'
ret = CreateCredResource();
OICFree(data);
return result;
}
-const OicSecCred_t* GetCredResourceData(const OicUuid_t* subject)
+OicSecCred_t* GetCredResourceData(const OicUuid_t* subject)
{
OicSecCred_t *cred = NULL;
return NULL;
}
+const OicSecCred_t* GetCredList()
+{
+ return gCred;
+}
+
+OicSecCred_t* GetCredEntryByCredId(const uint16_t credId)
+{
+ OicSecCred_t *cred = NULL;
+ OicSecCred_t *tmpCred = NULL;
+
+ if ( 1 > credId)
+ {
+ return NULL;
+ }
+
+ LL_FOREACH(gCred, tmpCred)
+ {
+ if(tmpCred->credId == credId)
+ {
+ cred = (OicSecCred_t*)OICCalloc(1, sizeof(OicSecCred_t));
+ VERIFY_NON_NULL(TAG, cred, ERROR);
+
+ // common
+ cred->next = NULL;
+ cred->credId = tmpCred->credId;
+ cred->credType = tmpCred->credType;
+ memcpy(cred->subject.id, tmpCred->subject.id , sizeof(cred->subject.id));
+ memcpy(cred->rownerID.id, tmpCred->rownerID.id , sizeof(cred->rownerID.id));
+ if (tmpCred->period)
+ {
+ cred->period = OICStrdup(tmpCred->period);
+ }
+
+ // key data
+ if (tmpCred->privateData.data)
+ {
+ cred->privateData.data = (uint8_t *)OICCalloc(1, tmpCred->privateData.len);
+ VERIFY_NON_NULL(TAG, cred->privateData.data, ERROR);
+
+ memcpy(cred->privateData.data, tmpCred->privateData.data, tmpCred->privateData.len);
+ cred->privateData.len = tmpCred->privateData.len;
+ cred->privateData.encoding = tmpCred->privateData.encoding;
+ }
+#if defined(__WITH_X509__) || defined(__WITH_TLS__)
+ else if (tmpCred->publicData.data)
+ {
+ cred->publicData.data = (uint8_t *)OICCalloc(1, tmpCred->publicData.len);
+ VERIFY_NON_NULL(TAG, cred->publicData.data, ERROR);
+
+ memcpy(cred->publicData.data, tmpCred->publicData.data, tmpCred->publicData.len);
+ cred->publicData.len = tmpCred->publicData.len;
+ }
+ else if (tmpCred->optionalData.data)
+ {
+ cred->optionalData.data = (uint8_t *)OICCalloc(1, tmpCred->optionalData.len);
+ VERIFY_NON_NULL(TAG, cred->optionalData.data, ERROR);
+
+ memcpy(cred->optionalData.data, tmpCred->optionalData.data, tmpCred->optionalData.len);
+ cred->optionalData.len = tmpCred->optionalData.len;
+ cred->optionalData.encoding = tmpCred->optionalData.encoding;
+ }
+
+ if (tmpCred->credUsage)
+ {
+ cred->credUsage = OICStrdup(tmpCred->credUsage);
+ }
+#endif /* __WITH_X509__ or __WITH_TLS__*/
+
+ return cred;
+ }
+ }
+
+exit:
+ FreeCred(cred);
+ return NULL;
+}
-#if defined(__WITH_DTLS__)
+#if defined(__WITH_DTLS__) || defined(__WITH_TLS__)
int32_t GetDtlsPskCredentials(CADtlsPskCredType_t type,
const uint8_t *desc, size_t desc_len,
uint8_t *result, size_t result_length)
uint32_t outKeySize;
if(NULL == outKey)
{
- OIC_LOG (ERROR, TAG, "Failed to memoray allocation.");
+ OIC_LOG (ERROR, TAG, "Failed to allocate memory.");
return ret;
}
return ret;
}
}
- }
- break;
+ OIC_LOG(DEBUG, TAG, "Can not find subject matched credential.");
- default:
- {
- OIC_LOG (ERROR, TAG, "Wrong value passed for CADtlsPskCredType_t.");
+#ifdef _ENABLE_MULTIPLE_OWNER_
+ const OicSecDoxm_t* doxm = GetDoxmResourceData();
+ if(doxm && doxm->mom && OIC_MULTIPLE_OWNER_DISABLE != doxm->mom->mode)
+ {
+ // in case of multiple owner transfer authentication
+ if(OIC_PRECONFIG_PIN == doxm->oxmSel)
+ {
+ OicSecCred_t* wildCardCred = GetCredResourceData(&WILDCARD_SUBJECT_ID);
+ if(wildCardCred)
+ {
+ OIC_LOG(DEBUG, TAG, "Detected wildcard credential.");
+ if(PIN_PASSWORD == wildCardCred->credType)
+ {
+ //Read PIN/PW
+ char* pinBuffer = NULL;
+ uint32_t pinLength = 0;
+ if(OIC_ENCODING_RAW == wildCardCred->privateData.encoding)
+ {
+ pinBuffer = OICCalloc(1, wildCardCred->privateData.len + 1);
+ if(NULL == pinBuffer)
+ {
+ OIC_LOG (ERROR, TAG, "Failed to allocate memory.");
+ return ret;
+ }
+ pinLength = wildCardCred->privateData.len;
+ memcpy(pinBuffer, wildCardCred->privateData.data, pinLength);
+ }
+ else if(OIC_ENCODING_BASE64 == wildCardCred->privateData.encoding)
+ {
+ size_t pinBufSize = B64DECODE_OUT_SAFESIZE((wildCardCred->privateData.len + 1));
+ pinBuffer = OICCalloc(1, pinBufSize);
+ if(NULL == pinBuffer)
+ {
+ OIC_LOG (ERROR, TAG, "Failed to allocate memory.");
+ return ret;
+ }
+
+ if(B64_OK != b64Decode((char*)wildCardCred->privateData.data, wildCardCred->privateData.len, pinBuffer, pinBufSize, &pinLength))
+ {
+ OIC_LOG (ERROR, TAG, "Failed to base64 decoding.");
+ return ret;
+ }
+ }
+ else
+ {
+ OIC_LOG(ERROR, TAG, "Unknown encoding type of PIN/PW credential.");
+ return ret;
+ }
+
+ //Set the PIN/PW to derive PSK
+ if (OC_STACK_OK != SetPreconfigPin(pinBuffer, pinLength))
+ {
+ OICFree(pinBuffer);
+ OIC_LOG(ERROR, TAG, "Failed to load PIN data.");
+ return ret;
+ }
+ OICFree(pinBuffer);
+
+ OicUuid_t myUuid;
+ if(OC_STACK_OK != GetDoxmDeviceID(&myUuid))
+ {
+ OIC_LOG(ERROR, TAG, "Failed to read device ID");
+ return ret;
+ }
+ SetUuidForPinBasedOxm(&myUuid);
+
+ //Calculate PSK using PIN/PW
+ if(0 == DerivePSKUsingPIN((uint8_t*)result))
+ {
+ ret = OWNER_PSK_LENGTH_128;
+ }
+ else
+ {
+ OIC_LOG_V(ERROR, TAG, "Failed to derive crypto key from PIN");
+ }
+
+ if(CA_STATUS_OK != CAregisterSslHandshakeCallback(MultipleOwnerDTLSHandshakeCB))
+ {
+ OIC_LOG(WARNING, TAG, "Error while bind the DTLS Handshake Callback.");
+ }
+ }
+ }
+ }
+ else if(OIC_RANDOM_DEVICE_PIN == doxm->oxmSel)
+ {
+ if(0 == DerivePSKUsingPIN((uint8_t*)result))
+ {
+ ret = OWNER_PSK_LENGTH_128;
+ }
+ else
+ {
+ OIC_LOG_V(ERROR, TAG, "Failed to derive crypto key from PIN : result");
+ ret = -1;
+ }
+ }
+ }
+#endif //_ENABLE_MULTIPLE_OWNER_
}
break;
}
VERIFY_SUCCESS(TAG, (0 == dtlsRes) , ERROR);
cred = GenerateCredential(tmpSubject, credType, NULL,
- &privKey, rownerID);
+ &privKey, rownerID, NULL);
if(NULL == cred)
{
OIC_LOG(ERROR, TAG, "GeneratePskWithPIN() : Failed to generate credential");
}
#endif /* __WITH_DTLS__ */
-#ifdef __WITH_X509__
-#define CERT_LEN_PREFIX (3)
-#define BYTE_SIZE (8) //bits
-#define PUB_KEY_X_COORD ("x")
-#define PUB_KEY_Y_COORD ("y")
-#define CERTIFICATE ("x5c")
-#define PRIVATE_KEY ("d")
-
-static uint32_t parseCertPrefix(uint8_t *prefix)
-{
- uint32_t res = 0;
- if (NULL != prefix)
- {
- for (int i = 0; i < CERT_LEN_PREFIX; ++i)
- {
- res |= (((uint32_t) prefix[i]) << ((CERT_LEN_PREFIX - 1 -i) * BYTE_SIZE));
- }
- }
- return res;
-}
-
-static OCStackResult GetCAPublicKeyData(CADtlsX509Creds_t *credInfo)
-{
- OCStackResult ret = OC_STACK_ERROR;
- uint8_t *ccPtr = credInfo->certificateChain;
- for (uint8_t i = 0; i < credInfo->chainLen - 1; ++i)
- {
- ccPtr += CERT_LEN_PREFIX + parseCertPrefix(ccPtr);
- }
-
- ByteArray cert = { .data = ccPtr + CERT_LEN_PREFIX, .len = parseCertPrefix(ccPtr) };
- CertificateX509 certStruct;
-
- VERIFY_SUCCESS(TAG, PKI_SUCCESS == DecodeCertificate(cert, &certStruct), ERROR);
-
- INC_BYTE_ARRAY(certStruct.pubKey, 2);
-
- memcpy(credInfo->rootPublicKeyX, certStruct.pubKey.data, PUBLIC_KEY_SIZE / 2);
- memcpy(credInfo->rootPublicKeyY, certStruct.pubKey.data + PUBLIC_KEY_SIZE / 2, PUBLIC_KEY_SIZE / 2);
-
- ret = OC_STACK_OK;
- exit:
- return ret;
-}
-
-int GetDtlsX509Credentials(CADtlsX509Creds_t *credInfo)
-{
- int ret = 1;
- VERIFY_NON_NULL(TAG, credInfo, ERROR);
- if (NULL == gCred)
- {
- VERIFY_SUCCESS(TAG, OC_STACK_OK == InitCredResource(), ERROR);
- }
-
- OicSecCred_t *cred = NULL;
- LL_SEARCH_SCALAR(gCred, cred, credType, SIGNED_ASYMMETRIC_KEY);
- VERIFY_NON_NULL(TAG, cred, ERROR);
-
- if (cred->publicData.len > MAX_CERT_MESSAGE_LEN || cred->privateData.len > PRIVATE_KEY_SIZE)
- {
- goto exit;
- }
- credInfo->chainLen = 2;
- memcpy(credInfo->certificateChain, cred->publicData.data, cred->publicData.len);
- memcpy(credInfo->devicePrivateKey, cred->privateData.data, cred->privateData.len);
- credInfo->certificateChainLen = cred->publicData.len;
- GetCAPublicKeyData(credInfo);
- ret = 0;
-
-exit:
-
- return ret;
-}
-#undef CERT_LEN_PREFIX
-#endif /* __WITH_X509__ */
OCStackResult SetCredRownerId(const OicUuid_t* newROwner)
{
memcpy(prevId.id, gCred->rownerID.id, sizeof(prevId.id));
memcpy(gCred->rownerID.id, newROwner->id, sizeof(newROwner->id));
+ // This added '256' is arbitrary value that is added to cover the name of the resource, map addition and ending
+ size = GetCredKeyDataSize(gCred);
+ size += (256 * OicSecCredCount(gCred));
ret = CredToCBORPayload(gCred, &cborPayload, &size, secureFlag);
VERIFY_SUCCESS(TAG, OC_STACK_OK == ret, ERROR);
}
return retVal;
}
+
+#if defined (__WITH_TLS__) || defined(__WITH_DTLS__)
+void GetDerCaCert(ByteArray_t * crt, const char * usage)
+{
+ OIC_LOG_V(DEBUG, TAG, "In %s", __func__);
+ if (NULL == crt || NULL == usage)
+ {
+ OIC_LOG_V(DEBUG, TAG, "Out %s", __func__);
+ return;
+ }
+ crt->len = 0;
+ OicSecCred_t * temp = NULL;
+
+ LL_FOREACH(gCred, temp)
+ {
+ if (SIGNED_ASYMMETRIC_KEY == temp->credType &&
+ 0 == strcmp(temp->credUsage, usage))
+ {
+ if(OIC_ENCODING_BASE64 == temp->optionalData.encoding)
+ {
+ size_t bufSize = B64DECODE_OUT_SAFESIZE((temp->optionalData.len + 1));
+ uint8 * buf = OICCalloc(1, bufSize);
+ if(NULL == buf)
+ {
+ OIC_LOG(ERROR, TAG, "Failed to allocate memory");
+ return;
+ }
+ uint32_t outSize;
+ if(B64_OK != b64Decode(temp->optionalData.data, temp->optionalData.len, buf, bufSize, &outSize))
+ {
+ OICFree(buf);
+ OIC_LOG(ERROR, TAG, "Failed to decode base64 data");
+ return;
+ }
+ crt->data = OICRealloc(crt->data, crt->len + outSize);
+ memcpy(crt->data + crt->len, buf, outSize);
+ crt->len += outSize;
+ OICFree(buf);
+ }
+ else
+ {
+ crt->data = OICRealloc(crt->data, crt->len + temp->optionalData.len);
+ memcpy(crt->data + crt->len, temp->optionalData.data, temp->optionalData.len);
+ crt->len += temp->optionalData.len;
+ }
+ OIC_LOG_V(DEBUG, TAG, "%s found", usage);
+ }
+ }
+ if(0 == crt->len)
+ {
+ OIC_LOG_V(WARNING, TAG, "%s not found", usage);
+ }
+ OIC_LOG_V(DEBUG, TAG, "Out %s", __func__);
+ return;
+}
+
+void GetDerOwnCert(ByteArray_t * crt, const char * usage)
+{
+ OIC_LOG_V(DEBUG, TAG, "In %s", __func__);
+ if (NULL == crt || NULL == usage)
+ {
+ OIC_LOG_V(DEBUG, TAG, "Out %s", __func__);
+ return;
+ }
+ crt->len = 0;
+ OicSecCred_t * temp = NULL;
+ LL_FOREACH(gCred, temp)
+ {
+ if (SIGNED_ASYMMETRIC_KEY == temp->credType &&
+ 0 == strcmp(temp->credUsage, usage))
+ {
+ crt->data = OICRealloc(crt->data, crt->len + temp->publicData.len);
+ memcpy(crt->data + crt->len, temp->publicData.data, temp->publicData.len);
+ crt->len += temp->publicData.len;
+ OIC_LOG_V(DEBUG, TAG, "%s found", usage);
+ }
+ }
+ if(0 == crt->len)
+ {
+ OIC_LOG_V(WARNING, TAG, "%s not found", usage);
+ }
+ OIC_LOG_V(DEBUG, TAG, "Out %s", __func__);
+ return;
+}
+
+void GetDerKey(ByteArray_t * key, const char * usage)
+{
+ OIC_LOG_V(DEBUG, TAG, "In %s", __func__);
+ if (NULL == key || NULL == usage)
+ {
+ OIC_LOG_V(DEBUG, TAG, "Out %s", __func__);
+ return;
+ }
+
+ OicSecCred_t * temp = NULL;
+ key->len = 0;
+ LL_FOREACH(gCred, temp)
+ {
+ if (SIGNED_ASYMMETRIC_KEY == temp->credType &&
+ 0 == strcmp(temp->credUsage, usage))
+ {
+ key->data = OICRealloc(key->data, key->len + temp->privateData.len);
+ memcpy(key->data + key->len, temp->privateData.data, temp->privateData.len);
+ key->len += temp->privateData.len;
+ OIC_LOG_V(DEBUG, TAG, "Key for %s found", usage);
+ }
+ }
+ if(0 == key->len)
+ {
+ OIC_LOG_V(WARNING, TAG, "Key for %s not found", usage);
+ }
+ OIC_LOG_V(DEBUG, TAG, "Out %s", __func__);
+}
+
+void InitCipherSuiteListInternal(bool * list, const char * usage)
+{
+ OIC_LOG_V(DEBUG, TAG, "In %s", __func__);
+ if (NULL == list || NULL == usage)
+ {
+ OIC_LOG(DEBUG, TAG, "NULL passed");
+ OIC_LOG_V(DEBUG, TAG, "Out %s", __func__);
+ return;
+ }
+ OicSecCred_t * temp = NULL;
+ LL_FOREACH(gCred, temp)
+ {
+ switch (temp->credType)
+ {
+ case PIN_PASSWORD:
+ {
+ list[0] = true;
+ OIC_LOG(DEBUG, TAG, "PIN_PASSWORD found");
+ break;
+ }
+ case SYMMETRIC_PAIR_WISE_KEY:
+ {
+ list[0] = true;
+ OIC_LOG(DEBUG, TAG, "SYMMETRIC_PAIR_WISE_KEY found");
+ break;
+ }
+ case SIGNED_ASYMMETRIC_KEY:
+ {
+ if (0 == strcmp(temp->credUsage, usage))
+ {
+ list[1] = true;
+ OIC_LOG_V(DEBUG, TAG, "SIGNED_ASYMMETRIC_KEY found for %s", usage);
+ }
+ break;
+ }
+ case SYMMETRIC_GROUP_KEY:
+ case ASYMMETRIC_KEY:
+ case ASYMMETRIC_ENCRYPTION_KEY:
+ {
+ OIC_LOG(WARNING, TAG, "Unsupported credential type for TLS.");
+ break;
+ }
+ default:
+ {
+ OIC_LOG(WARNING, TAG, "Unknown credential type for TLS.");
+ break;
+ }
+ }
+ }
+ OIC_LOG_V(DEBUG, TAG, "Out %s", __func__);
+}
+#endif