Add MapPathToHandle API to handle path string

-- Add new MapPathToHandle API to handle path string, currently it does
not support dictionary.
-- This API would be used in data management support for mobile client
side.
-- Given the a string representation of a WDM path read out the relevant
tags and provide the equivalent path handle.  The WDM path is
represented as a string using the following rules
   a. tags are separated with `/`
   b. the path MUST begin with a leading `/` and MUST NOT contain a trailing slash
   c. numerical tags in the WDM path MUST be encoded using the standard C library for integer to string encoding
diff --git a/src/lib/profiles/data-management/Current/TraitData.cpp b/src/lib/profiles/data-management/Current/TraitData.cpp
index 2f4d718..6c1ebd9 100644
--- a/src/lib/profiles/data-management/Current/TraitData.cpp
+++ b/src/lib/profiles/data-management/Current/TraitData.cpp
@@ -88,6 +88,75 @@
     return err;
 }
 
+WEAVE_ERROR TraitSchemaEngine::ParseTagString(const char *apTagString, char **apEndptr, uint8_t& aParseRes) const
+{
+    WEAVE_ERROR err = WEAVE_NO_ERROR;
+
+    VerifyOrExit(apTagString != NULL, err = WEAVE_ERROR_INVALID_ARGUMENT);
+    VerifyOrExit(*apTagString == '/', err = WEAVE_ERROR_INVALID_ARGUMENT);
+
+    apTagString ++;
+
+    aParseRes = strtoul(apTagString, apEndptr, 0);
+    VerifyOrExit(!(*apEndptr == apTagString || (**apEndptr != '\0' && **apEndptr != '/')), err = WEAVE_ERROR_INVALID_ARGUMENT);
+    VerifyOrExit(aParseRes < kContextTagMaxNum, err = WEAVE_ERROR_INVALID_TLV_TAG);
+
+exit:
+    return err;
+}
+
+WEAVE_ERROR TraitSchemaEngine::MapPathToHandle(const char * aPathString, PropertyPathHandle & aHandle) const
+{
+    WEAVE_ERROR err = WEAVE_NO_ERROR;
+    PropertyPathHandle childProperty, curProperty;
+    char *parseEnd;
+    uint8_t parseRes = 0;
+    uint64_t tag = 0;
+
+    VerifyOrExit(aPathString != NULL, err = WEAVE_ERROR_INVALID_ARGUMENT);
+
+    // initialize the out argument to NULL
+    aHandle = kNullPropertyPathHandle;
+
+    // Set our starting point for traversal to the root node.
+    curProperty = kRootPropertyPathHandle;
+
+    if (aPathString[0] == '/' && aPathString[1] == '\0')
+    {
+        ExitNow();
+    }
+
+    // Descend into our schema tree using the tags encountered to help navigate through the various branches.
+    while (*aPathString != '\0')
+    {
+        err = ParseTagString(aPathString, &parseEnd, parseRes);
+        SuccessOrExit(err);
+
+        // Todo: add dictionary support, not yet supported
+        tag = ContextTag(parseRes);
+
+        childProperty = GetChildHandle(curProperty, TagNumFromTag(tag));
+        if (IsNullPropertyPathHandle(childProperty))
+        {
+            err = WEAVE_ERROR_TLV_TAG_NOT_FOUND;
+            SuccessOrExit(err);
+        }
+
+        // Set the current node.
+        curProperty = childProperty;
+
+        aPathString = parseEnd;
+    }
+
+exit:
+    if (err == WEAVE_NO_ERROR)
+    {
+        aHandle = curProperty;
+    }
+
+    return err;
+}
+
 WEAVE_ERROR TraitSchemaEngine::MapPathToHandle(TLVReader & aPathReader, PropertyPathHandle & aHandle) const
 {
     WEAVE_ERROR err = WEAVE_NO_ERROR;
diff --git a/src/lib/profiles/data-management/Current/TraitData.h b/src/lib/profiles/data-management/Current/TraitData.h
index d1c1e12..2ffde51 100644
--- a/src/lib/profiles/data-management/Current/TraitData.h
+++ b/src/lib/profiles/data-management/Current/TraitData.h
@@ -337,6 +337,21 @@
     WEAVE_ERROR MapPathToHandle(nl::Weave::TLV::TLVReader & aPathReader, PropertyPathHandle & aHandle) const;
 
     /**
+     * Given the a string representation of a WDM path read out the relevant tags and provide
+     * the equivalent path handle.  The WDM path is represented as a string using the following rules:
+     * - tags are separated with `/`
+     * - the path MUST begin with a leading `/` and MUST NOT contain a trailing slash
+     * - numerical tags in the WDM path MUST be encoded using the standard C library for integer to string encoding,
+     * i.e. decimal encoding (default) MUST NOT contain a leading 0, a hexadecimal  encoding MUST begin with `0x`,
+     * and octal encoding MUST contain a leading `0`.
+     *
+     * @retval #WEAVE_NO_ERROR                  On success.
+     * @retval #WEAVE_ERROR_TLV_TAG_NOT_FOUND   If a matching handle could not be found.
+     * @retval #WEAVE_ERROR_INVALID_ARGUMENT    If a path string is malformed
+     */
+    WEAVE_ERROR MapPathToHandle(const char * aPathString, PropertyPathHandle & aHandle) const;
+
+    /**
      * Convert the path handle to a TLV path.
      *
      * @retval #WEAVE_NO_ERROR On success.
@@ -523,6 +538,13 @@
     PropertyPathHandle _GetChildHandle(PropertyPathHandle aParentHandle, uint8_t aContextTag) const;
     bool GetBitFromPathHandleBitfield(uint8_t * aBitfield, PropertyPathHandle aPathHandle) const;
 
+    /*
+     * the path MUST begin with a leading `/` and MUST NOT contain a trailing slash
+     * numerical tags in the WDM path MUST be encoded using the standard C library for integer to string encoding,
+     * aParseRes must be less than kContextTagMaxNum. If apEndptr is not NULL,
+     * it stores the address of the first "/" in *apEndptr.
+     */
+    WEAVE_ERROR ParseTagString(const char *apTagString, char **apEndptr, uint8_t& aParseRes) const;
 public:
     const Schema mSchema;
 };