/*
 * Copyright (C) 2010, 2013 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 INC. AND ITS CONTRIBUTORS ``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 INC. OR ITS 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.
 */

#pragma once

#include <limits.h>
#include <stdint.h>

namespace JSC {

class Identifier;

enum {
    // Token Bitfield: 0b000000000RTE000IIIIPPPPKUXXXXXXX
    // R = right-associative bit
    // T = unterminated error flag
    // E = error flag
    // I = binary operator allows 'in'
    // P = binary operator precedence
    // K = keyword flag
    // U = unary operator flag
    //
    // We must keep the upper 8bit (1byte) region empty. JSTokenType must be 24bits.
    UnaryOpTokenFlag = 128,
    KeywordTokenFlag = 256,
    BinaryOpTokenPrecedenceShift = 9,
    BinaryOpTokenAllowsInPrecedenceAdditionalShift = 4,
    BinaryOpTokenPrecedenceMask = 15 << BinaryOpTokenPrecedenceShift,
    ErrorTokenFlag = 1 << (BinaryOpTokenAllowsInPrecedenceAdditionalShift + BinaryOpTokenPrecedenceShift + 7),
    UnterminatedErrorTokenFlag = ErrorTokenFlag << 1,
    RightAssociativeBinaryOpTokenFlag = UnterminatedErrorTokenFlag << 1
};

#define BINARY_OP_PRECEDENCE(prec) (((prec) << BinaryOpTokenPrecedenceShift) | ((prec) << (BinaryOpTokenPrecedenceShift + BinaryOpTokenAllowsInPrecedenceAdditionalShift)))
#define IN_OP_PRECEDENCE(prec) ((prec) << (BinaryOpTokenPrecedenceShift + BinaryOpTokenAllowsInPrecedenceAdditionalShift))

enum JSTokenType {
    NULLTOKEN = KeywordTokenFlag,
    TRUETOKEN,
    FALSETOKEN,
    BREAK,
    CASE,
    DEFAULT,
    FOR,
    NEW,
    VAR,
    CONSTTOKEN,
    CONTINUE,
    FUNCTION,
    RETURN,
    IF,
    THISTOKEN,
    DO,
    WHILE,
    SWITCH,
    WITH,
    RESERVED,
    RESERVED_IF_STRICT,
    THROW,
    TRY,
    CATCH,
    FINALLY,
    DEBUGGER,
    ELSE,
    IMPORT,
    EXPORT_,
    CLASSTOKEN,
    EXTENDS,
    SUPER,

    // Contextual keywords
    
    LET,
    YIELD,
    AWAIT,

    FirstContextualKeywordToken = LET,
    LastContextualKeywordToken = AWAIT,
    FirstSafeContextualKeywordToken = AWAIT,
    LastSafeContextualKeywordToken = LastContextualKeywordToken,

    OPENBRACE = 0,
    CLOSEBRACE,
    OPENPAREN,
    CLOSEPAREN,
    OPENBRACKET,
    CLOSEBRACKET,
    COMMA,
    QUESTION,
    BACKQUOTE,
    INTEGER,
    DOUBLE,
    BIGINT,
    IDENT,
    STRING,
    TEMPLATE,
    REGEXP,
    SEMICOLON,
    COLON,
    DOT,
    EOFTOK,
    EQUAL,
    PLUSEQUAL,
    MINUSEQUAL,
    MULTEQUAL,
    DIVEQUAL,
    LSHIFTEQUAL,
    RSHIFTEQUAL,
    URSHIFTEQUAL,
    ANDEQUAL,
    MODEQUAL,
    POWEQUAL,
    XOREQUAL,
    OREQUAL,
    DOTDOTDOT,
    ARROWFUNCTION,
    QUESTIONDOT,
    LastUntaggedToken,

