Merge branch 'upstream' into tizen
[platform/upstream/iotivity.git] / resource / csdk / stack / src / ocpayloadparse.c
index 203986f..4763299 100644 (file)
 //
 //-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
 
-#include "ocpayloadcbor.h"
+// Defining _POSIX_C_SOURCE macro with 200112L (or greater) as value
+// causes header files to expose definitions
+// corresponding to the POSIX.1-2001 base
+// specification (excluding the XSI extension).
+// For POSIX.1-2001 base specification,
+// Refer http://pubs.opengroup.org/onlinepubs/009695399/
+// Required for strok_r
+#define _POSIX_C_SOURCE 200112L
+#include <string.h>
 #include <stdlib.h>
-#include "logger.h"
+#include "oic_string.h"
 #include "oic_malloc.h"
-#include "ocstackinternal.h"
 #include "ocpayload.h"
-#include "cbor.h"
+#include "ocpayloadcbor.h"
+#include "ocstackinternal.h"
+#include "payload_logging.h"
+#include "rdpayload.h"
 
-#define TAG PCF("OCPayloadParse")
+#define TAG "OIC_RI_PAYLOADPARSE"
 
-static OCStackResult OCParseDiscoveryPayload(OCPayload** outPayload, CborValue* arrayVal);
-static OCStackResult OCParseDevicePayload(OCPayload** outPayload, CborValue* arrayVal);
-static OCStackResult OCParsePlatformPayload(OCPayload** outPayload, CborValue* arrayVal);
-static bool OCParseSingleRepPayload(OCRepPayload** outPayload, CborValue* repParent);
-static OCStackResult OCParseRepPayload(OCPayload** outPayload, CborValue* arrayVal);
-static OCStackResult OCParsePresencePayload(OCPayload** outPayload, CborValue* arrayVal);
-static OCStackResult OCParseSecurityPayload(OCPayload** outPayload, CborValue* arrayVal);
+static OCStackResult OCParseDiscoveryPayload(OCPayload **outPayload, CborValue *arrayVal);
+static OCStackResult OCParseDevicePayload(OCPayload **outPayload, CborValue *arrayVal);
+static OCStackResult OCParsePlatformPayload(OCPayload **outPayload, CborValue *arrayVal);
+static CborError OCParseSingleRepPayload(OCRepPayload **outPayload, CborValue *repParent, bool isRoot);
+static OCStackResult OCParseRepPayload(OCPayload **outPayload, CborValue *arrayVal);
+static OCStackResult OCParsePresencePayload(OCPayload **outPayload, CborValue *arrayVal);
+static OCStackResult OCParseSecurityPayload(OCPayload **outPayload, const uint8_t *payload, size_t size);
 
-OCStackResult OCParsePayload(OCPayload** outPayload, const uint8_t* payload, size_t payloadSize)
+OCStackResult OCParsePayload(OCPayload **outPayload, OCPayloadType payloadType,
+        const uint8_t *payload, size_t payloadSize)
 {
-    CborParser parser;
-    CborValue rootValue;
-    bool err = false;
+    OCStackResult result = OC_STACK_MALFORMED_RESPONSE;
+    CborError err;
 
-    OC_LOG_V(INFO, TAG, "CBOR Parsing size: %d", payloadSize, payload);
-    if((err = cbor_parser_init(payload, payloadSize, 0, &parser, &rootValue)) != false)
-    {
-        OC_LOG_V(ERROR, TAG, "CBOR Parser init failed: %d", err);
-        return OC_STACK_ERROR;
-    }
+    VERIFY_PARAM_NON_NULL(TAG, outPayload, "Conversion of outPayload failed");
+    VERIFY_PARAM_NON_NULL(TAG, payload, "Invalid cbor payload value");
 
-    if(!cbor_value_is_array(&rootValue))
-    {
-        OC_LOG_V(ERROR, TAG, "CBOR payload root object is not an array :%x", rootValue.type);
-        return OC_STACK_MALFORMED_RESPONSE;
-    }
+    OIC_LOG_V(INFO, TAG, "CBOR Parsing size: %zu of Payload Type: %d, Payload:",
+            payloadSize, payloadType);
+    OIC_LOG_BUFFER(DEBUG, TAG, payload, payloadSize);
 
-    CborValue arrayValue;
-    // enter the array
-    err = err || cbor_value_enter_container(&rootValue, &arrayValue);
+    CborParser parser;
+    CborValue rootValue;
 
-    int payloadType;
-    err = err || cbor_value_get_int(&arrayValue, &payloadType);
-    err = err || cbor_value_advance_fixed(&arrayValue);
+    err = cbor_parser_init(payload, payloadSize, 0, &parser, &rootValue);
+    VERIFY_CBOR_SUCCESS(TAG, err, "Failed initializing init value")
 
-    if(err)
-    {
-        OC_LOG_V(ERROR, TAG, "CBOR payload parse failed :%d", err);
-        return OC_STACK_MALFORMED_RESPONSE;
-    }
-
-    OCStackResult result = OC_STACK_ERROR;
     switch(payloadType)
     {
         case PAYLOAD_TYPE_DISCOVERY:
-            result = OCParseDiscoveryPayload(outPayload, &arrayValue);
+            result = OCParseDiscoveryPayload(outPayload, &rootValue);
             break;
         case PAYLOAD_TYPE_DEVICE:
-            result = OCParseDevicePayload(outPayload, &arrayValue);
+            result = OCParseDevicePayload(outPayload, &rootValue);
             break;
         case PAYLOAD_TYPE_PLATFORM:
-            result = OCParsePlatformPayload(outPayload, &arrayValue);
+            result = OCParsePlatformPayload(outPayload, &rootValue);
             break;
         case PAYLOAD_TYPE_REPRESENTATION:
-            result = OCParseRepPayload(outPayload, &arrayValue);
+            result = OCParseRepPayload(outPayload, &rootValue);
             break;
         case PAYLOAD_TYPE_PRESENCE:
-            result = OCParsePresencePayload(outPayload, &arrayValue);
+            result = OCParsePresencePayload(outPayload, &rootValue);
             break;
         case PAYLOAD_TYPE_SECURITY:
-            result = OCParseSecurityPayload(outPayload, &arrayValue);
+            result = OCParseSecurityPayload(outPayload, payload, payloadSize);
+            break;
+        case PAYLOAD_TYPE_RD:
+            result = OCRDCborToPayload(&rootValue, outPayload);
             break;
         default:
-            OC_LOG_V(ERROR, TAG, "ParsePayload Type default: %d", payloadType);
-            result = OC_STACK_ERROR;
+            OIC_LOG_V(ERROR, TAG, "ParsePayload Type default: %d", payloadType);
+            result = OC_STACK_INVALID_PARAM;
             break;
     }
 
-    if(result == OC_STACK_OK)
-    {
-        err = err || cbor_value_leave_container(&rootValue, &arrayValue);
-        if(err != CborNoError)
-        {
-            return OC_STACK_MALFORMED_RESPONSE;
-        }
-    }
-    else
-    {
-        OC_LOG_V(INFO, TAG, "Finished parse payload, result is %d", result);
-    }
+    OIC_LOG_V(INFO, TAG, "Finished parse payload, result is %d", result);
 
+exit:
     return result;
 }
 
 void OCFreeOCStringLL(OCStringLL* ll);
 
-static OCStackResult OCParseSecurityPayload(OCPayload** outPayload, CborValue* arrayVal)
+static OCStackResult OCParseSecurityPayload(OCPayload** outPayload, const uint8_t *payload,
+        size_t size)
 {
-    bool err = false;
-    char * securityData = NULL;
-
-    if(cbor_value_is_map(arrayVal))
+    if (size > 0)
     {
-        CborValue curVal;
-        err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_REPRESENTATION, &curVal);
-
-        if(cbor_value_is_valid(&curVal))
-        {
-            size_t len;
-            err = err || cbor_value_dup_text_string(&curVal, &securityData, &len, NULL);
-        }
+        *outPayload = (OCPayload *)OCSecurityPayloadCreate(payload, size);
     }
     else
     {
-        OC_LOG_V(ERROR, TAG, PCF("Cbor main value not a map"));
-        return OC_STACK_MALFORMED_RESPONSE;
+        *outPayload = NULL;
     }
+    return OC_STACK_OK;
+}
 
-    err = err || cbor_value_advance(arrayVal);
-
-    if(err)
+static char* InPlaceStringTrim(char* str)
+{
+    while (str[0] == ' ')
     {
-        OC_LOG_V(ERROR, TAG, "Cbor in error condition");
-        OICFree(securityData);
-        return OC_STACK_MALFORMED_RESPONSE;
+        ++str;
     }
 
-    *outPayload = (OCPayload*)OCSecurityPayloadCreate(securityData);
-    OICFree(securityData);
+    size_t lastchar = strlen(str);
 
-    return OC_STACK_OK;
+    while (str[lastchar] == ' ')
+    {
+        str[lastchar] = '\0';
+        --lastchar;
+    }
 
+    return str;
 }
 
