/*
 * Copyright (C) 2004, 2006, 2008 Apple Inc. All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE COMPUTER, INC. OR
 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */

#include "sky/engine/wtf/text/TextCodecLatin1.h"

#include "sky/engine/wtf/PassOwnPtr.h"
#include "sky/engine/wtf/text/CString.h"
#include "sky/engine/wtf/text/StringBuffer.h"
#include "sky/engine/wtf/text/TextCodecASCIIFastPath.h"
#include "sky/engine/wtf/text/WTFString.h"

using namespace WTF;

namespace WTF {

static const UChar table[256] = {
    0x0000, 0x0001, 0x0002, 0x0003, 0x0004, 0x0005, 0x0006, 0x0007, // 00-07
    0x0008, 0x0009, 0x000A, 0x000B, 0x000C, 0x000D, 0x000E, 0x000F, // 08-0F
    0x0010, 0x0011, 0x0012, 0x0013, 0x0014, 0x0015, 0x0016, 0x0017, // 10-17
    0x0018, 0x0019, 0x001A, 0x001B, 0x001C, 0x001D, 0x001E, 0x001F, // 18-1F
    0x0020, 0x0021, 0x0022, 0x0023, 0x0024, 0x0025, 0x0026, 0x0027, // 20-27
    0x0028, 0x0029, 0x002A, 0x002B, 0x002C, 0x002D, 0x002E, 0x002F, // 28-2F
    0x0030, 0x0031, 0x0032, 0x0033, 0x0034, 0x0035, 0x0036, 0x0037, // 30-37
    0x0038, 0x0039, 0x003A, 0x003B, 0x003C, 0x003D, 0x003E, 0x003F, // 38-3F
    0x0040, 0x0041, 0x0042, 0x0043, 0x0044, 0x0045, 0x0046, 0x0047, // 40-47
    0x0048, 0x0049, 0x004A, 0x004B, 0x004C, 0x004D, 0x004E, 0x004F, // 48-4F
    0x0050, 0x0051, 0x0052, 0x0053, 0x0054, 0x0055, 0x0056, 0x0057, // 50-57
    0x0058, 0x0059, 0x005A, 0x005B, 0x005C, 0x005D, 0x005E, 0x005F, // 58-5F
    0x0060, 0x0061, 0x0062, 0x0063, 0x0064, 0x0065, 0x0066, 0x0067, // 60-67
    0x0068, 0x0069, 0x006A, 0x006B, 0x006C, 0x006D, 0x006E, 0x006F, // 68-6F
    0x0070, 0x0071, 0x0072, 0x0073, 0x0074, 0x0075, 0x0076, 0x0077, // 70-77
    0x0078, 0x0079, 0x007A, 0x007B, 0x007C, 0x007D, 0x007E, 0x007F, // 78-7F
    0x20AC, 0x0081, 0x201A, 0x0192, 0x201E, 0x2026, 0x2020, 0x2021, // 80-87
    0x02C6, 0x2030, 0x0160, 0x2039, 0x0152, 0x008D, 0x017D, 0x008F, // 88-8F
    0x0090, 0x2018, 0x2019, 0x201C, 0x201D, 0x2022, 0x2013, 0x2014, // 90-97
    0x02DC, 0x2122, 0x0161, 0x203A, 0x0153, 0x009D, 0x017E, 0x0178, // 98-9F
    0x00A0, 0x00A1, 0x00A2, 0x00A3, 0x00A4, 0x00A5, 0x00A6, 0x00A7, // A0-A7
    0x00A8, 0x00A9, 0x00AA, 0x00AB, 0x00AC, 0x00AD, 0x00AE, 0x00AF, // A8-AF
    0x00B0, 0x00B1, 0x00B2, 0x00B3, 0x00B4, 0x00B5, 0x00B6, 0x00B7, // B0-B7
    0x00B8, 0x00B9, 0x00BA, 0x00BB, 0x00BC, 0x00BD, 0x00BE, 0x00BF, // B8-BF
    0x00C0, 0x00C1, 0x00C2, 0x00C3, 0x00C4, 0x00C5, 0x00C6, 0x00C7, // C0-C7
    0x00C8, 0x00C9, 0x00CA, 0x00CB, 0x00CC, 0x00CD, 0x00CE, 0x00CF, // C8-CF
    0x00D0, 0x00D1, 0x00D2, 0x00D3, 0x00D4, 0x00D5, 0x00D6, 0x00D7, // D0-D7
    0x00D8, 0x00D9, 0x00DA, 0x00DB, 0x00DC, 0x00DD, 0x00DE, 0x00DF, // D8-DF
    0x00E0, 0x00E1, 0x00E2, 0x00E3, 0x00E4, 0x00E5, 0x00E6, 0x00E7, // E0-E7
    0x00E8, 0x00E9, 0x00EA, 0x00EB, 0x00EC, 0x00ED, 0x00EE, 0x00EF, // E8-EF
    0x00F0, 0x00F1, 0x00F2, 0x00F3, 0x00F4, 0x00F5, 0x00F6, 0x00F7, // F0-F7
    0x00F8, 0x00F9, 0x00FA, 0x00FB, 0x00FC, 0x00FD, 0x00FE, 0x00FF  // F8-FF
};

void TextCodecLatin1::registerEncodingNames(EncodingNameRegistrar registrar)
{
    registrar("windows-1252", "windows-1252");
    registrar("ISO-8859-1", "ISO-8859-1");
    registrar("US-ASCII", "US-ASCII");

    registrar("WinLatin1", "windows-1252");
    registrar("ibm-1252", "windows-1252");
    registrar("ibm-1252_P100-2000", "windows-1252");

    registrar("CP819", "ISO-8859-1");
    registrar("IBM819", "ISO-8859-1");
    registrar("csISOLatin1", "ISO-8859-1");
    registrar("iso-ir-100", "ISO-8859-1");
    registrar("iso_8859-1:1987", "ISO-8859-1");
    registrar("l1", "ISO-8859-1");
    registrar("latin1", "ISO-8859-1");

    registrar("ANSI_X3.4-1968", "US-ASCII");
    registrar("ANSI_X3.4-1986", "US-ASCII");
    registrar("ASCII", "US-ASCII");
    registrar("IBM367", "US-ASCII");
    registrar("ISO646-US", "US-ASCII");
    registrar("ISO_646.irv:1991", "US-ASCII");
    registrar("cp367", "US-ASCII");
    registrar("csASCII", "US-ASCII");
    registrar("ibm-367_P100-1995", "US-ASCII");
    registrar("iso-ir-6", "US-ASCII");
    registrar("iso-ir-6-us", "US-ASCII");
    registrar("us", "US-ASCII");
    registrar("x-ansi", "US-ASCII");
}

static PassOwnPtr<TextCodec> newStreamingTextDecoderWindowsLatin1(const TextEncoding&, const void*)
{
    return adoptPtr(new TextCodecLatin1);
}

void TextCodecLatin1::registerCodecs(TextCodecRegistrar registrar)
{
    registrar("windows-1252", newStreamingTextDecoderWindowsLatin1, 0);

    // ASCII and Latin-1 both decode as Windows Latin-1 although they retain unique identities.
    registrar("ISO-8859-1", newStreamingTextDecoderWindowsLatin1, 0);
    registrar("US-ASCII", newStreamingTextDecoderWindowsLatin1, 0);
}

String TextCodecLatin1::decode(const char* bytes, size_t length, FlushBehavior, bool, bool&)
{
    LChar* characters;
    if (!length)
        return emptyString();
    String result = String::createUninitialized(length, characters);

    const uint8_t* source = reinterpret_cast<const uint8_t*>(bytes);
    const uint8_t* end = reinterpret_cast<const uint8_t*>(bytes + length);
    const uint8_t* alignedEnd = alignToMachineWord(end);
    LChar* destination = characters;

    while (source < end) {
        if (isASCII(*source)) {
            // Fast path for ASCII. Most Latin-1 text will be ASCII.
            if (isAlignedToMachineWord(source)) {
                while (source < alignedEnd) {
                    MachineWord chunk = *reinterpret_cast_ptr<const MachineWord*>(source);

                    if (!isAllASCII<LChar>(chunk))
                        goto useLookupTable;

                    copyASCIIMachineWord(destination, source);
                    source += sizeof(MachineWord);
                    destination += sizeof(MachineWord);
                }

                if (source == end)
                    break;
            }
            *destination = *source;
        } else {
useLookupTable:
            if (table[*source] > 0xff)
                goto upConvertTo16Bit;

            *destination = table[*source];
        }

        ++source;
        ++destination;
    }

    return result;

upConvertTo16Bit:
    UChar* characters16;
    String result16 = String::createUninitialized(length, characters16);

    UChar* destination16 = characters16;

    // Zero extend and copy already processed 8 bit data
    LChar* ptr8 = characters;
    LChar* endPtr8 = destination;

    while (ptr8 < endPtr8)
        *destination16++ = *ptr8++;

    // Handle the character that triggered the 16 bit path
    *destination16 = table[*source];
    ++source;
    ++destination16;

    while (source < end) {
        if (isASCII(*source)) {
            // Fast path for ASCII. Most Latin-1 text will be ASCII.
            if (isAlignedToMachineWord(source)) {
                while (source < alignedEnd) {
                    MachineWord chunk = *reinterpret_cast_ptr<const MachineWord*>(source);

                    if (!isAllASCII<LChar>(chunk))
                        goto useLookupTable16;

                    copyASCIIMachineWord(destination16, source);
                    source += sizeof(MachineWord);
                    destination16 += sizeof(MachineWord);
                }

                if (source == end)
                    break;
            }
            *destination16 = *source;
        } else {
useLookupTable16:
            *destination16 = table[*source];
        }

        ++source;
        ++destination16;
    }

    return result16;
}

template<typename CharType>
static CString encodeComplexWindowsLatin1(const CharType* characters, size_t length, UnencodableHandling handling)
{
    Vector<char> result(length);
    char* bytes = result.data();

    size_t resultLength = 0;
    for (size_t i = 0; i < length; ) {
        UChar32 c;
        U16_NEXT(characters, i, length, c);
        unsigned char b = c;
        // Do an efficient check to detect characters other than 00-7F and A0-FF.
        if (b != c || (c & 0xE0) == 0x80) {
            // Look for a way to encode this with Windows Latin-1.
            for (b = 0x80; b < 0xA0; ++b)
                if (table[b] == c)
                    goto gotByte;
            // No way to encode this character with Windows Latin-1.
            UnencodableReplacementArray replacement;
            int replacementLength = TextCodec::getUnencodableReplacement(c, handling, replacement);
            result.grow(resultLength + replacementLength + length - i);
            bytes = result.data();
            memcpy(bytes + resultLength, replacement, replacementLength);
            resultLength += replacementLength;
            continue;
        }
    gotByte:
        bytes[resultLength++] = b;
    }

    return CString(bytes, resultLength);
}

template<typename CharType>
CString TextCodecLatin1::encodeCommon(const CharType* characters, size_t length, UnencodableHandling handling)
{
    {
        char* bytes;
        CString string = CString::newUninitialized(length, bytes);

        // Convert the string a fast way and simultaneously do an efficient check to see if it's all ASCII.
        UChar ored = 0;
        for (size_t i = 0; i < length; ++i) {
            UChar c = characters[i];
            bytes[i] = c;
            ored |= c;
        }

        if (!(ored & 0xFF80))
            return string;
    }

    // If it wasn't all ASCII, call the function that handles more-complex cases.
    return encodeComplexWindowsLatin1(characters, length, handling);
}

CString TextCodecLatin1::encode(const UChar* characters, size_t length, UnencodableHandling handling)
{
    return encodeCommon(characters, length, handling);
}

CString TextCodecLatin1::encode(const LChar* characters, size_t length, UnencodableHandling handling)
{
    return encodeCommon(characters, length, handling);
}

} // namespace WTF