    // Begin tagged tokens
    PLUSPLUS = 0 | UnaryOpTokenFlag,
    MINUSMINUS = 1 | UnaryOpTokenFlag,
    AUTOPLUSPLUS = 2 | UnaryOpTokenFlag,
    AUTOMINUSMINUS = 3 | UnaryOpTokenFlag,
    EXCLAMATION = 4 | UnaryOpTokenFlag,
    TILDE = 5 | UnaryOpTokenFlag,
    TYPEOF = 6 | UnaryOpTokenFlag | KeywordTokenFlag,
    VOIDTOKEN = 7 | UnaryOpTokenFlag | KeywordTokenFlag,
    DELETETOKEN = 8 | UnaryOpTokenFlag | KeywordTokenFlag,
    COALESCE = 0 | BINARY_OP_PRECEDENCE(1),
    OR = 0 | BINARY_OP_PRECEDENCE(2),
    AND = 0 | BINARY_OP_PRECEDENCE(3),
    BITOR = 0 | BINARY_OP_PRECEDENCE(4),
    BITXOR = 0 | BINARY_OP_PRECEDENCE(5),
    BITAND = 0 | BINARY_OP_PRECEDENCE(6),
    EQEQ = 0 | BINARY_OP_PRECEDENCE(7),
    NE = 1 | BINARY_OP_PRECEDENCE(7),
    STREQ = 2 | BINARY_OP_PRECEDENCE(7),
    STRNEQ = 3 | BINARY_OP_PRECEDENCE(7),
    LT = 0 | BINARY_OP_PRECEDENCE(8),
    GT = 1 | BINARY_OP_PRECEDENCE(8),
    LE = 2 | BINARY_OP_PRECEDENCE(8),
    GE = 3 | BINARY_OP_PRECEDENCE(8),
    INSTANCEOF = 4 | BINARY_OP_PRECEDENCE(8) | KeywordTokenFlag,
    INTOKEN = 5 | IN_OP_PRECEDENCE(8) | KeywordTokenFlag,
    LSHIFT = 0 | BINARY_OP_PRECEDENCE(9),
    RSHIFT = 1 | BINARY_OP_PRECEDENCE(9),
    URSHIFT = 2 | BINARY_OP_PRECEDENCE(9),
    PLUS = 0 | BINARY_OP_PRECEDENCE(10) | UnaryOpTokenFlag,
    MINUS = 1 | BINARY_OP_PRECEDENCE(10) | UnaryOpTokenFlag,
    TIMES = 0 | BINARY_OP_PRECEDENCE(11),
    DIVIDE = 1 | BINARY_OP_PRECEDENCE(11),
    MOD = 2 | BINARY_OP_PRECEDENCE(11),
    POW = 0 | BINARY_OP_PRECEDENCE(12) | RightAssociativeBinaryOpTokenFlag, // Make sure that POW has the highest operator precedence.
    ERRORTOK = 0 | ErrorTokenFlag,
    UNTERMINATED_IDENTIFIER_ESCAPE_ERRORTOK = 0 | ErrorTokenFlag | UnterminatedErrorTokenFlag,
    INVALID_IDENTIFIER_ESCAPE_ERRORTOK = 1 | ErrorTokenFlag,
    UNTERMINATED_IDENTIFIER_UNICODE_ESCAPE_ERRORTOK = 2 | ErrorTokenFlag | UnterminatedErrorTokenFlag,
    INVALID_IDENTIFIER_UNICODE_ESCAPE_ERRORTOK = 3 | ErrorTokenFlag,
    UNTERMINATED_MULTILINE_COMMENT_ERRORTOK = 4 | ErrorTokenFlag | UnterminatedErrorTokenFlag,
    UNTERMINATED_NUMERIC_LITERAL_ERRORTOK = 5 | ErrorTokenFlag | UnterminatedErrorTokenFlag,
    UNTERMINATED_OCTAL_NUMBER_ERRORTOK = 6 | ErrorTokenFlag | UnterminatedErrorTokenFlag,
    INVALID_NUMERIC_LITERAL_ERRORTOK = 7 | ErrorTokenFlag,
    UNTERMINATED_STRING_LITERAL_ERRORTOK = 8 | ErrorTokenFlag | UnterminatedErrorTokenFlag,
    INVALID_STRING_LITERAL_ERRORTOK = 9 | ErrorTokenFlag,
    INVALID_PRIVATE_NAME_ERRORTOK = 10 | ErrorTokenFlag,
    UNTERMINATED_HEX_NUMBER_ERRORTOK = 11 | ErrorTokenFlag | UnterminatedErrorTokenFlag,
    UNTERMINATED_BINARY_NUMBER_ERRORTOK = 12 | ErrorTokenFlag | UnterminatedErrorTokenFlag,
    UNTERMINATED_TEMPLATE_LITERAL_ERRORTOK = 13 | ErrorTokenFlag | UnterminatedErrorTokenFlag,
    UNTERMINATED_REGEXP_LITERAL_ERRORTOK = 14 | ErrorTokenFlag | UnterminatedErrorTokenFlag,
    INVALID_TEMPLATE_LITERAL_ERRORTOK = 15 | ErrorTokenFlag,
    UNEXPECTED_ESCAPE_ERRORTOK = 16 | ErrorTokenFlag,
};
static_assert(static_cast<unsigned>(POW) <= 0x00ffffffU, "JSTokenType must be 24bits.");

struct JSTextPosition {
    JSTextPosition() = default;
    JSTextPosition(int _line, int _offset, int _lineStartOffset) 
        : line(_line)
        , offset(_offset)
        , lineStartOffset(_lineStartOffset)
    { 
        checkConsistency();
    }