-static OCStackResult OCParseDiscoveryPayload(OCPayload** outPayload, CborValue* arrayVal)
+static CborError OCParseStringLL(CborValue *map, char *type, OCStringLL **resource)
 {
-    bool err = false;
-
-    OCDiscoveryPayload* out = OCDiscoveryPayloadCreate();
+    CborValue val;
+    CborError err = cbor_value_map_find_value(map, type, &val);
+    VERIFY_CBOR_SUCCESS(TAG, err, "to find StringLL TAG");
 
-    if(!out)
+    if (cbor_value_is_array(&val))
     {
-        return OC_STACK_NO_MEMORY;
+        CborValue txtStr;
+        err = cbor_value_enter_container(&val, &txtStr);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to enter container");
+        while (cbor_value_is_text_string(&txtStr))
+        {
+            size_t len = 0;
+            char *input = NULL;
+            err = cbor_value_dup_text_string(&txtStr, &input, &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find StringLL value.");
+            if (input)
+            {
+                char *savePtr = NULL;
+                char *curPtr = strtok_r(input, " ", &savePtr);
+                while (curPtr)
+                {
+                    char *trimmed = InPlaceStringTrim(curPtr);
+                    if (trimmed[0] !='\0')
+                    {
+                        if (!OCResourcePayloadAddStringLL(resource, trimmed))
+                        {
+                            return CborErrorOutOfMemory;
+                        }
+                    }
+                    curPtr = strtok_r(NULL, " ", &savePtr);
+                }
+                OICFree(input);
+            }
+            if (cbor_value_is_text_string(&txtStr))
+            {
+                err = cbor_value_advance(&txtStr);
+                VERIFY_CBOR_SUCCESS(TAG, err, "to advance string value");
+            }
+        }
     }
+exit:
+    return err;
+}
 
-    size_t resourceCount = 0;
-    while(!err &&
-            cbor_value_is_map(arrayVal))
+static OCStackResult OCParseDiscoveryPayload(OCPayload **outPayload, CborValue *rootValue)
+{
+    OCStackResult ret = OC_STACK_INVALID_PARAM;
+    OCResourcePayload *resource = NULL;
+    OCDiscoveryPayload *out = NULL;
+    size_t len = 0;
+    CborError err = CborNoError;
+    *outPayload = NULL;
+
+    VERIFY_PARAM_NON_NULL(TAG, outPayload, "Invalid Parameter outPayload");
+    VERIFY_PARAM_NON_NULL(TAG, rootValue, "Invalid Parameter rootValue");
+    if (cbor_value_is_array(rootValue))
     {
-        OCResourcePayload* resource = (OCResourcePayload*)OICCalloc(1, sizeof(OCResourcePayload));
-        if(!resource)
+        // Root value is already inside the main root array
+        CborValue rootMap;
+        ret = OC_STACK_NO_MEMORY;
+        out = OCDiscoveryPayloadCreate();
+        VERIFY_PARAM_NON_NULL(TAG, out, "Failed error initializing discovery payload");
+
+        // Enter the main root map
+        ret = OC_STACK_MALFORMED_RESPONSE;
+        err = cbor_value_enter_container(rootValue, &rootMap);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to enter root map container");
+
+        // Look for DI
+        CborValue curVal;
+        if (!cbor_value_is_map(&rootMap))
         {
-            OC_LOG_V(ERROR, TAG, "Memory allocation failed");
-            return OC_STACK_NO_MEMORY;
+            OIC_LOG(ERROR, TAG, "Malformed packet!!");
+            goto exit;
+        }
+        err = cbor_value_map_find_value(&rootMap, OC_RSRVD_DEVICE_ID, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find device id tag");
+        if (cbor_value_is_valid(&curVal))
+        {
+            if (cbor_value_is_byte_string(&curVal))
+            {
+                err = cbor_value_dup_byte_string(&curVal, (uint8_t **)&(out->sid), &len, NULL);
+                VERIFY_CBOR_SUCCESS(TAG, err, "to copy device id value");
+            }
+            else if (cbor_value_is_text_string(&curVal))
+            {
+                err = cbor_value_dup_text_string(&curVal, &(out->sid), &len, NULL);
+                VERIFY_CBOR_SUCCESS(TAG, err, "to copy device id value");
+            }
         }
-        CborValue curVal;
-
-        // Uri
-        err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_HREF, &curVal);
-        size_t len;
-        err = err || cbor_value_dup_text_string(&curVal, &(resource->uri), &len, NULL);
 
-        // SID
-        err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_SERVER_INSTANCE_ID, &curVal);
-        err = err || cbor_value_dup_byte_string(&curVal, &(resource->sid), &len, NULL);
+        // BaseURI - Not a mandatory field
+        err = cbor_value_map_find_value(&rootMap, OC_RSRVD_BASE_URI, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find uri tag");
+        if (cbor_value_is_valid(&curVal))
+        {
+            err = cbor_value_dup_text_string(&curVal, &(out->baseURI), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find base uri value");
+        }
 
-        // Prop Tag
+        // HREF - Not a mandatory field
+        err = cbor_value_map_find_value(&rootMap, OC_RSRVD_HREF, &curVal);
+        if (cbor_value_is_valid(&curVal))
         {
-             err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_PROPERTY, &curVal);
-            // ResourceTypes
-            CborValue rtArray;
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_RESOURCE_TYPE, &rtArray);
+            err = cbor_value_dup_text_string(&curVal, &(out->uri), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find uri value");
+        }
 
-            CborValue rtVal;
-             err = err || cbor_value_enter_container(&rtArray, &rtVal);
+        // RT - Not a mandatory field
+        err = cbor_value_map_find_value(&rootMap, OC_RSRVD_RESOURCE_TYPE, &curVal);
+        if (cbor_value_is_valid(&curVal))
+        {
+            err = cbor_value_dup_text_string(&curVal, &(out->type), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find base uri value");
+        }
 
-            OCStringLL* llPtr = NULL;
-            while(!err && cbor_value_is_text_string(&rtVal))
+        // IF - Not a mandatory field
+        err = cbor_value_map_find_value(&rootMap, OC_RSRVD_INTERFACE, &curVal);
+        if (cbor_value_is_valid(&curVal))
+        {
+            err =  OCParseStringLL(&rootMap, OC_RSRVD_INTERFACE, &out->interface);
+        }
+        if (!out->interface)
+        {
+            if (!OCResourcePayloadAddStringLL(&out->interface, OC_RSRVD_INTERFACE_LL))
             {
-                if(resource->types == NULL)
-                {
-                    resource->types = (OCStringLL*)OICCalloc(1, sizeof(OCStringLL));
-                    llPtr = resource->types;
-                    if(!llPtr)
-                    {
-                        OC_LOG_V(ERROR, TAG, "Memory allocation failed");
-                        OICFree(resource->uri);
-                        OICFree(resource->sid);
-                        OICFree(resource);
-                        return OC_STACK_NO_MEMORY;
-                    }
-                }
-                else
-                {
-                    llPtr->next = (OCStringLL*)OICCalloc(1, sizeof(OCStringLL));
-                    llPtr = llPtr->next;
-                    if(!llPtr)
-                    {
-                        OC_LOG_V(ERROR, TAG, "Memory allocation failed");
-                        OICFree(resource->uri);
-                        OICFree(resource->sid);
-                        OCFreeOCStringLL(resource->types);
-                        OICFree(resource);
-                        return OC_STACK_NO_MEMORY;
-                    }
+                err = CborErrorOutOfMemory;
+            }
+        }
 
-                }
+        // Name - Not a mandatory field
+        err = cbor_value_map_find_value(&rootMap, OC_RSRVD_DEVICE_NAME, &curVal);
+        if (cbor_value_is_valid(&curVal))
+        {
+            err = cbor_value_dup_text_string(&curVal, &out->name, &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find device name");
+        }
 
-                 err = err || cbor_value_dup_text_string(&rtVal, &(llPtr->value), &len, NULL);
-                 err = err || cbor_value_advance(&rtVal);
-            }
+        // Look for Links which will have an array as the value
+        CborValue linkMap;
+        err = cbor_value_map_find_value(&rootMap, OC_RSRVD_LINKS, &linkMap);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find links tag");
 
-             err = err || cbor_value_leave_container(&rtArray, &rtVal);
-            //
-            // Interface Types
-            CborValue ifArray;
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_INTERFACE, &ifArray);
-            CborValue ifVal;
-             err = err || cbor_value_enter_container(&ifArray, &ifVal);
+        // Enter the links array and start iterating through the array processing
+        // each resource which shows up as a map.
+        CborValue resourceMap;
+        err = cbor_value_enter_container(&linkMap, &resourceMap);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to enter link map");
+
+        while (cbor_value_is_map(&resourceMap))
+        {
+            resource = (OCResourcePayload *)OICCalloc(1, sizeof(OCResourcePayload));
+            VERIFY_PARAM_NON_NULL(TAG, resource, "Failed allocating resource payload");
+
+            // Uri
+            err = cbor_value_map_find_value(&resourceMap, OC_RSRVD_HREF, &curVal);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find href tag");
+            err = cbor_value_dup_text_string(&curVal, &(resource->uri), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find href value");
 
-            llPtr = NULL;
-            while(!err && cbor_value_is_text_string(&ifVal))
+            // ResourceTypes
+            err =  OCParseStringLL(&resourceMap, OC_RSRVD_RESOURCE_TYPE, &resource->types);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find resource type tag/value");
+
+            // Interface Types
+            err =  OCParseStringLL(&resourceMap, OC_RSRVD_INTERFACE, &resource->interfaces);
+            if (CborNoError != err)
             {
-                if(resource->interfaces == NULL)
-                {
-                    resource->interfaces = (OCStringLL*)OICCalloc(1, sizeof(OCStringLL));
-                    llPtr = resource->interfaces;
-                    if(!llPtr)
-                    {
-                        OC_LOG_V(ERROR, TAG, "Memory allocation failed");
-                        OICFree(resource->uri);
-                        OICFree(resource->sid);
-                        OCFreeOCStringLL(resource->types);
-                        OICFree(resource);
-                        return OC_STACK_NO_MEMORY;
-                    }
-                }
-                else
+                if (!OCResourcePayloadAddStringLL(&resource->interfaces, OC_RSRVD_INTERFACE_LL))
                 {
-                    llPtr->next = (OCStringLL*)OICCalloc(1, sizeof(OCStringLL));
-                    llPtr = llPtr->next;
-                    if(!llPtr)
-                    {
-                        OC_LOG_V(ERROR, TAG, "Memory allocation failed");
-                        OICFree(resource->uri);
-                        OICFree(resource->sid);
-                        OCFreeOCStringLL(resource->types);
-                        OCFreeOCStringLL(resource->interfaces);
-                        OICFree(resource);
-                        return OC_STACK_NO_MEMORY;
-                    }
+                    OIC_LOG(ERROR, TAG, "Failed to add string to StringLL");
+                    goto exit;
                 }
-
-                 err = err || cbor_value_dup_text_string(&ifVal, &(llPtr->value), &len, NULL);
-                 err = err || cbor_value_advance(&ifVal);
             }
-             err = err || cbor_value_leave_container(&ifArray, &ifVal);
 
             // Policy
+            CborValue policyMap;
+            err = cbor_value_map_find_value(&resourceMap, OC_RSRVD_POLICY, &policyMap);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find policy tag");
+
+            // Bitmap
+            err = cbor_value_map_find_value(&policyMap, OC_RSRVD_BITMAP, &curVal);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find bitmap tag");
+            err = cbor_value_get_int(&curVal, (int *)&resource->bitmap);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find bitmap value");
+
+            // Secure Flag
+            err = cbor_value_map_find_value(&policyMap, OC_RSRVD_SECURE, &curVal);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find secure tag");
+            if (cbor_value_is_valid(&curVal))
             {
-                CborValue policyMap;
-                err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_POLICY, &policyMap);
-
-                // Bitmap
-                CborValue val;
-                err = err || cbor_value_map_find_value(&policyMap, OC_RSRVD_BITMAP, &val);
-                uint64_t temp = 0;
-                err = err || cbor_value_get_uint64(&val, &temp);
-                resource->bitmap = (uint8_t)temp;
-                // Secure Flag
-                err = err || cbor_value_map_find_value(&policyMap, OC_RSRVD_SECURE, &val);
-                if(cbor_value_is_valid(&val))
-                {
-                    err = err || cbor_value_get_boolean(&val, &(resource->secure));
-                    // Port
-                    CborValue port;
-                    err = err || cbor_value_map_find_value(&policyMap, OC_RSRVD_HOSTING_PORT,
-                                    &port);
-                    if(cbor_value_is_valid(&port))
-                    {
-                        err = err || cbor_value_get_uint64(&port, &temp);
-                        resource->port = (uint16_t)temp;
-                    }
-                }
+                err = cbor_value_get_boolean(&curVal, &(resource->secure));
+                VERIFY_CBOR_SUCCESS(TAG, err, "to find secure value");
             }
-        }
 
-         err = err || cbor_value_advance(arrayVal);
-        if(err)
-        {
-            OICFree(resource->uri);
-            OICFree(resource->sid);
-            OCFreeOCStringLL(resource->types);
-            OCFreeOCStringLL(resource->interfaces);
-            OICFree(resource);
-            OCDiscoveryPayloadDestroy(out);
-            OC_LOG_V(ERROR, TAG, "CBOR in error condition", err);
-            return OC_STACK_MALFORMED_RESPONSE;
+            // Port
+            err = cbor_value_map_find_value(&policyMap, OC_RSRVD_HOSTING_PORT, &curVal);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find port tag");
+            if (cbor_value_is_valid(&curVal))
+            {
+                err = cbor_value_get_int(&curVal, (int *)&resource->port);
+                VERIFY_CBOR_SUCCESS(TAG, err, "to find port value");
+            }
+
+            err = cbor_value_advance(&resourceMap);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to advance resource map");
+
+            OCDiscoveryPayloadAddNewResource(out, resource);
         }
-        ++resourceCount;
-        OCDiscoveryPayloadAddNewResource(out, resource);
-    }
 
-    *outPayload = (OCPayload*)out;
+        err = cbor_value_leave_container(rootValue, &resourceMap);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to advance resource map");
+    }
+    else
+    {
+        OIC_LOG(ERROR, TAG, "Malformed packet ");
+        goto exit;
+    }
 
+    *outPayload = (OCPayload *)out;
     return OC_STACK_OK;
+
+exit:
+    OCDiscoveryResourceDestroy(resource);
+    OCDiscoveryPayloadDestroy(out);
+    return ret;
 }
 
