/*             ----> 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 routines for certain 64-bit math operations and simulated
           floating point.

    RedUint64DivMod32() and RedUint64DivMod64() are derived from code at
    http://www.hackersdelight.org.  This web site states explicitly that "You
    are free to use, copy, and distribute any of the code on this web site,
    whether modified by you or not.  You need not give attribution."
*/
#include <redfs.h>
#include <redtestutils.h>


static uint32_t nlz64(uint64_t ullValue);


/** @brief Return a ratio value formatted as a floating point string accurate to
           the specified number of decimal places.

    The  function exists to provide floating point style output without using
    any actual floating point types.

    This function may scale the numbers down to avoid overflow at the high end.
    Likewise, potential divide-by-zero errors are internally avoided.  Here are
    some examples:

    Dividend | Divisor | DecPlaces | Result
    -------- | ------- | --------- | ------
    12133    | 28545   | 2         | "0.42"
    1539     | 506     | 2         | "3.04"

    To get a number formatted as a percentage, take the take the portion of the
    total (normally the smaller part), multiply it by 100, and pass it to this
    function as the Dividend, pass the "total" value to this function as the
    Divisor, and specify the desired number of decimal places.

    For example, if you have a disk format overhead value of N blocks out of a
    total of Y blocks on the disk, and you want to display the format overhead
    as a percentage, you would use a function call
    similar to:

    ~~~{.c}
    RedRatio(szBuffer, sizeof(szBuffer), N*100U, Y, 2U);
    ~~~

    If N=145, Y=4096, and decimal places is 2, the resulting output would be
    "3.54".

    The string returned will always be null-terminated, even if it means
    stomping on the least significant decimal digit.

    If either the dividend or divisor values are zero, the string "0.0" will be
    returned, with the prescribed number of decimal places.

    @note This function has "reasonable" limits which meet the needs of the
          various supplemental utilities which use this function.  Extremely
          large ratios, or using many decimal places may not function as
          desired.

    Parameters:
    @param pBuffer      A pointer to the buffer in which to store the null
                        terminated results.
    @param ulBufferLen  The length of the output buffer.
    @param ullDividend  The "total" value to divide.
    @param ullDivisor   The portion of ullDividend for which to calculate the
                        ratio (may be greater than ulDividend).
    @param ulDecPlaces  The number of decimal places to use, from 0 to 9.

    @return @p pBuffer.
*/
char *RedRatio(
    char       *pBuffer,
    uint32_t    ulBufferLen,
    uint64_t    ullDividend,
    uint64_t    ullDivisor,
    uint32_t    ulDecPlaces)
{
    REDASSERT(pBuffer != NULL);
    REDASSERT(ulBufferLen > 0U);
    REDASSERT(ulDecPlaces <= 9U);   /* arbitrary */

    if((ullDivisor > 0U) && (ullDividend > 0U))
    {
        uint32_t    ii;
        uint32_t    ulFactor = 1U;
        uint64_t    ullDecimal;
        uint64_t    ullTemp;

        for(ii = 1U; ii <= ulDecPlaces; ii++)
        {
            ulFactor *= 10U;
        }

        ullDecimal = RedMulDiv64(ullDividend, ulFactor, ullDivisor);

        /*  Shouldn't really be calling this function in a situation where we
            can overflow at this point...
        */
        REDASSERT(ullDecimal != UINT64_MAX);

        if(ullDivisor <= ullDividend)
        {
            uint32_t ulDecimal;

            (void)RedUint64DivMod32(ullDecimal, ulFactor, &ulDecimal);
            ullDecimal = ulDecimal;
        }

        ullTemp = RedUint64DivMod64(ullDividend, ullDivisor, NULL);

        if(ulDecPlaces > 0U)
        {
            RedSNPrintf(pBuffer, ulBufferLen, "%llu.%0*llu", (unsigned long long)ullTemp,
                (unsigned)ulDecPlaces, (unsigned long long)ullDecimal);
        }
        else
        {
            RedSNPrintf(pBuffer, ulBufferLen, "%llu", (unsigned long long)ullTemp);
        }
    }
    else
    {
        /*  If either the dividend or divisor is zero, then just output a "0.0"
            string with the prescribed number of decimal places.
        */
        if(ulDecPlaces > 0U)
        {
            RedSNPrintf(pBuffer, ulBufferLen, "0.%0*u", (unsigned)ulDecPlaces, 0U);
        }
        else
        {
            RedStrNCpy(pBuffer, "0", ulBufferLen);
        }
    }

    /*  Ensure the returned buffer is always null-terminated
    */
    pBuffer[ulBufferLen - 1U] = '\0';

    return pBuffer;
}