    JSTextPosition operator+(int adjustment) const { return JSTextPosition(line, offset + adjustment, lineStartOffset); }
    JSTextPosition operator+(unsigned adjustment) const { return *this + static_cast<int>(adjustment); }
    JSTextPosition operator-(int adjustment) const { return *this + (- adjustment); }
    JSTextPosition operator-(unsigned adjustment) const { return *this + (- static_cast<int>(adjustment)); }

    operator int() const { return offset; }

    bool operator==(const JSTextPosition& other) const
    {
        return line == other.line
            && offset == other.offset
            && lineStartOffset == other.lineStartOffset;
    }
    bool operator!=(const JSTextPosition& other) const
    {
        return !(*this == other);
    }

    int column() const { return offset - lineStartOffset; }
    void checkConsistency()
    {
        // FIXME: We should test ASSERT(offset >= lineStartOffset); but that breaks a lot of tests.
        ASSERT(line >= 0);
        ASSERT(offset >= 0);
        ASSERT(lineStartOffset >= 0);
    }

    // FIXME: these should be unsigned.
    int line { -1 };
    int offset { -1 };
    int lineStartOffset { -1 };
};

union JSTokenData {
    struct {
        const Identifier* cooked;
        const Identifier* raw;
        bool isTail;
    };
    struct {
        uint32_t line;
        uint32_t offset;
        uint32_t lineStartOffset;
    };
    double doubleValue;
    struct {
        const Identifier* ident;
        bool escaped;
    };
    struct {
        const Identifier* bigIntString;
        uint8_t radix;
    };
    struct {
        const Identifier* pattern;
        const Identifier* flags;
    };
};

struct JSTokenLocation {
    JSTokenLocation() = default;

    int line { 0 };
    unsigned lineStartOffset { 0 };
    unsigned startOffset { 0 };
    unsigned endOffset { 0 };
};

struct JSToken {
    JSTokenType m_type { ERRORTOK };
    JSTokenData m_data { { nullptr, nullptr, false } };
    JSTokenLocation m_location;
    JSTextPosition m_startPosition;
    JSTextPosition m_endPosition;
};

ALWAYS_INLINE bool isUpdateOp(JSTokenType token)
{
    return token >= PLUSPLUS && token <= AUTOMINUSMINUS;
}

ALWAYS_INLINE bool isUnaryOp(JSTokenType token)
{
    return token & UnaryOpTokenFlag;
}

} // namespace JSC