-static OCStackResult OCParseDevicePayload(OCPayload** outPayload, CborValue* arrayVal)
+static OCStackResult OCParseDevicePayload(OCPayload **outPayload, CborValue *rootValue)
 {
-    bool err = false;
+    OCStackResult ret = OC_STACK_INVALID_PARAM;
+    CborError err = CborNoError;
+    OCDevicePayload *out = NULL;
+    VERIFY_PARAM_NON_NULL(TAG, outPayload, "Invalid param outPayload");
+    VERIFY_PARAM_NON_NULL(TAG, rootValue, "Invalid param rootValue");
+
+    *outPayload = NULL;
 
-    if(cbor_value_is_map(arrayVal))
+    out = (OCDevicePayload *)OICCalloc(1, sizeof(OCDevicePayload));
+    VERIFY_PARAM_NON_NULL(TAG, out, "Failed allocating device payload")
+    out->base.type = PAYLOAD_TYPE_DEVICE;
+    ret = OC_STACK_MALFORMED_RESPONSE;
+
+    if (cbor_value_is_map(rootValue))
     {
-        char* uri = NULL;
-        uint8_t* sid = NULL;
-        char* dname = NULL;
-        char* specVer = NULL;
-        char* dmVer = NULL;
         CborValue curVal;
-         err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_HREF, &curVal);
-        size_t len;
-         err = err || cbor_value_dup_text_string(&curVal, &uri, &len, NULL);
-
-        // Representation
+        // Resource Type
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_RESOURCE_TYPE, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find resource type tag");
+        if (cbor_value_is_valid(&curVal))
         {
-             err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_REPRESENTATION, &curVal);
-
-            CborValue repVal;
-            // Device ID
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_DEVICE_ID, &repVal);
-             err = err || cbor_value_dup_byte_string(&repVal, &sid, &len, NULL);
-            // Device Name
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_DEVICE_NAME, &repVal);
-             err = err || cbor_value_dup_text_string(&repVal, &dname, &len, NULL);
-            // Device Spec Version
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_SPEC_VERSION, &repVal);
-             err = err || cbor_value_dup_text_string(&repVal, &specVer, &len, NULL);
-            // Data Model Version
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_DATA_MODEL_VERSION, &repVal);
-             err = err || cbor_value_dup_text_string(&repVal, &dmVer, &len, NULL);
-
+            err =  OCParseStringLL(rootValue, OC_RSRVD_RESOURCE_TYPE, &out->types);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find rt type tag/value");
         }
 
-         err = err || cbor_value_advance(arrayVal);
-
-        if(err)
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_INTERFACE, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find interface tag");
+        if (cbor_value_is_valid(&curVal))
         {
-            OICFree(uri);
-            OICFree(sid);
-            OICFree(dname);
-            OICFree(specVer);
-            OICFree(dmVer);
-            OC_LOG_V(ERROR, TAG, "CBOR in error condition %d", err);
-            return OC_STACK_MALFORMED_RESPONSE;
+            err =  OCParseStringLL(rootValue, OC_RSRVD_INTERFACE, &out->interfaces);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find interfaces tag/value");
         }