/** @brief Multiply 64-bit and 32-bit numbers, and divide by a 64-bit number,
           returning a 64-bit result.

    @note This function may return an approximate value if multiplying
          @p ullBase and @p ulMultplier results in a number larger than 64-bits
          _and_ this cannot be avoided by scaling.

    @param ullBase      The base 64-bit number number.
    @param ulMultiplier The 32-bit number by which to multiply.
    @param ullDivisor   The 64-bit number by which to divide.

    @return The 64-bit unsigned integer result.  Always returns zero if either
            @p ullBase or @p ulMultiplier are zero (regardless what
            @p ullDivisor is).  Returns UINT64_MAX if an overflow condition
            occurred, or if @p ullDivisor is zero.
*/
uint64_t RedMulDiv64(
    uint64_t ullBase,
    uint32_t ulMultiplier,
    uint64_t ullDivisor)
{
    uint64_t ullTemp;

    /*  Result would always be zero if either of these are zero.  Specifically
        test this case before looking for a zero divisor.
    */
    if((ullBase == 0U) || (ulMultiplier == 0U))
    {
        return 0U;
    }

    if(ullDivisor == 0U)
    {
        return UINT64_MAX;
    }

    /*  Since we don't have the ability (yet) to use 128-bit numbers, we jump
        through the following hoops (in order) to try to determine the proper
        results without losing precision:

        1) Shift the divisor and one of the multiplicands as many times as is
           necessary to reduce the scale -- only if it can be done without
           losing precision.
        2) Divide one of the multiplicands by the divisor first, but only if it
           divides evenly, preserving precision.
        3) Same as #2, but try it for the other multiplicand.
        4) Last ditch, divide the larger multiplicand by the divisor first, then
           do the multiply.  This <WILL> lose precision.

        These solutions are identified as CODE-PATHs #1-4 which are used to
        identify the matching tests in dltmain.c.

        Note that execution might partially include CODE-PATH #1 up until
        shifting can no longer be done without losing precision.  In that case,
        one of the three remaining options will be used.
    */

    ullTemp = RedUint64DivMod32(UINT64_MAX, ulMultiplier, NULL);
    while(ullBase > ullTemp)
    {
        uint64_t ullMod;
        uint64_t ullBaseTemp;
        uint64_t ullWideMultiplier;

        /*  CODE-PATH #1
        */
        /*  So long as ulDivisor, and at least one of the other numbers, are
            evenly divisible by 2, we can scale the numbers so the result does
            not overflow the intermediate 64-bit value.
        */
        if((ullDivisor & 1U) == 0U)
        {
            if((ullBase & 1U) == 0U)
            {
                /*  CODE-PATH #1a
                */
                ullDivisor >>= 1U;
                ullBase >>= 1U;
                continue;
            }

            if(((ulMultiplier & 1U) == 0U) && ((ullTemp & UINT64_SUFFIX(0x8000000000000000)) == 0U))
            {
                /*  CODE-PATH #1b
                */
                ullDivisor >>= 1U;
                ulMultiplier >>= 1U;
                ullTemp <<= 1U;
                continue;
            }
        }

        /*  If we get to this point, the above method (#1) cannot be used
            because not enough of the numbers are even long enough to scale the
            operands down.  We'll see if either multiplicand is evenly divisble
            by ulDivisor, and if so, do the divide first, then the multiply.
            (Note that once we get to this point, we will never exercise the
            while{} loop anymore.)
        */

        /*  CODE-PATH #2
        */
        ullBaseTemp = RedUint64DivMod64(ullBase, ullDivisor, &ullMod);
        if(ullMod == 0U)
        {
            /*  Evenly divides, so check that we won't overflow, and finish up.
            */
            ullBase = ullBaseTemp;
            if(ullBase > ullTemp)
            {
                return UINT64_MAX;
            }
            else
            {
                /*  We've validated that this will not overflow.
                */
                ullBase *= ulMultiplier;
                return ullBase;
            }
        }

        /*  CODE-PATH #3
        */
        ullWideMultiplier = RedUint64DivMod64(ulMultiplier, ullDivisor, &ullMod);
        if(ullMod == 0U)
        {
            /*  Evenly divides, so check that we won't overflow, and finish up.
            */

            /*  Must recalculate ullTemp relative to ullBase
            */
            ullTemp = RedUint64DivMod64(UINT64_MAX, ullBase, NULL);
            if(ullWideMultiplier > ullTemp)
            {
                return UINT64_MAX;
            }
            else
            {
                uint32_t ulNarrowMultiplier = (uint32_t)ullWideMultiplier;

                /*  We've validated that this will not overflow.
                */
                ullBase *= ulNarrowMultiplier;
                return ullBase;
            }
        }

        /*  CODE-PATH #4

            Neither of the multipliers is evenly divisible by the divisor, so
            just punt and divide the larger number first, then do the final
            multiply.

            All the other attempts above would preserve precision -- this is the
            only case where precision may be lost.
        */

        /*  If necessary reverse the ullBase and ulMultiplier operands so that
            ullBase contains the larger of the two values.
        */
        if(ullBase < ulMultiplier)
        {
            uint32_t ulTemp = ulMultiplier;

            ulMultiplier = (uint32_t)ullBase;
            ullBase = ulTemp;
        }

        ullBase = RedUint64DivMod64(ullBase, ullDivisor, NULL);
        ullTemp = RedUint64DivMod32(UINT64_MAX, ulMultiplier, NULL);
        if(ullBase > ullTemp)
        {
            return UINT64_MAX;
        }
        else
        {
            ullBase *= ulMultiplier;
            return ullBase;
        }
    }

    /*  We only get to this point if either there was never any chance of
        overflow, or if the pure shifting mechanism succeeded in reducing
        the scale so overflow is not a problem.
    */

    ullBase *= ulMultiplier;
    ullBase = RedUint64DivMod64(ullBase, ullDivisor, NULL);

    return ullBase;
}


