/*             ----> DO NOT REMOVE THE FOLLOWING NOTICE <----

                   Copyright (c) 2014-2015 Datalight, Inc.
                       All Rights Reserved Worldwide.

    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation; use version 2 of the License.

    This program is distributed in the hope that it will be useful,
    but "AS-IS," WITHOUT ANY WARRANTY; without even the implied warranty
    of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License along
    with this program; if not, write to the Free Software Foundation, Inc.,
    51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/
/*  Businesses and individuals that for commercial or other reasons cannot
    comply with the terms of the GPLv2 license may obtain a commercial license
    before incorporating Reliance Edge into proprietary software for
    distribution in any form.  Visit http://www.datalight.com/reliance-edge for
    more information.
*/
/** @file
    @brief Implements utilities that convert strings to numbers.
*/
#include <redfs.h>
#include <redtestutils.h>


#define ISHEXDIGITU(c)  (((c) >= 'A') && ((c) <= 'F'))
#define ISHEXDIGITL(c)  (((c) >= 'a') && ((c) <= 'f'))
#define ISHEXDIGIT(c)   (ISHEXDIGITL(c) || ISHEXDIGITU(c))


/** @brief Converts an ASCII number into an int32_t.

    Converts all decimal digit numbers up to the end of the string or to the
    first non-numerical character.

    @note This function does *not* ignore leading white space.

    @param pszNum   Pointer to a constant array of characters.

    @return The integer represented in the string.
*/
int32_t RedAtoI(
    const char *pszNum)
{
    int32_t     lValue = 0;
    int32_t     lNegative = 1;
    uint32_t    ulIdx = 0U;

    if(pszNum[ulIdx] == '+')
    {
        ulIdx++;
    }
    else if(pszNum[ulIdx] == '-')
    {
        ulIdx++;
        lNegative = -1;
    }
    else
    {
        /*  No sign, implicitly positive.
        */
    }

    while(ISDIGIT(pszNum[ulIdx]))
    {
        lValue *= 10;
        lValue += pszNum[ulIdx] - '0';
        ulIdx++;
    }

    lValue *= lNegative;

    return lValue;
}


/** @brief Convert a hexadecimal ASCII number into a uint32_t value.

    The function processes all hex digits up to a NUL-terminator, or to the
    first non-hex character.  Only hexadecimal digits are processed, so leading
    white space, or a leading "0x" prefix are not allowed.

    If pachNum points to an empty string (points to a NUL), this function will
    return NULL, and the value at *pulNum will not be modified.

    @note This function does not check for overflow.  If there are more
          significant digits than can be represented in a uint32_t variable, the
          output is unspecified.

    @param pachNum  A pointer to a constant array of hex characters.
    @param pulNum   A pointer to the location in which to store the uint32_t
                    result.  Upon return, this value will be modified ONLY if
                    the function succeeds and the returned pointer is valid (not
                    NULL).

    @return A pointer to the byte following the converted number or NULL to
            indicate failure.
*/
const char *RedHtoUL(
    const char *pszNum,
    uint32_t   *pulNum)
{
    uint64_t    ullValue;
    const char *pszReturn;

    pszReturn = RedHtoULL(pszNum, &ullValue);
    if(pszReturn != NULL)
    {
        if(ullValue < UINT32_MAX)
        {
            *pulNum = (uint32_t)ullValue;
        }
        else
        {
            pszReturn = NULL;
        }
    }

    return pszReturn;
}