-
-        *outPayload = (OCPayload*)OCDevicePayloadCreate(uri, sid, dname, specVer, dmVer);
-
-        OICFree(uri);
-        OICFree(sid);
-        OICFree(dname);
-        OICFree(specVer);
-        OICFree(dmVer);
-        if(!*outPayload)
+        // Device ID
+        size_t len = 0;
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_DEVICE_ID, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find device id tag");
+        if (cbor_value_is_valid(&curVal))
+        {
+            if (cbor_value_is_byte_string(&curVal))
+            {
+                err = cbor_value_dup_byte_string(&curVal, (uint8_t **)&out->sid, &len, NULL);
+                VERIFY_CBOR_SUCCESS(TAG, err, "to find device id in device payload");
+            }
+            else if (cbor_value_is_text_string(&curVal))
+            {
+                err = cbor_value_dup_text_string(&curVal, &out->sid, &len, NULL);
+                VERIFY_CBOR_SUCCESS(TAG, err, "to find device id in device payload");
+            }
+        }
+        // Device Name
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_DEVICE_NAME, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find device name tag");
+        if (cbor_value_is_valid(&curVal))
+        {
+            err = cbor_value_dup_text_string(&curVal, &out->deviceName, &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find device name in device payload");
+        }
+        // Device Spec Version
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_SPEC_VERSION, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find spec ver tag");
+        if (cbor_value_is_valid(&curVal))
+        {
+            err = cbor_value_dup_text_string(&curVal, &out->specVersion, &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find spec version in device payload");
+        }
+        // Data Model Version
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_DATA_MODEL_VERSION, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find data model ver tag");
+        if (cbor_value_is_valid(&curVal))
         {
-            return OC_STACK_NO_MEMORY;
+            err = cbor_value_dup_text_string(&curVal, &out->dataModelVersion, &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find data model version in device payload");
         }
+        err = cbor_value_advance(rootValue);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to advance device payload");
 
+        *outPayload = (OCPayload *)out;
         return OC_STACK_OK;
     }
-    else
-    {
-        OC_LOG(ERROR, TAG, PCF("Root device node was not a map"));
-        return OC_STACK_MALFORMED_RESPONSE;
-    }
 
+exit:
+    OCDevicePayloadDestroy(out);
+    return ret;
 }
 
-static OCStackResult OCParsePlatformPayload(OCPayload** outPayload, CborValue* arrayVal)
+static OCStackResult OCParsePlatformPayload(OCPayload **outPayload, CborValue *rootValue)
 {
-    bool err = false;
+    OCStackResult ret = OC_STACK_INVALID_PARAM;
+    CborError err = CborNoError;
+    OCPlatformInfo info = {0};
+    char* rt = NULL;
+    OCStringLL* interfaces = NULL;
+    OCPlatformPayload* out = NULL;
 
-    if(cbor_value_is_map(arrayVal))
+    VERIFY_PARAM_NON_NULL(TAG, outPayload, "Invalid Parameter outPayload");
+
+    if (cbor_value_is_map(rootValue))
     {
-        char* uri = NULL;
-        OCPlatformInfo info = {};
-        CborValue curVal;
-         err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_HREF, &curVal);
-        size_t len;
-         err = err || cbor_value_dup_text_string(&curVal, &uri, &len, NULL);
+        CborValue repVal;
+        size_t len = 0;
+        ret = OC_STACK_MALFORMED_RESPONSE;
+
+        // Platform ID
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_PLATFORM_ID, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find platform id tag");
+        if (cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.platformID), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find platformID in the platform payload");
+        }
+         // MFG Name
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_MFG_NAME, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find mfg name tag");
+        if (cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.manufacturerName), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find manufactureName in the platform payload");
+        }
+        // MFG URL
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_MFG_URL, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find mfg url tag");
+        if (cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.manufacturerUrl), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find manufactureUrl in the platform payload");
+        }
+        // Model Num
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_MODEL_NUM, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find model num tag");
+        if (cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.modelNumber), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find modelNumber in the platform payload");
+        }
+        // Date of Mfg
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_MFG_DATE, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find mfg date tag");
+        if (cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.dateOfManufacture), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find dateOfManufacture in the platform payload");
+        }
+        // Platform Version
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_PLATFORM_VERSION, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find platform ver tag");
+        if (cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.platformVersion), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find platformVersion in the platform payload");
+        }
+        // OS Version
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_OS_VERSION, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find os ver tag");
+        if (cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.operatingSystemVersion), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find OSVersion in the platform payload");
+        }
+        // Hardware Version
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_HARDWARE_VERSION, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find hw ver tag");
+        if(cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.hardwareVersion), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find HWVersion in the platform payload");
+        }
+        // Firmware Version
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_FIRMWARE_VERSION, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find fw ver tag");
+        if(cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.firmwareVersion), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find firmwareVersion in the platform payload");
+        }
+        // Support URL
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_SUPPORT_URL, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find support url tag");
+        if(cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.supportUrl), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find supportUrl in the platform payload");
+        }
+        // System Time
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_SYSTEM_TIME, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find sys time tag");
+        if(cbor_value_is_valid(&repVal))
+        {
+            err = cbor_value_dup_text_string(&repVal, &(info.systemTime), &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find systemTume in the platform payload");
+        }
 
-        // Representation
+        // Resource type
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_RESOURCE_TYPE, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find resource type tag");
+        if(cbor_value_is_valid(&repVal))
         {
-             err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_REPRESENTATION, &curVal);
+            err = cbor_value_dup_text_string(&repVal, &rt, &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find resource type in the platform payload");
+        }
 
-            CborValue repVal;
-            // Platform ID
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_PLATFORM_ID, &repVal);
-             err = err || cbor_value_dup_text_string(&repVal, &(info.platformID), &len, NULL);
+        // Interface Types
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_INTERFACE, &repVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find interface tag");
+        if(cbor_value_is_valid(&repVal))
+        {
+            err =  OCParseStringLL(rootValue, OC_RSRVD_INTERFACE, &interfaces);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find interfaces tag/value");
+        }
 
-            // MFG Name
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_MFG_NAME, &repVal);
-             err = err || cbor_value_dup_text_string(&repVal, &(info.manufacturerName), &len, NULL);
+        err = cbor_value_advance(rootValue);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find supportUrl in the platform payload");
 
-            // MFG URL
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_MFG_URL, &repVal);
-            if(cbor_value_is_valid(&repVal))
-            {
-                 err = err || cbor_value_dup_text_string(&repVal, &(info.manufacturerUrl), &len, NULL);
-            }
+       out = (OCPlatformPayload *)OCPlatformPayloadCreateAsOwner(&info);
+       out->rt = rt;
+       out->interfaces = interfaces;
+       *outPayload = (OCPayload *)out;
+       OIC_LOG_PAYLOAD(DEBUG, *outPayload);
+       return OC_STACK_OK;
+    }
 
-            // Model Num
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_MODEL_NUM, &repVal);
-            if(cbor_value_is_valid(&repVal))
-            {
-                 err = err || cbor_value_dup_text_string(&repVal, &(info.modelNumber), &len, NULL);
-            }
+exit:
+    OCPlatformInfoDestroy(&info);
+    OIC_LOG(ERROR, TAG, "CBOR error In ParsePlatformPayload");
+    return ret;
+}
 
-            // Date of Mfg
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_MFG_DATE, &repVal);
-            if(cbor_value_is_valid(&repVal))
-            {
-                 err = err || cbor_value_dup_text_string(&repVal, &(info.dateOfManufacture), &len,
-                        NULL);
-            }
+static OCRepPayloadPropType DecodeCborType(CborType type)
+{
+    switch (type)
+    {
+        case CborNullType:
+            return OCREP_PROP_NULL;
+        case CborIntegerType:
+            return OCREP_PROP_INT;
+        case CborDoubleType:
+        case CborFloatType:
+            return OCREP_PROP_DOUBLE;
+        case CborBooleanType:
+            return OCREP_PROP_BOOL;
+        case CborTextStringType:
+            return OCREP_PROP_STRING;
+        case CborByteStringType:
+            return OCREP_PROP_BYTE_STRING;
+        case CborMapType:
+            return OCREP_PROP_OBJECT;
+        case CborArrayType:
+            return OCREP_PROP_ARRAY;
+        default:
+            return OCREP_PROP_NULL;
+    }
+}
+static CborError OCParseArrayFindDimensionsAndType(const CborValue *parent,
+        size_t dimensions[MAX_REP_ARRAY_DEPTH], OCRepPayloadPropType *type)
+{
+    CborValue insideArray;
+    *type = OCREP_PROP_NULL;
+    dimensions[0] = dimensions[1] = dimensions[2] = 0;
 
-            // Platform Version
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_PLATFORM_VERSION, &repVal);
-            if(cbor_value_is_valid(&repVal))
-            {
-                 err = err || cbor_value_dup_text_string(&repVal, &(info.platformVersion), &len,
-                        NULL);
-            }
+    CborError err = cbor_value_enter_container(parent, &insideArray);
+    VERIFY_CBOR_SUCCESS(TAG, err, "Failed to enter container");
 