/** @brief Divide a 64-bit value by a 32-bit value, returning the quotient and
           the remainder.

    Essentially this function does the following:

    ~~~{.c}
    if(pulRemainder != NULL)
    {
        *pulRemainder = (uint32_t)(ullDividend % ulDivisor);
    }
    return ullDividend / ulDivisor;
    ~~~

    However, it does so without ever actually dividing/modulating a 64-bit
    value, since such operations are not allowed in all environments.

    @param ullDividend  The value to divide.
    @param ulDivisor    The value to divide by.
    @param pulRemander  Populated with the remainder; may be NULL.

    @return The quotient (result of the division).
*/
uint64_t RedUint64DivMod32(
    uint64_t    ullDividend,
    uint32_t    ulDivisor,
    uint32_t   *pulRemainder)
{
    uint64_t    ullQuotient;
    uint32_t    ulResultRemainder;

    /*  Check for divide by zero.
    */
    if(ulDivisor == 0U)
    {
        REDERROR();

        /*  Nonsense value if no asserts.
        */
        ullQuotient = UINT64_SUFFIX(0xFFFFFFFFFFFFFBAD);
        ulResultRemainder = 0xFFFFFBADU;
    }
    else if(ullDividend <= UINT32_MAX)
    {
        uint32_t ulDividend = (uint32_t)ullDividend;

        ullQuotient = ulDividend / ulDivisor;
        ulResultRemainder = ulDividend % ulDivisor;
    }
    else
    {
        uint32_t    ulResultHi;
        uint32_t    ulResultLo;
        uint32_t    ulRemainder;
        uint8_t     bIndex;
        uint32_t    ulThisDivision;
        uint32_t    ulMask;
        uint8_t     ucNextValue;
        uint32_t    ulInterimHi, ulInterimLo;
        uint32_t    ulLowDword = (uint32_t)ullDividend;
        uint32_t    ulHighDword = (uint32_t)(ullDividend >> 32U);

        /*  Compute the high part and get the remainder
        */
        ulResultHi = ulHighDword / ulDivisor;
        ulResultLo = 0U;
        ulRemainder = ulHighDword % ulDivisor;

        /*  Compute the low part
        */
        ulMask = 0xFF000000U;
        for(bIndex = 0U; bIndex < sizeof(uint32_t); bIndex++)
        {
            ucNextValue = (uint8_t)((ulLowDword & ulMask) >> ((sizeof(uint32_t) - 1U - bIndex) * 8U));
            ulInterimHi = ulRemainder >> 24U;
            ulInterimLo = (ulRemainder << 8U) | ucNextValue;
            ulThisDivision = 0U;
            while(ulInterimHi != 0U)
            {
                uint64_t ullInterim = ((uint64_t)ulInterimHi << 32U) + ulInterimLo;

                ullInterim -= ulDivisor;
                ulThisDivision++;

                ulInterimHi = (uint32_t)(ullInterim >> 32U);
                ulInterimLo = (uint32_t)ullInterim;
            }
            ulThisDivision += ulInterimLo / ulDivisor;
            ulRemainder = ulInterimLo % ulDivisor;
            ulResultLo <<= 8U;
            ulResultLo += ulThisDivision;
            ulMask >>= 8U;
        }

        ullQuotient = ((uint64_t)ulResultHi << 32U) + ulResultLo;
        ulResultRemainder = (uint32_t)(ullDividend - (ullQuotient * ulDivisor));
    }

    if(pulRemainder != NULL)
    {
        *pulRemainder = ulResultRemainder;
    }

    return ullQuotient;
}