/** @brief Convert a hexadecimal ASCII number into a D_UINT64 value.

    The function processes all hex digits up to a NUL-terminator, or to the
    first non-hex character.  Only hexadecimal digits are processed, so leading
    white space, or a leading "0x" prefix are not allowed.

    If pachNum points to an empty string (points to a NUL), this function will
    return NULL, and the value at *pulNum will not be modified.

    @note This function does not check for overflow.  If there are more
          significant digits than can be represented in a uint64_t variable, the
          output is unspecified.

    @param pszNum   A pointer to a constant array of hex characters.
    @param pullNum  A pointer to the location in which to store the uint64_t
                    result.  Upon return, this value will be modified ONLY if
                    the function succeeds and the returned pointer is valid (not
                    NULL).

    @return A pointer to the byte following the converted number, or NULL to
            indicate failure.
*/
const char *RedHtoULL(
    const char *pszNum,
    uint64_t   *pullNum)
{
    uint64_t    ullValue = 0U;
    const char *pszReturn = NULL;
    uint32_t    ulIdx = 0U;

    REDASSERT(pszNum != NULL);
    REDASSERT(pullNum != NULL);

    while(pszNum[ulIdx] != '\0')
    {
        char cDigit = pszNum[ulIdx];

        if(ISDIGIT(cDigit))
        {
            cDigit -= '0';
        }
        else if(ISHEXDIGITU(cDigit))
        {
            cDigit -= ('A' - 10);
        }
        else if(ISHEXDIGITL(cDigit))
        {
            cDigit -= ('a' - 10);
        }
        else
        {
            break;
        }

        REDASSERT((ullValue & UINT64_SUFFIX(0xF000000000000000)) == 0U);

        ullValue <<= 4U;
        ullValue += cDigit;

        ulIdx++;
        pszReturn = &pszNum[ulIdx];
    }

    /*  Modify the number returned only if we found one or more valid hex
        digits.
    */
    if(pszReturn != NULL)
    {
        *pullNum = ullValue;
    }

    return pszReturn;
}


/** @brief Convert the ASCII number to a uint32_t  value.

    The number may be hex or decimal.  Hex numbers must be prefixed by '0x', and
    they may be upper or lower case.  The conversion process will stop with the
    first non hex or decimal digit.

    If the number is negative (the first character is a '-' sign), the value
    will be range checked and returned as the equivalent unsigned value.

    @note   This function will NOT fail for numbers which exceed the size of a
            uint32_t value.

    @param pszNum   A pointer to the ASCII number to convert
    @param pulNum   A pointer to the uint32_t location to store the result.
                    This value will be modified on return only if the function
                    succeeds and the returned pointer is valid (not NULL).

    @return A pointer to the byte following the converted number, or NULL to
            indicate failure.
*/
const char *RedNtoUL(
    const char *pszNum,
    uint32_t   *pulNum)
{
    bool        fNegative = false;
    uint32_t    ulIdx = 0U;
    const char *pszReturn;

    REDASSERT(pszNum != NULL);
    REDASSERT(pulNum != NULL);

    if(pszNum[ulIdx] == '-')
    {
        fNegative = true;
        ulIdx++;
    }

    /*  Hex numbers must be prefixed with '0x'.
    */
    if((pszNum[ulIdx] == '0') && ((pszNum[ulIdx + 1U] == 'x') || (pszNum[ulIdx + 1U] == 'X')))
    {
        ulIdx += 2U;

        if(ISDIGIT(pszNum[ulIdx]) || ISHEXDIGIT(pszNum[ulIdx]))
        {
            pszReturn = RedHtoUL(&pszNum[ulIdx], pulNum);
        }
        else
        {
            pszReturn = NULL;
        }
    }
    else if(ISDIGIT(pszNum[ulIdx]))
    {
        uint32_t ulTemp;

        ulTemp = RedAtoI(&pszNum[ulIdx]);

        while(ISDIGIT(pszNum[ulIdx]))
        {
            ulIdx++;
        }

        if(fNegative)
        {
            /*  Fail if the number is out of range.
            */
            if(ulTemp > INT32_MAX)
            {
                pszReturn = NULL;
            }
            else
            {
                *pulNum = -((int32_t)ulTemp);
                pszReturn = &pszNum[ulIdx];
            }
        }
        else
        {
            *pulNum = ulTemp;
            pszReturn = &pszNum[ulIdx];
        }
    }
    else
    {
        /*  Return an error if there is not at least one hex or decimal digit.
        */
        pszReturn = NULL;
    }

    return pszReturn;
}