-            // OS Version
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_OS_VERSION, &repVal);
-            if(cbor_value_is_valid(&repVal))
-            {
-                 err = err || cbor_value_dup_text_string(&repVal, &(info.operatingSystemVersion),
-                        &len, NULL);
-            }
+    while (cbor_value_is_valid(&insideArray))
+    {
+        OCRepPayloadPropType tempType = DecodeCborType(cbor_value_get_type(&insideArray));
 
-            // Hardware Version
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_HARDWARE_VERSION, &repVal);
-            if(cbor_value_is_valid(&repVal))
-            {
-                 err = err || cbor_value_dup_text_string(&repVal, &(info.hardwareVersion), &len,
-                        NULL);
-            }
+        if (tempType == OCREP_PROP_ARRAY)
+        {
+            size_t subdim[MAX_REP_ARRAY_DEPTH];
+            tempType = OCREP_PROP_NULL;
+            err = OCParseArrayFindDimensionsAndType(&insideArray, subdim, &tempType);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to parse array");
 
-            // Firmware Version
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_FIRMWARE_VERSION, &repVal);
-            if(cbor_value_is_valid(&repVal))
+            if (subdim[2] != 0)
             {
-                 err = err || cbor_value_dup_text_string(&repVal, &(info.firmwareVersion), &len,
-                        NULL);
+                OIC_LOG(ERROR, TAG, "Parse array helper, sub-array too deep");
             }
 
-            // Support URL
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_SUPPORT_URL, &repVal);
-            if(cbor_value_is_valid(&repVal))
+            dimensions[1] = dimensions[1] >= subdim[0] ? dimensions[1] : subdim[0];
+            dimensions[2] = dimensions[2] >= subdim[1] ? dimensions[2] : subdim[1];
+
+            if (*type != OCREP_PROP_NULL && tempType != OCREP_PROP_NULL && *type != tempType)
             {
-                 err = err || cbor_value_dup_text_string(&repVal, &(info.supportUrl), &len, NULL);
+                OIC_LOG(ERROR, TAG, "Array parse failed, mixed arrays not allowed (subtype)");
+                return CborUnknownError;
             }
-
-            // System Time
-             err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_SYSTEM_TIME, &repVal);
-            if(cbor_value_is_valid(&repVal))
+            else if (*type == OCREP_PROP_NULL)
             {
-                 err = err || cbor_value_dup_text_string(&repVal, &(info.systemTime), &len, NULL);
+                // We don't know the type of this array yet, so the assignment is OK
+                *type = tempType;
             }
         }
-
-         err = err || cbor_value_advance(arrayVal);
-
-        if(err)
+        else if (*type == OCREP_PROP_NULL)
         {
-            OICFree(info.dateOfManufacture);
-            OICFree(info.firmwareVersion);
-            OICFree(info.hardwareVersion);
-            OICFree(info.manufacturerName);
-            OICFree(info.manufacturerUrl);
-            OICFree(info.modelNumber);
-            OICFree(info.operatingSystemVersion);
-            OICFree(info.platformID);
-            OICFree(info.platformVersion);
-            OICFree(info.supportUrl);
-            OICFree(info.systemTime);
-            OC_LOG(ERROR, TAG, PCF("CBOR error In ParsePlatformPayload"));
-            return OC_STACK_MALFORMED_RESPONSE;
+            // We don't know the type of this array yet, so the assignment is OK
+            *type = tempType;
         }
-
-        *outPayload = (OCPayload*)OCPlatformPayloadCreateAsOwner(uri, &info);
-
-        if(!*outPayload)
+        // tempType is allowed to be NULL, since it might now know the answer yet
+        else if (tempType != OCREP_PROP_NULL && *type != tempType)
         {
-            return OC_STACK_NO_MEMORY;
+            // this is an invalid situation!
+            OIC_LOG(ERROR, TAG, "Array parse failed, mixed arrays not allowed");
+            return CborUnknownError;
         }
 
-        return OC_STACK_OK;
+        ++dimensions[0];
+        err = cbor_value_advance(&insideArray);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed to advance array");
     }
-    else
+
+exit:
+    return err;
+}
+
+static size_t getAllocSize(OCRepPayloadPropType type)
+{
+    switch (type)
     {
-        OC_LOG(ERROR, TAG, PCF("Root device node was not a map"));
-        return OC_STACK_MALFORMED_RESPONSE;
+        case OCREP_PROP_INT:
+            return sizeof (int64_t);
+        case OCREP_PROP_DOUBLE:
+            return sizeof (double);
+        case OCREP_PROP_BOOL:
+            return sizeof (bool);
+        case OCREP_PROP_STRING:
+            return sizeof (char*);
+        case OCREP_PROP_BYTE_STRING:
+            return sizeof (OCByteString);
+        case OCREP_PROP_OBJECT:
+            return sizeof (OCRepPayload*);
+        default:
+            return 0;
     }
 }
 