/** @brief Divide a 64-bit value by a 64-bit value, returning the quotient and
           the remainder.

    Essentially this function does the following:

    ~~~{.c}
    if(pullRemainder != NULL)
    {
        *pullRemainder = ullDividend % ullDivisor;
    }
    return ullDividend / ullDivisor;
    ~~~

    However, it does so without ever actually dividing/modulating a 64-bit
    value, since such operations are not allowed in all environments.

    @param ullDividend  The value to divide.
    @param ullDivisor   The value to divide by.
    @param pullRemander Populated with the remainder; may be NULL.

    @return The quotient (result of the division).
*/
uint64_t RedUint64DivMod64(
    uint64_t    ullDividend,
    uint64_t    ullDivisor,
    uint64_t   *pullRemainder)
{
    /*  The variables u0, u1, etc. take on only 32-bit values, but they are
        declared uint64_t to avoid some compiler warning messages and to avoid
        some unnecessary EXTRs that the compiler would put in, to convert
        uint64_ts to ints.
    */
    uint64_t    u0;
    uint64_t    u1;
    uint64_t    q0;
    uint64_t    q1;
    uint64_t    ullQuotient;

    /*  First the procedure takes care of the case in which the divisor is a
        32-bit quantity.  There are two subcases: (1) If the left half of the
        dividend is less than the divisor, one execution of RedUint64DivMod32()
        is all that is required (overflow is not possible). (2) Otherwise it
        does two divisions, using the grade school method.
    */

    if((ullDivisor >> 32U) == 0U)
    {
        if((ullDividend >> 32U) < ullDivisor)
        {
            /*  If ullDividend/ullDivisor cannot overflow, just do one division.
            */
            ullQuotient = RedUint64DivMod32(ullDividend, (uint32_t)ullDivisor, NULL);
        }
        else
        {
            uint32_t k;

            /*  If ullDividend/ullDivisor would overflow:
            */

            /*  Break ullDividend up into two halves.
            */
            u1 = ullDividend >> 32U;
            u0 = ullDividend & 0xFFFFFFFFU;

            /*  First quotient digit and first remainder.
            */
            q1 = RedUint64DivMod32(u1, (uint32_t)ullDivisor, &k);

            /*  2nd quot. digit.
            */
            q0 = RedUint64DivMod32(((uint64_t)k << 32U) + u0, (uint32_t)ullDivisor, NULL);

            ullQuotient = (q1 << 32U) + q0;
        }
    }
    else
    {
        uint64_t n;
        uint64_t v1;

        n = nlz64(ullDivisor);          /* 0 <= n <= 31. */
        v1 = (ullDivisor << n) >> 32U;  /* Normalize the divisor so its MSB is 1. */
        u1 = ullDividend >> 1U;         /* To ensure no overflow. */

        /*  Get quotient from divide unsigned insn.
        */
        q1 = RedUint64DivMod32(u1, (uint32_t)v1, NULL);

        q0 = (q1 << n) >> 31U;  /* Undo normalization and division of ullDividend by 2. */

        /*  Make q0 correct or too small by 1.
        */
        if(q0 != 0U)
        {
            q0--;
        }

        if((ullDividend - (q0 * ullDivisor)) >= ullDivisor)
        {
            q0++;   /* Now q0 is correct. */
        }

        ullQuotient = q0;
    }

    if(pullRemainder != NULL)
    {
        *pullRemainder = ullDividend - (ullQuotient * ullDivisor);
    }

    return ullQuotient;
}


/** @brief Compute the number of leading zeroes in a 64-bit value.

    @param ullValue The value for which to compute the NLZ.

    @return The number of leading zeroes in @p ullValue.
*/
static uint32_t nlz64(
    uint64_t    ullValue)
{
    uint32_t    n;

    if(ullValue == 0U)
    {
        n = 64U;
    }
    else
    {
        uint64_t x = ullValue;

        n = 0U;

        if(x <= UINT64_SUFFIX(0x00000000FFFFFFFF))
        {
            n += 32U;
            x <<= 32U;
        }

        if(x <= UINT64_SUFFIX(0x0000FFFFFFFFFFFF))
        {
            n += 16U;
            x <<= 16U;
        }

        if(x <= UINT64_SUFFIX(0x00FFFFFFFFFFFFFF))
        {
            n += 8U;
            x <<= 8U;
        }

        if(x <= UINT64_SUFFIX(0x0FFFFFFFFFFFFFFF))
        {
            n += 4U;
            x <<= 4U;
        }

        if(x <= UINT64_SUFFIX(0x3FFFFFFFFFFFFFFF))
        {
            n += 2U;
            x <<= 2U;
        }

        if(x <= UINT64_SUFFIX(0x7FFFFFFFFFFFFFFF))
        {
            n += 1;
        }
    }

    return n;
}