/** @brief Convert the ASCII number pointed to by pachNum to a uint64_t value.

    The number may be hex or decimal.  Hex numbers must be prefixed by '0x', and
    they may be upper or lower case.  The conversion process will stop with the
    first non hex or decimal digit.

    If the number is negative (the first character is a '-' sign), the value
    will be range checked and returned as the equivalent unsigned value.

    @param pszNum   A pointer to the ASCII number to convert.
    @param pullNum  A pointer to the uint64_t location to store the result.
                    This value will be modified on return only if the function
                    succeeds and the returned pointer is valid (not NULL).

    @return A pointer to the byte following the converted number, or NULL to
            indicate failure.
*/
const char *RedNtoULL(
    const char *pszNum,
    uint64_t   *pullNum)
{
    bool        fNegative = false;
    uint32_t    ulIdx = 0U;
    const char *pszReturn;

    REDASSERT(pszNum != NULL);
    REDASSERT(pullNum != NULL);

    if(pszNum[ulIdx] == '-')
    {
        fNegative = true;
        ulIdx++;
    }

    /*  Hex numbers must be prefixed with '0x'.
    */
    if((pszNum[ulIdx] == '0') && ((pszNum[ulIdx + 1U] == 'x') || (pszNum[ulIdx + 1U] == 'X')))
    {
        ulIdx += 2U;

        if(ISDIGIT(pszNum[ulIdx]) || ISHEXDIGIT(pszNum[ulIdx]))
        {
            pszReturn = RedHtoULL(&pszNum[ulIdx], pullNum);
        }
        else
        {
            pszReturn = NULL;
        }
    }
    else if(ISDIGIT(pszNum[ulIdx]))
    {
        uint64_t ullTemp = 0U;

        while(ISDIGIT(pszNum[ulIdx]))
        {
            ullTemp *= 10U;
            ullTemp += pszNum[ulIdx] - '0';
            ulIdx++;
        }

        if(fNegative)
        {
            /*  Fail if the number is out of range.
            */
            if(ullTemp > INT64_MAX)
            {
                pszReturn = NULL;
            }
            else
            {
                *pullNum = (uint64_t)(-((int64_t)ullTemp));
                pszReturn = &pszNum[ulIdx];
            }
        }
        else
        {
            *pullNum = ullTemp;
            pszReturn = &pszNum[ulIdx];
        }
    }
    else
    {
        /*  Return an error if there is not at least one hex or decimal digit.
        */
        pszReturn = NULL;
    }

    return pszReturn;
}


/** @brief Convert an ASCII hex or decimal number, which may may have a "B",
           "KB", or "MB" suffix (case insensitive), to a binary value.

    Hex numbers must be prefixed with "0x".

    @note If there is no postfix, KB is assumed!

    May fail due to bad formatting or overflow.

    @param pszNum       A pointer to the ASCII number to convert.
    @param pulResult    A pointer to a uint32_t in which to place the result.

    @return A pointer to the byte following the string, or NULL to indicate an
            error.  In the event of an error, *pulResult will not be modified.
*/
const char *RedSizeToUL(
    const char *pszNum,
    uint32_t   *pulResult)
{
    uint32_t    ulResult;
    const char *pszSuffix;
    const char *pszReturn;
    uint32_t    ulIdx = 0U;

    REDASSERT(pszNum != NULL);
    REDASSERT(pulResult != NULL);

    /*  Do the basic hex/decimal conversion
    */
    pszSuffix = RedNtoUL(pszNum, &ulResult);
    if(pszSuffix != NULL)
    {
        if((pszSuffix[ulIdx] == 'B') || (pszSuffix[ulIdx] == 'b'))
        {
            ulIdx++;
            pszReturn = &pszSuffix[ulIdx];
        }
        else if(    ((pszSuffix[ulIdx] == 'M') || (pszSuffix[ulIdx] == 'm'))
                 && ((pszSuffix[ulIdx + 1U] == 'B') || (pszSuffix[ulIdx + 1U] == 'b')))
        {
            ulIdx += 2U;

            if(ulResult > (UINT32_MAX / (1024U * 1024U)))
            {
                pszReturn = NULL;
            }
            else
            {
                ulResult *= 1024U * 1024U;
                pszReturn = &pszSuffix[ulIdx];
            }
        }
        else
        {
            /*  The number is either postfixed with "KB" or something
                else (we don't care), but we must increment the pointer
                if it is something recognize.
            */
            if(    ((pszSuffix[ulIdx] == 'K') || (pszSuffix[ulIdx] == 'k'))
                && ((pszSuffix[ulIdx + 1U] == 'B') || (pszSuffix[ulIdx + 1U] == 'b')))
            {
                ulIdx += 2U;
            }

            /*  "B" or "MB" were not specified, so it must be "KB"
            */
            if(ulResult > (UINT32_MAX / 1024U))
            {
                pszReturn = NULL;
            }
            else
            {
                ulResult *= 1024UL;
                pszReturn = &pszSuffix[ulIdx];
            }
        }

        if(pszReturn != NULL)
        {
            *pulResult = ulResult;
        }
    }
    else
    {
        pszReturn = NULL;
    }

    return pszReturn;
}