-static bool OCParseArray(OCRepPayload* out, const char* name, CborValue* container)
+static size_t arrayStep(size_t dimensions[MAX_REP_ARRAY_DEPTH], size_t elementNum)
+{
+    return
+        (dimensions[1] == 0 ? 1 : dimensions[1]) *
+        (dimensions[2] == 0 ? 1 : dimensions[2]) *
+        elementNum;
+}
+
+static CborError OCParseArrayFillArray(const CborValue *parent,
+        size_t dimensions[MAX_REP_ARRAY_DEPTH], OCRepPayloadPropType type, void *targetArray)
 {
     CborValue insideArray;
-    bool err = false;
-    uint64_t tempInt = 0;
+
+    size_t i = 0;
+    char *tempStr = NULL;
+    OCByteString ocByteStr = { .bytes = NULL, .len = 0};
+    size_t tempLen = 0;
+    OCRepPayload *tempPl = NULL;
+
+    size_t newdim[MAX_REP_ARRAY_DEPTH];
+    newdim[0] = dimensions[1];
+    newdim[1] = dimensions[2];
+    newdim[2] = 0;
+
+    CborError err = cbor_value_enter_container(parent, &insideArray);
+    VERIFY_CBOR_SUCCESS(TAG, err, "Failed to enter container");
+
+    while (!err && i < dimensions[0] && cbor_value_is_valid(&insideArray))
+    {
+        bool noAdvance = false;
+        if (cbor_value_get_type(&insideArray) != CborNullType)
+        {
+            switch (type)
+            {
+                case OCREP_PROP_INT:
+                    if (dimensions[1] == 0)
+                    {
+                        err = cbor_value_get_int64(&insideArray, &(((int64_t*)targetArray)[i]));
+                    }
+                    else
+                    {
+                        err = OCParseArrayFillArray(&insideArray, newdim, type,
+                            &(((int64_t*)targetArray)[arrayStep(dimensions, i)]));
+                    }
+                    break;
+                case OCREP_PROP_DOUBLE:
+                    if (dimensions[1] == 0)
+                    {
+                        double *d = &(((double*)targetArray)[i]);
+                        if (cbor_value_get_type(&insideArray) == CborDoubleType)
+                        {
+                            err = cbor_value_get_double(&insideArray, d);
+                        }
+                        else
+                        {
+                            /* must be float */
+                            float f;
+                            err = cbor_value_get_float(&insideArray, &f);
+                            if (!err)
+                                *d = f;
+                        }
+                    }
+                    else
+                    {
+                        err = OCParseArrayFillArray(&insideArray, newdim, type,
+                            &(((double*)targetArray)[arrayStep(dimensions, i)]));
+                    }
+                    break;
+                case OCREP_PROP_BOOL:
+                    if (dimensions[1] == 0)
+                    {
+                        err = cbor_value_get_boolean(&insideArray, &(((bool*)targetArray)[i]));
+                    }
+                    else
+                    {
+                        err = OCParseArrayFillArray(&insideArray, newdim, type,
+                            &(((bool*)targetArray)[arrayStep(dimensions, i)]));
+                    }
+                    break;
+                case OCREP_PROP_STRING:
+                    if (dimensions[1] == 0)
+                    {
+                        err = cbor_value_dup_text_string(&insideArray, &tempStr, &tempLen, NULL);
+                        ((char**)targetArray)[i] = tempStr;
+                        tempStr = NULL;
+                    }
+                    else
+                    {
+                        err = OCParseArrayFillArray(&insideArray, newdim, type,
+                            &(((char**)targetArray)[arrayStep(dimensions, i)]));
+                    }
+                    break;
+                case OCREP_PROP_BYTE_STRING:
+                    if (dimensions[1] == 0)
+                    {
+                        err = cbor_value_dup_byte_string(&insideArray, &(ocByteStr.bytes),
+                                &(ocByteStr.len), NULL);
+                        ((OCByteString*)targetArray)[i] = ocByteStr;
+                    }
+                    else
+                    {
+                        err = OCParseArrayFillArray(&insideArray, newdim, type,
+                                &(((OCByteString*)targetArray)[arrayStep(dimensions, i)]));
+                    }
+                    break;
+                case OCREP_PROP_OBJECT:
+                    if (dimensions[1] == 0)
+                    {
+                        err = OCParseSingleRepPayload(&tempPl, &insideArray, false);
+                        ((OCRepPayload**)targetArray)[i] = tempPl;
+                        tempPl = NULL;
+                        noAdvance = true;
+                    }
+                    else
+                    {
+                        err = OCParseArrayFillArray(&insideArray, newdim, type,
+                            &(((OCRepPayload**)targetArray)[arrayStep(dimensions, i)]));
+                    }
+                    break;
+                default:
+                    OIC_LOG(ERROR, TAG, "Invalid Array type in Parse Array");
+                    err = CborErrorUnknownType;
+                    break;
+            }
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed setting repPayload");
+        }
+        ++i;
+        if (!noAdvance && cbor_value_is_valid(&insideArray))
+        {
+            err = cbor_value_advance(&insideArray);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed advnce insideArray");
+        }
+    }
+
+exit:
+    return err;
+}
+
+static CborError OCParseArray(OCRepPayload *out, const char *name, CborValue *container)
+{
+    void *arr = NULL;
     OCRepPayloadPropType type;
     size_t dimensions[MAX_REP_ARRAY_DEPTH];
-    err = err || cbor_value_enter_container(container, &insideArray);
+    size_t dimTotal = 0;
+    size_t allocSize = 0;
+    bool res = true;
+    CborError err = OCParseArrayFindDimensionsAndType(container, dimensions, &type);
+    VERIFY_CBOR_SUCCESS(TAG, err, "Array details weren't clear");
 
-    err = err || cbor_value_get_uint64(&insideArray, &tempInt);
-    err = err || cbor_value_advance_fixed(&insideArray);
-    type = (OCRepPayloadPropType)tempInt;
-
-    for(int i = 0; i < MAX_REP_ARRAY_DEPTH; ++ i)
+    if (type == OCREP_PROP_NULL)
     {
-         err = err || cbor_value_get_uint64(&insideArray, &tempInt);
-         err = err || cbor_value_advance_fixed(&insideArray);
-        dimensions[i] = tempInt;
+        res = OCRepPayloadSetNull(out, name);
+        err = (CborError) !res;
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed setting value");
+        err = cbor_value_advance(container);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed advancing container");
+        return err;
     }
 
-    size_t dimTotal = calcDimTotal(dimensions);
+    dimTotal = calcDimTotal(dimensions);
+    allocSize = getAllocSize(type);
+    arr = OICCalloc(dimTotal, allocSize);
+    VERIFY_PARAM_NON_NULL(TAG, arr, "Array Parse allocation failed");
+
+    res = OCParseArrayFillArray(container, dimensions, type, arr);
+    VERIFY_CBOR_SUCCESS(TAG, err, "Failed parse array");
 
-    void* arr = NULL;
-    char* tempStr;
-    size_t len;
-    OCRepPayload* pl;
-    switch(type)
+    switch (type)
     {
         case OCREP_PROP_INT:
-            arr = (int64_t*)OICMalloc(dimTotal * sizeof(int64_t));
-            for(size_t i = 0; i < dimTotal && !err; ++i)
-            {
-                 err = err || cbor_value_get_int64(&insideArray, &(((int64_t*)arr)[i]));
-                 err = err || cbor_value_advance_fixed(&insideArray);
-            }
-            if(!err &&
-                OCRepPayloadSetIntArrayAsOwner(out, name, (int64_t*)arr, dimensions))
-            {}
-            else
-            {
-                err = CborUnknownError;
-            }
+            res = OCRepPayloadSetIntArrayAsOwner(out, name, (int64_t *)arr, dimensions);
             break;
         case OCREP_PROP_DOUBLE:
-            arr = (double*)OICMalloc(dimTotal * sizeof(double));
-            for(size_t i = 0; i < dimTotal && !err; ++i)
-            {
-                 err = err || cbor_value_get_double(&insideArray, &(((double*)arr)[i]));
-                 err = err || cbor_value_advance_fixed(&insideArray);
-            }
-            if(!err &&
-                OCRepPayloadSetDoubleArrayAsOwner(out, name, (double*)arr, dimensions))
-            {}
-            else
-            {
-                err = CborUnknownError;
-            }
+            res = OCRepPayloadSetDoubleArrayAsOwner(out, name, (double *)arr, dimensions);
             break;
         case OCREP_PROP_BOOL:
-            arr = (bool*)OICMalloc(dimTotal * sizeof(bool));
-            for(size_t i = 0; i < dimTotal && !err; ++i)
-            {
-                 err = err || cbor_value_get_boolean(&insideArray, &(((bool*)arr)[i]));
-                 err = err || cbor_value_advance_fixed(&insideArray);
-            }
-            if(!err &&
-                OCRepPayloadSetBoolArrayAsOwner(out, name, (bool*)arr, dimensions))
-            {}
-            else
-            {
-                err = CborUnknownError;
-            }
+            res = OCRepPayloadSetBoolArrayAsOwner(out, name, (bool *)arr, dimensions);
             break;
         case OCREP_PROP_STRING:
-            arr = (char**)OICMalloc(dimTotal * sizeof(char*));
-            for(size_t i = 0; i < dimTotal && !err; ++i)
-            {
-                err = err || cbor_value_dup_text_string(&insideArray, &tempStr, &len, NULL);
-                ((char**) arr)[i] = tempStr;
-                err = err || cbor_value_advance(&insideArray);
-            }
-            if(!err &&
-                OCRepPayloadSetStringArrayAsOwner(out, name, (char**)arr, dimensions))
-            {}
-            else
-            {
-                err = CborUnknownError;
-            }
+            res = OCRepPayloadSetStringArrayAsOwner(out, name, (char **)arr, dimensions);
+            break;
+        case OCREP_PROP_BYTE_STRING:
+            res = OCRepPayloadSetByteStringArrayAsOwner(out, name, (OCByteString *)arr, dimensions);
             break;
         case OCREP_PROP_OBJECT:
-            arr = (OCRepPayload**)OICMalloc(dimTotal * sizeof(OCRepPayload*));
-            for(size_t i = 0; i < dimTotal && !err; ++i)
-            {
-                pl = NULL;
-                 err = err || OCParseSingleRepPayload(&pl, &insideArray);
-                ((OCRepPayload**)arr)[i] = pl;
-                 err = err || cbor_value_advance(&insideArray);
-            }
-            if(!err &&
-                OCRepPayloadSetPropObjectArrayAsOwner(out, name, (OCRepPayload**)arr, dimensions))
-            {}
-            else
-            {
-                err = CborUnknownError;
-            }
+            res = OCRepPayloadSetPropObjectArrayAsOwner(out, name, (OCRepPayload**)arr, dimensions);
             break;
         default:
-            OC_LOG(ERROR, TAG, "Invalid Array type in Parse Array");
-            err = CborUnknownError;
+            OIC_LOG(ERROR, TAG, "Invalid Array type in Parse Array");
             break;
     }
-
-    return err;
-}
-
-static bool OCParseSingleRepPayload(OCRepPayload** outPayload, CborValue* repParent)
-{
-    *outPayload = OCRepPayloadCreate();
-    OCRepPayload* curPayload = *outPayload;
-    bool err = false;
-    if(!*outPayload)
+    err = (CborError) !res;
+    VERIFY_CBOR_SUCCESS(TAG, err, "Failed setting array parameter");
+    return CborNoError;
+exit:
+    if (type == OCREP_PROP_STRING)
     {
-        return CborErrorOutOfMemory;
+        for(size_t i = 0; i < dimTotal; ++i)
+        {
+            OICFree(((char**)arr)[i]);
+        }
     }
-
-    size_t len;
-    CborValue curVal;
-    err = err || cbor_value_map_find_value(repParent, OC_RSRVD_HREF, &curVal);
-    if(cbor_value_is_valid(&curVal))
+    if (type == OCREP_PROP_BYTE_STRING)
     {
-        err = err || cbor_value_dup_text_string(&curVal, &curPayload->uri, &len,
-            NULL);
+        for(size_t i = 0; i < dimTotal; ++i)
+        {
+            OICFree(((OCByteString*)arr)[i].bytes);
+        }
     }
-
-    err = err || cbor_value_map_find_value(repParent, OC_RSRVD_PROPERTY, &curVal);
-    if(cbor_value_is_valid(&curVal))
+    if (type == OCREP_PROP_OBJECT)
     {
-        CborValue insidePropArray;
-        err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_RESOURCE_TYPE,
-                &insidePropArray);
-
-        if(cbor_value_is_array(&insidePropArray))
+        for(size_t i = 0; i < dimTotal; ++i)
         {
-            CborValue rtArray;
-            err = err || cbor_value_enter_container(&insidePropArray, &rtArray);
-
-            while(!err && cbor_value_is_valid(&rtArray))
-            {
-                char* curRt;
-                err = err || cbor_value_dup_text_string(&rtArray, &curRt, &len, NULL);
-                err = err || cbor_value_advance(&rtArray);
-                OCRepPayloadAddResourceTypeAsOwner(curPayload, curRt);
-            }
-
-            err = err || cbor_value_leave_container(&insidePropArray, &rtArray);
+            OCRepPayloadDestroy(((OCRepPayload**)arr)[i]);
         }
+    }
+    OICFree(arr);
+    return err;
+}
 
