/*
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You under the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#ifdef _WIN32
#pragma warning( disable: 4146 )
#endif

#include <decaf/lang/Integer.h>
#include <decaf/lang/Character.h>
#include <sstream>
#include <vector>

using namespace decaf;
using namespace decaf::lang;
using namespace decaf::lang::exceptions;

////////////////////////////////////////////////////////////////////////////////
const int Integer::SIZE = 32;
const int Integer::MAX_VALUE = (int)0x7FFFFFFF;
const int Integer::MIN_VALUE = (int)0x80000000;

////////////////////////////////////////////////////////////////////////////////
Integer::Integer(int value) : value(value) {
}

////////////////////////////////////////////////////////////////////////////////
Integer::Integer(const std::string& value) : value() {
    this->value = parseInt(value);
}

////////////////////////////////////////////////////////////////////////////////
int Integer::compareTo(const Integer& i) const {
    return this->value < i.value ? -1 : this->value == i.value ? 0 : 1;
}

////////////////////////////////////////////////////////////////////////////////
int Integer::compareTo(const int& i) const {
    return this->value < i ? -1 : this->value == i ? 0 : 1;
}

////////////////////////////////////////////////////////////////////////////////
Integer::~Integer() {
}

////////////////////////////////////////////////////////////////////////////////
int Integer::bitCount(int value) {

    if (value == 0) {
        return 0;
    }

    unsigned int uvalue = (unsigned int) value;

    // 32-bit recursive reduction using SWAR...
    // but first step is mapping 2-bit values
    // into sum of 2 1-bit values in sneaky way
    uvalue -= ((uvalue >> 1) & 0x55555555);
    uvalue = (((uvalue >> 2) & 0x33333333) + (uvalue & 0x33333333));
    uvalue = (((uvalue >> 4) + uvalue) & 0x0F0F0F0F);
    uvalue += (uvalue >> 8);
    uvalue += (uvalue >> 16);
    return (uvalue & 0x0000003F);
}

////////////////////////////////////////////////////////////////////////////////
int Integer::reverseBytes(int value) {

    if (value == 0) {
        return 0;
    }

    unsigned int uvalue = (unsigned int) value;

    unsigned int b3 = uvalue >> 24;
    unsigned int b2 = (uvalue >> 8) & 0xFF00;
    unsigned int b1 = (uvalue & 0xFF00) << 8;
    unsigned int b0 = uvalue << 24;
    return (b0 | b1 | b2 | b3);
}

////////////////////////////////////////////////////////////////////////////////
int Integer::reverse(int value) {

    if (value == 0) {
        return 0;
    }

    unsigned int uvalue = (unsigned int) value;

    uvalue = (((uvalue & 0xAAAAAAAA) >> 1) | ((uvalue & 0x55555555) << 1));
    uvalue = (((uvalue & 0xCCCCCCCC) >> 2) | ((uvalue & 0x33333333) << 2));
    uvalue = (((uvalue & 0xF0F0F0F0) >> 4) | ((uvalue & 0x0F0F0F0F) << 4));
    uvalue = (((uvalue & 0xFF00FF00) >> 8) | ((uvalue & 0x00FF00FF) << 8));
    return ((uvalue >> 16) | (uvalue << 16));
}

////////////////////////////////////////////////////////////////////////////////
std::string Integer::toString() const {
    return Integer::toString(this->value, 10);
}

////////////////////////////////////////////////////////////////////////////////
std::string Integer::toString(int value) {
    return Integer::toString(value, 10);
}

////////////////////////////////////////////////////////////////////////////////
std::string Integer::toString(int value, int radix) {

    if (radix < Character::MIN_RADIX || radix > Character::MAX_RADIX) {
        radix = 10;
    }

    if (value == 0) {
        return "0";
    }

    int count = 2, j = value;
    bool negative = value < 0;
    if (!negative) {
        count = 1;
        j = -value;
    }

    while ((value /= radix) != 0) {
        count++;
    }

    std::vector<char> buffer(count);

    do {
        int ch = 0 - (j % radix);
        if (ch > 9) {
            ch = ch - 10 + 'a';
        } else {
            ch += '0';
        }
        buffer[--count] = (char) ch;
    } while ((j /= radix) != 0);

    if (negative) {
        buffer[0] = '-';
    }

    return std::string(&buffer[0], buffer.size());
}

////////////////////////////////////////////////////////////////////////////////
std::string Integer::toBinaryString(int value) {

    int count = 1;
    int j = value;

    if (value < 0) {
        count = 32;
    } else {
        while ((j >>= 1) != 0) {
            count++;
        }
    }

    std::vector<char> buffer(count);

    do {
        buffer[--count] = (char) ((value & 1) + '0');
        value >>= 1;
    } while (count > 0);

    return std::string(&buffer[0], buffer.size());
}

////////////////////////////////////////////////////////////////////////////////
std::string Integer::toOctalString(int value) {

    int count = 1, j = value;
    unsigned int uvalue = (unsigned int) value;

    if (value < 0) {
        count = 11;  // (8 * sizeof(value) + 2) / 3;
    } else {
        while ((j >>= 3) != 0) {
            count++;
        }
    }

    std::vector<char> buffer(count);

    do {
        buffer[--count] = (char) ((uvalue & 7) + '0');
        uvalue >>= 3;
    } while (count > 0);

    return std::string(&buffer[0], buffer.size());
}

////////////////////////////////////////////////////////////////////////////////
std::string Integer::toHexString(int value) {

    int count = 1;
    int j = value;

    if (value < 0) {
        count = 8;
    } else {
        while ((j >>= 4) != 0) {
            count++;
        }
    }

    std::vector<char> buffer(count);

    do {
        int t = value & 15;
        if (t > 9) {
            t = t - 10 + 'a';
        } else {
            t += '0';
        }
        buffer[--count] = (char) t;
        value >>= 4;
    } while (count > 0);

    return std::string(&buffer[0], buffer.size());
}

////////////////////////////////////////////////////////////////////////////////
int Integer::parseInt(const String& value) {
    return Integer::parseInt(value, 10);
}

////////////////////////////////////////////////////////////////////////////////
int Integer::parseInt(const String& value, int radix) {

    if (radix < Character::MIN_RADIX ||
        radix > Character::MAX_RADIX ) {
        throw NumberFormatException(
            __FILE__, __LINE__,
            "Integer:decode - Invalid radix" );
    }

    int length = (int)value.length(), i = 0;
    if (length == 0) {
        throw NumberFormatException(
            __FILE__, __LINE__,
            "Integer:decode - Invalid: zero length string");
    }

    bool negative = value.charAt(i) == '-';
    if (negative && ++i == length) {
        throw NumberFormatException(
            __FILE__, __LINE__,
            "Integer:decode - Invalid only a minus sign given");
    }

    return Integer::parse(value, i, radix, negative);
}

////////////////////////////////////////////////////////////////////////////////
Integer Integer::valueOf(const String& value) {
    return Integer(Integer::parseInt(value));
}

////////////////////////////////////////////////////////////////////////////////
Integer Integer::valueOf(const String& value, int radix) {
    return Integer(Integer::parseInt(value, radix));
}

////////////////////////////////////////////////////////////////////////////////
Integer Integer::decode(const String& value) {

    int length = (int) value.length(), i = 0;
    if (length == 0) {
        throw NumberFormatException(
            __FILE__, __LINE__,
            "Integer:decode - Invalid zero size string");
    }

    char firstDigit = value.charAt(i);
    bool negative = firstDigit == '-';
    if (negative) {
        if (length == 1) {
            throw NumberFormatException(
                __FILE__, __LINE__,
                "Integer:decode - Invalid zero string, minus only");
        }

        firstDigit = value.charAt(++i);
    }

    int base = 10;
    if (firstDigit == '0') {
        if (++i == length) {
            return valueOf(0);
        }

        if ((firstDigit = value.charAt(i)) == 'x' || firstDigit == 'X') {
            if( i == length ) {
                throw NumberFormatException(
                    __FILE__, __LINE__,
                    "Integer:decode - Invalid zero string, minus only");
            }
            i++;
            base = 16;
        } else {
            base = 8;
        }
    } else if (firstDigit == '#') {
        if (i == length) {
            throw NumberFormatException(
                __FILE__, __LINE__,
                "Integer:decode - Invalid zero string, minus only");
        }
        i++;
        base = 16;
    }

    int result = parse(value, i, base, negative);
    return valueOf(result);
}

////////////////////////////////////////////////////////////////////////////////
int Integer::parse(const String& value, int offset, int radix, bool negative) {

    int max = Integer::MIN_VALUE / radix;
    int result = 0, length = (int) value.length();

    while (offset < length) {
        int digit = Character::digit(value.charAt(offset++), radix);
        if (digit == -1) {
            throw NumberFormatException(
                __FILE__, __LINE__,
                "Integer::parse - number string is invalid: ", value.c_str());
        }
        if (max > result) {
            throw NumberFormatException(
                __FILE__, __LINE__,
                "Integer::parse - number string is invalid: ", value.c_str());
        }
        int next = result * radix - digit;
        if (next > result) {
            throw NumberFormatException(
                __FILE__, __LINE__,
                "Integer::parse - number string is invalid: ", value.c_str());
        }
        result = next;
    }
    if (!negative) {
        result = -result;
        if (result < 0) {
            throw NumberFormatException(
                __FILE__, __LINE__,
                "Integer::parse - number string is invalid: ", value.c_str());
        }
    }
    return result;
}

////////////////////////////////////////////////////////////////////////////////
int Integer::highestOneBit(int value) {

    if (value == 0) {
        return 0;
    }

    unsigned int uvalue = (unsigned int) value;

    uvalue |= (uvalue >> 1);
    uvalue |= (uvalue >> 2);
    uvalue |= (uvalue >> 4);
    uvalue |= (uvalue >> 8);
    uvalue |= (uvalue >> 16);
    return (uvalue & ~(uvalue >> 1));
}

////////////////////////////////////////////////////////////////////////////////
int Integer::lowestOneBit(int value) {
    if (value == 0) {
        return 0;
    }

    unsigned int uvalue = (unsigned int) value;
    return (uvalue & (-uvalue));
}

////////////////////////////////////////////////////////////////////////////////
int Integer::numberOfLeadingZeros(int value) {

    if (value == 0) {
        return 0;
    }

    unsigned int uvalue = (unsigned int) value;

    value |= value >> 1;
    value |= value >> 2;
    value |= value >> 4;
    value |= value >> 8;
    value |= value >> 16;
    return Integer::bitCount(~uvalue);
}

////////////////////////////////////////////////////////////////////////////////
int Integer::numberOfTrailingZeros(int value) {
    if (value == 0) {
        return 0;
    }

    unsigned int uvalue = (unsigned int) value;
    return bitCount((uvalue & -uvalue) - 1);
}

////////////////////////////////////////////////////////////////////////////////
int Integer::rotateLeft(int value, int distance) {
    unsigned int i = (unsigned int) value;
    int j = distance & 0x1F;
    return (i << j) | (i >> (-j & 0x1F));
}

////////////////////////////////////////////////////////////////////////////////
int Integer::rotateRight(int value, int distance) {
    unsigned int i = (unsigned int) value;
    int j = distance & 0x1F;
    return (i >> j) | (i << (-j & 0x1F));
}

////////////////////////////////////////////////////////////////////////////////
int Integer::signum(int value) {
    return (value == 0 ? 0 : (value < 0 ? -1 : 1));
}