-        err = err || cbor_value_map_find_value(&curVal, OC_RSRVD_INTERFACE, &insidePropArray);
+static CborError OCParseSingleRepPayload(OCRepPayload **outPayload, CborValue *objMap, bool isRoot)
+{
+    CborError err = CborUnknownError;
+    char *name = NULL;
+    bool res = false;
+    VERIFY_PARAM_NON_NULL(TAG, outPayload, "Invalid Parameter outPayload");
+    VERIFY_PARAM_NON_NULL(TAG, objMap, "Invalid Parameter objMap");
 
-        if(cbor_value_is_array(&insidePropArray))
+    if (cbor_value_is_map(objMap))
+    {
+        if (!*outPayload)
         {
-            CborValue ifArray;
-            err = err || cbor_value_enter_container(&insidePropArray, &ifArray);
-
-            while(!err && cbor_value_is_valid(&ifArray))
+            *outPayload = OCRepPayloadCreate();
+            if (!*outPayload)
             {
-                char* curIf;
-                err = err || cbor_value_dup_text_string(&ifArray, &curIf, &len, NULL);
-                err = err || cbor_value_advance(&ifArray);
-                OCRepPayloadAddInterfaceAsOwner(curPayload, curIf);
+                return CborErrorOutOfMemory;
             }
-
-            err = err || cbor_value_leave_container(&insidePropArray, &ifArray);
         }
-    }
-    err = err || cbor_value_map_find_value(repParent, OC_RSRVD_REPRESENTATION, &curVal);
-    if(cbor_value_is_map(&curVal))
-    {
-        CborValue repMap;
-        err = err || cbor_value_enter_container(&curVal, &repMap);
-
-        while(!err && cbor_value_is_valid(&repMap))
-        {
-            char* name;
-             err = err || cbor_value_dup_text_string(&repMap, &name, &len, NULL);
 
-             err = err || cbor_value_advance(&repMap);
+        OCRepPayload *curPayload = *outPayload;
 
-            int64_t intval = 0;
-            bool boolval = false;
-            char* strval = NULL;
-            double doubleval = 0;
-            OCRepPayload* pl;
+        size_t len = 0;
+        CborValue repMap;
+        err = cbor_value_enter_container(objMap, &repMap);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed entering repMap");
 
-            switch(cbor_value_get_type(&repMap))
+        while (!err && cbor_value_is_valid(&repMap))
+        {
+            if (cbor_value_is_text_string(&repMap))
+            {
+                err = cbor_value_dup_text_string(&repMap, &name, &len, NULL);
+                VERIFY_CBOR_SUCCESS(TAG, err, "Failed finding tag name in the map");
+                err = cbor_value_advance(&repMap);
+                VERIFY_CBOR_SUCCESS(TAG, err, "Failed advancing rootMap");
+                if (name &&
+                    isRoot &&
+                    ((0 == strcmp(OC_RSRVD_HREF, name)) ||
+                     (0 == strcmp(OC_RSRVD_RESOURCE_TYPE, name)) ||
+                    (0 == strcmp(OC_RSRVD_INTERFACE, name))))
+                {
+                    err = cbor_value_advance(&repMap);
+                    OICFree(name);
+                    continue;
+                }
+            }
+            CborType type = cbor_value_get_type(&repMap);
+            switch (type)
             {
                 case CborNullType:
-                    OCRepPayloadSetNull(curPayload, name);
+                    res = OCRepPayloadSetNull(curPayload, name);
                     break;
                 case CborIntegerType:
-                    err = err || cbor_value_get_int64(&repMap, &intval);
-                    OCRepPayloadSetPropInt(curPayload, name, intval);
+                    {
+                        int64_t intval = 0;
+                        err = cbor_value_get_int64(&repMap, &intval);
+                        VERIFY_CBOR_SUCCESS(TAG, err, "Failed getting int value");
+                        res = OCRepPayloadSetPropInt(curPayload, name, intval);
+                    }
                     break;
                 case CborDoubleType:
-                    err = err || cbor_value_get_double(&repMap, &doubleval);
-                    OCRepPayloadSetPropDouble(curPayload, name, doubleval);
+                    {
+                        double doubleval = 0;
+                        err = cbor_value_get_double(&repMap, &doubleval);
+                        VERIFY_CBOR_SUCCESS(TAG, err, "Failed getting double value");
+                        res = OCRepPayloadSetPropDouble(curPayload, name, doubleval);
+                    }
                     break;
                 case CborBooleanType:
-                    err = err || cbor_value_get_boolean(&repMap, &boolval);
-                    OCRepPayloadSetPropBool(curPayload, name, boolval);
+                    {
+                        bool boolval = false;
+                        err = cbor_value_get_boolean(&repMap, &boolval);
+                        VERIFY_CBOR_SUCCESS(TAG, err, "Failed getting boolean value");
+                        res = OCRepPayloadSetPropBool(curPayload, name, boolval);
+                    }
                     break;
                 case CborTextStringType:
-                    err = err || cbor_value_dup_text_string(&repMap, &strval, &len, NULL);
-                    OCRepPayloadSetPropStringAsOwner(curPayload, name, strval);
+                    {
+                        char *strval = NULL;
+                        err = cbor_value_dup_text_string(&repMap, &strval, &len, NULL);
+                        VERIFY_CBOR_SUCCESS(TAG, err, "Failed getting string value");
+                        res = OCRepPayloadSetPropStringAsOwner(curPayload, name, strval);
+                    }
+                    break;
+                case CborByteStringType:
+                    {
+                        uint8_t* bytestrval = NULL;
+                        err = cbor_value_dup_byte_string(&repMap, &bytestrval, &len, NULL);
+                        VERIFY_CBOR_SUCCESS(TAG, err, "Failed getting byte string value");
+                        OCByteString tmp = {.bytes = bytestrval, .len = len};
+                        res = OCRepPayloadSetPropByteStringAsOwner(curPayload, name, &tmp);
+                    }
                     break;
                 case CborMapType:
-                    err = err || OCParseSingleRepPayload(&pl, &repMap);
-                    OCRepPayloadSetPropObjectAsOwner(curPayload, name, pl);
+                    {
+                        OCRepPayload *pl = NULL;
+                        err = OCParseSingleRepPayload(&pl, &repMap, false);
+                        VERIFY_CBOR_SUCCESS(TAG, err, "Failed setting parse single rep");
+                        res = OCRepPayloadSetPropObjectAsOwner(curPayload, name, pl);
+                    }
                     break;
                 case CborArrayType:
-                    err = err || OCParseArray(curPayload, name, &repMap);
+                    err = OCParseArray(curPayload, name, &repMap);
                     break;
                 default:
-                    OC_LOG_V(ERROR, TAG, "Parsing rep property, unknown type %d", repMap.type);
-                    err = true;
+                    OIC_LOG_V(ERROR, TAG, "Parsing rep property, unknown type %d", repMap.type);
+                    res = false;
+            }
+            if (type != CborArrayType)
+            {
+                err = (CborError) !res;
             }
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed setting value");
 
-             err = err || cbor_value_advance(&repMap);
+            if (type != CborMapType && cbor_value_is_valid(&repMap))
+            {
+                err = cbor_value_advance(&repMap);
+                VERIFY_CBOR_SUCCESS(TAG, err, "Failed advance repMap");
+            }
             OICFree(name);
+            name = NULL;
         }
-        err = err || cbor_value_leave_container(&curVal, &repMap);
-    }
-
-    if(err)
-    {
-        OCRepPayloadDestroy(*outPayload);
-        *outPayload = NULL;
+        if (cbor_value_is_container(objMap))
+        {
+            err = cbor_value_leave_container(objMap, &repMap);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to leave container");
+        }
+        return err;
     }
 
+exit:
+    OICFree(name);
+    OCRepPayloadDestroy(*outPayload);
+    *outPayload = NULL;
     return err;
 }
-static OCStackResult OCParseRepPayload(OCPayload** outPayload, CborValue* arrayVal)
-{
-    bool err = false;
 
-    OCRepPayload* rootPayload = NULL;
-    OCRepPayload* curPayload = NULL;
-    OCRepPayload* temp = NULL;
-    while(!err && cbor_value_is_map(arrayVal))
+static OCStackResult OCParseRepPayload(OCPayload **outPayload, CborValue *root)
+{
+    OCStackResult ret = OC_STACK_INVALID_PARAM;
+    CborError err;
+    OCRepPayload *temp = NULL;
+    OCRepPayload *rootPayload = NULL;
+    OCRepPayload *curPayload = NULL;
+    CborValue rootMap = *root;
+    VERIFY_PARAM_NON_NULL(TAG, outPayload, "Invalid Parameter outPayload");
+    VERIFY_PARAM_NON_NULL(TAG, root, "Invalid Parameter root");
+
+    *outPayload = NULL;
+    if (cbor_value_is_array(root))
+    {
+        err = cbor_value_enter_container(root, &rootMap);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed entering repMap");
+    }
+    while (cbor_value_is_valid(&rootMap))
     {
-         err = err || OCParseSingleRepPayload(&temp, arrayVal);
+        temp = OCRepPayloadCreate();
+        ret = OC_STACK_NO_MEMORY;
+        VERIFY_PARAM_NON_NULL(TAG, temp, "Failed allocating memory");
+
+        CborValue curVal;
+        ret = OC_STACK_MALFORMED_RESPONSE;
+
+        // temporary fix to check for malformed cbor payload
+        if (!cbor_value_is_map(&rootMap) && !cbor_value_is_array(&rootMap)){
+            goto exit;
+        }
+
+        if (cbor_value_is_map(&rootMap))
+        {
+            err = cbor_value_map_find_value(&rootMap, OC_RSRVD_HREF, &curVal);
+            VERIFY_CBOR_SUCCESS(TAG, err, "to find href tag");
+            if (cbor_value_is_valid(&curVal))
+            {
+                size_t len = 0;
+                err = cbor_value_dup_text_string(&curVal, &temp->uri, &len, NULL);
+                VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find uri");
+            }
+        }
+
+        // Resource types
+        if (cbor_value_is_map(&rootMap))
+        {
+            if (CborNoError == cbor_value_map_find_value(&rootMap, OC_RSRVD_RESOURCE_TYPE, &curVal))
+            {
+                err =  OCParseStringLL(&rootMap, OC_RSRVD_RESOURCE_TYPE, &temp->types);
+                VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find rt type tag/value");
+            }
+        }
+
+        // Interface Types
+        if (cbor_value_is_map(&rootMap))
+        {
+            if (CborNoError == cbor_value_map_find_value(&rootMap, OC_RSRVD_INTERFACE, &curVal))
+            {
+                err =  OCParseStringLL(&rootMap, OC_RSRVD_INTERFACE, &temp->interfaces);
+                VERIFY_CBOR_SUCCESS(TAG, err, "Failed to find interfaces tag/value");
+            }
+        }
+
+        if (cbor_value_is_map(&rootMap))
+        {
+            err = OCParseSingleRepPayload(&temp, &rootMap, true);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to parse single rep payload");
+        }
 
         if(rootPayload == NULL)
         {
@@ -790,80 +1136,76 @@ static OCStackResult OCParseRepPayload(OCPayload** outPayload, CborValue* arrayV
             curPayload = curPayload->next;
         }
 
-
-         err = err || cbor_value_advance(arrayVal);
-        if(err)
+        if (cbor_value_is_array(&rootMap))
         {
-            OCRepPayloadDestroy(rootPayload);
-            OC_LOG_V(ERROR, TAG, PCF("CBOR error in ParseRepPayload"));
-            return OC_STACK_MALFORMED_RESPONSE;
+            err = cbor_value_advance(&rootMap);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed to advance single rep payload");
         }
     }
-
-    *outPayload = (OCPayload*)rootPayload;
-
+    *outPayload = (OCPayload *)rootPayload;
     return OC_STACK_OK;
+
+exit:
+    OCRepPayloadDestroy(temp);
+    OCRepPayloadDestroy(rootPayload);
+    OIC_LOG(ERROR, TAG, "CBOR error in ParseRepPayload");
+    return ret;
 }
 
-static OCStackResult OCParsePresencePayload(OCPayload** outPayload, CborValue* arrayVal)
+static OCStackResult OCParsePresencePayload(OCPayload **outPayload, CborValue *rootValue)
 {
-    bool err = false;
-    if(cbor_value_is_map(arrayVal))
-    {
-        uint64_t seqNum = 0;
-        uint64_t maxAge = 0;
-        OCPresenceTrigger trigger = OC_PRESENCE_TRIGGER_CREATE;
-        char* tempStr = NULL;
-        size_t len = 0;
+    OCStackResult ret = OC_STACK_INVALID_PARAM;
+    OCPresencePayload *payload = NULL;
+    VERIFY_PARAM_NON_NULL(TAG, outPayload, "Invalid Parameter outPayload");
+
+    *outPayload = NULL;
 
+    payload = (OCPresencePayload *)OICCalloc(1, sizeof(OCPresencePayload));
+    ret = OC_STACK_NO_MEMORY;
+    VERIFY_PARAM_NON_NULL(TAG, payload, "Failed allocating presence payload");
+    payload->base.type = PAYLOAD_TYPE_PRESENCE;
+    ret = OC_STACK_MALFORMED_RESPONSE;
+
+    if (cbor_value_is_map(rootValue))
+    {
         CborValue curVal;
+
         // Sequence Number
-         err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_NONCE, &curVal);
-         err = err || cbor_value_get_uint64(&curVal, &seqNum);
+        CborError err = cbor_value_map_find_value(rootValue, OC_RSRVD_NONCE, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed finding nonce tag");
+        err = cbor_value_get_uint64(&curVal, (uint64_t *)&payload->sequenceNumber);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed finding nonce value");
 
         // Max Age
-         err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_TTL, &curVal);
-         err = err || cbor_value_get_uint64(&curVal, &maxAge);
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_TTL, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed finding ttl tag");
+        err = cbor_value_get_uint64(&curVal, (uint64_t *)&payload->maxAge);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed finding ttl value");
 
         // Trigger
-         err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_TRIGGER, &curVal);
-         err = err || cbor_value_dup_text_string(&curVal, &tempStr, &len, NULL);
-        trigger = convertTriggerStringToEnum(tempStr);
-        OICFree(tempStr);
-        tempStr = NULL;
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_TRIGGER, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed finding trigger tag");
+        err = cbor_value_get_simple_type(&curVal, (uint8_t *)&payload->trigger);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed finding trigger value");
 
         // Resource type name
-         err = err || cbor_value_map_find_value(arrayVal, OC_RSRVD_RESOURCE_TYPE, &curVal);
-        if(cbor_value_is_valid(&curVal))
+        err = cbor_value_map_find_value(rootValue, OC_RSRVD_RESOURCE_TYPE, &curVal);
+        VERIFY_CBOR_SUCCESS(TAG, err, "to find res type tag");
+        if (cbor_value_is_valid(&curVal))
         {
-             err = err || cbor_value_dup_text_string(&curVal, &tempStr, &len, NULL);
+            size_t len = 0;
+            err = cbor_value_dup_text_string(&curVal, &payload->resourceType, &len, NULL);
+            VERIFY_CBOR_SUCCESS(TAG, err, "Failed finding resource type value");
         }
 
-        err = err || cbor_value_advance(arrayVal);
-
-        if(!err)
-        {
-            *outPayload = (OCPayload*)OCPresencePayloadCreate(seqNum, maxAge, trigger, tempStr);
-        }
-        OICFree(tempStr);
-
-        if(err)
-        {
-            OCPayloadDestroy(*outPayload);
-            OC_LOG_V(ERROR, TAG, PCF("CBOR error Parse Presence Payload"));
-            return OC_STACK_MALFORMED_RESPONSE;
-        }
-
-        if(!*outPayload)
-        {
-            return OC_STACK_NO_MEMORY;
-        }
+        err = cbor_value_advance(rootValue);
+        VERIFY_CBOR_SUCCESS(TAG, err, "Failed advancing root value");
 
+        *outPayload = (OCPayload *)payload;
         return OC_STACK_OK;
     }
-    else
-    {
-        OC_LOG(ERROR, TAG, PCF("Root presence node was not a map"));
-        return OC_STACK_MALFORMED_RESPONSE;
-    }
+exit:
+    OIC_LOG(ERROR, TAG, "CBOR error Parse Presence Payload");
+    OCPresencePayloadDestroy(payload);
+    return ret;
 }