/*
 * Copyright (c) 2021 Huawei Device Co., Ltd.
 * Licensed 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.
 */

#ifndef ECMASCRIPT_COMPILER_CALL_SIGNATURE_H
#define ECMASCRIPT_COMPILER_CALL_SIGNATURE_H

#include <array>
#include <memory>

#include "ecmascript/base/config.h"
#include "ecmascript/compiler/variable_type.h"

#include "libpandabase/macros.h"
#include "libpandabase/utils/bit_field.h"

namespace panda::ecmascript::kungfu {
class Circuit;

enum class ArgumentsOrder {
    DEFAULT_ORDER,  // Push Arguments in stack from right -> left
};

// Lightweight replacement for std::function<void*(void*)>.
// Avoids type-erasure overhead per stub (~956 unique lambda closures → a few template factories).
class TargetConstructor {
public:
    using FactoryFn = void *(*)(void *env, void *data);

    TargetConstructor() : fn_(nullptr), data_(nullptr) {}
    TargetConstructor(std::nullptr_t) : fn_(nullptr), data_(nullptr) {}  // NOLINT
    TargetConstructor(FactoryFn fn, void *data) : fn_(fn), data_(data) {}

    void *operator()(void *env) const
    {
        return fn_(env, data_);
    }

    explicit operator bool() const
    {
        return fn_ != nullptr;
    }

    bool operator==(std::nullptr_t) const
    {
        return fn_ == nullptr;
    }

    bool operator!=(std::nullptr_t) const
    {
        return fn_ != nullptr;
    }

private:
    FactoryFn fn_;
    void *data_;
};

class CallSignature;
class Environment;

// Shared template factory for stubs with (CallSignature*, Environment*) constructor.
// Used by BC, Common, and Baseline stubs. Replaces per-stub lambda closures.
template <typename BuilderT>
static inline void *StubBuilderFactory(void *env, void *data)
{
    return static_cast<void *>(
        new BuilderT(static_cast<CallSignature *>(data), static_cast<Environment *>(env)));
}

class CallSignature {
public:
    enum class TargetKind : uint8_t {
        COMMON_STUB = 0,
        RUNTIME_STUB,
        RUNTIME_STUB_VARARGS,
        RUNTIME_STUB_NO_GC,
        ASM_CALL_BARRIER_STUB,
        OPTIMIZED_STUB,
        OPTIMIZED_FAST_CALL_STUB,
        DEOPT_STUB,
        BYTECODE_HANDLER,
        BYTECODE_DEBUGGER_HANDLER,
        BYTECODE_HELPER_HANDLER,
    #if ECMASCRIPT_ENABLE_INTERPRETER_PGO_STUBS
        BYTECODE_PROFILE_HANDLER,
    #if ECMASCRIPT_ENABLE_INTERPRETER_JIT_STUBS
        BYTECODE_JIT_PROFILE_HANDLER,
    #endif
    #endif
        BYTECODE_STW_COPY_HANDLER,
        JSFUNCTION,
        BUILTINS_STUB,
        BUILTINS_WITH_ARGV_STUB,
        BASELINE_STUB,
        COMMON_STW_COPY_STUB,
        BUILTINS_STW_COPY_STUB,

        STUB_BEGIN = COMMON_STUB,
        STUB_END = BYTECODE_HANDLER,
        BCHANDLER_BEGIN = BYTECODE_HANDLER,
        BCHANDLER_END = JSFUNCTION
    };
    enum class CallConv: uint8_t {
        CCallConv = 0,
        GHCCallConv = 1,
        WebKitJSCallConv = 2,
    };
    // ParamAttr only works for LLVM backend.
    enum class ParamAttr: uint8_t {
        NoAttr = 0,
        Dead
    };
    static constexpr size_t TARGET_KIND_BIT_LENGTH = 5;
    static constexpr size_t CALL_CONV_BIT_LENGTH = 2;
    using TargetKindBit = panda::BitField<TargetKind, 0, TARGET_KIND_BIT_LENGTH>;
    using CallConvBit = TargetKindBit::NextField<CallConv, CALL_CONV_BIT_LENGTH>;
    using VariadicArgsBit = CallConvBit::NextField<bool, 1>;
    using TailCallBit = VariadicArgsBit::NextField<bool, 1>;
    using NoTailCallBit = TailCallBit::NextField<bool, 1>;
    using GCLeafFunctionBit = NoTailCallBit::NextField<bool, 1>;

    CallSignature(std::string name, int flags, size_t paramCounter, ArgumentsOrder order,
                  VariableType returnType)
        : name_(name), paramCounter_(paramCounter), order_(order), returnType_(returnType)
    {
        SetTargetKind(TargetKind::COMMON_STUB);
        SetCallConv(CallSignature::CallConv::CCallConv);
        SetTailCall(false);
        SetNoTailCall(false);
        SetGCLeafFunction(false);
        SetVariadicArgs(flags);
    }

    CallSignature(std::string name, int flags, ArgumentsOrder order, VariableType returnType,
                  std::initializer_list<VariableType> params)
        : CallSignature(std::move(name), flags, params.size(), order, returnType)
    {
        paramsType_ = std::make_unique<std::vector<VariableType>>(params);
    }

    CallSignature() = default;

    ~CallSignature() = default;

    CallSignature(CallSignature const &other)
    {
        name_ = other.name_;
        paramCounter_ = other.paramCounter_;
        order_ = other.order_;
        id_ = other.id_;
        returnType_ = other.returnType_;
        constructor_ = other.constructor_;
        if (paramCounter_ > 0 && other.paramsType_ != nullptr) {
            paramsType_ = std::make_unique<std::vector<VariableType>>(paramCounter_);
            for (size_t i = 0; i < paramCounter_; i++) {
                (*paramsType_)[i] = other.GetParametersType()[i];
            }
        }
        kind_ = other.kind_;
    }

    CallSignature &operator=(CallSignature const &other)
    {
        name_ = other.name_;
        paramCounter_ = other.paramCounter_;
        order_ = other.order_;
        id_ = other.id_;
        returnType_ = other.returnType_;
        constructor_ = other.constructor_;
        if (paramCounter_ > 0 && other.paramsType_ != nullptr) {
            paramsType_ = std::make_unique<std::vector<VariableType>>(paramCounter_);
            for (size_t i = 0; i < paramCounter_; i++) {
                (*paramsType_)[i] = other.GetParametersType()[i];
            }
        }
        kind_ = other.kind_;
        return *this;
    }

    bool IsCommonStub() const
    {
        return (GetTargetKind() == TargetKind::COMMON_STUB);
    }

    bool IsRuntimeVAStub() const
    {
        return (GetTargetKind() == TargetKind::RUNTIME_STUB_VARARGS);
    }

    bool IsRuntimeStub() const
    {
        return (GetTargetKind() == TargetKind::RUNTIME_STUB);
    }

    bool IsASMCallBarrierStub() const
    {
        return (GetTargetKind() == TargetKind::ASM_CALL_BARRIER_STUB);
    }

    bool IsRuntimeNGCStub() const
    {
        return (GetTargetKind() == TargetKind::RUNTIME_STUB_NO_GC);
    }

    bool IsOptimizedStub() const
    {
        return (GetTargetKind() == TargetKind::OPTIMIZED_STUB);
    }

    bool IsOptimizedFastCallStub() const
    {
        return (GetTargetKind() == TargetKind::OPTIMIZED_FAST_CALL_STUB);
    }

    bool IsBCDebuggerStub() const
    {
        return (GetTargetKind() == TargetKind::BYTECODE_DEBUGGER_HANDLER);
    }

    bool IsStub() const
    {
        TargetKind targetKind = GetTargetKind();
        return TargetKind::STUB_BEGIN <= targetKind && targetKind < TargetKind::STUB_END;
    }

    bool IsBCStub() const
    {
        TargetKind targetKind = GetTargetKind();
        return TargetKind::BCHANDLER_BEGIN <= targetKind && targetKind < TargetKind::BCHANDLER_END;
    }

    bool IsBuiltinsStub() const
    {
        return (GetTargetKind() == TargetKind::BUILTINS_STUB);
    }

    bool IsBuiltinsWithArgvStub() const
    {
        return (GetTargetKind() == TargetKind::BUILTINS_WITH_ARGV_STUB);
    }

    bool IsBCHandlerStub() const
    {
        return (GetTargetKind() == TargetKind::BYTECODE_HANDLER);
    }

    bool IsDeoptStub() const
    {
        return (GetTargetKind() == TargetKind::DEOPT_STUB);
    }

    bool IsBaselineStub() const
    {
        return (GetTargetKind() == TargetKind::BASELINE_STUB);
    }

    void SetParameters(VariableType *paramsType)
    {
        if (paramCounter_ > 0 && paramsType_ == nullptr) {
            paramsType_ = std::make_unique<std::vector<VariableType>>(paramCounter_);
            for (size_t i = 0; i < paramCounter_; i++) {
                (*paramsType_)[i] = paramsType[i];
            }
        }
    }

    VariableType *GetParametersType() const
    {
        if (paramsType_ != nullptr) {
            return paramsType_->data();
        } else {
            return nullptr;
        }
    }

    void SetParamAttr(std::vector<ParamAttr> &&paramAttr)
    {
        if (paramCounter_ > 0 && paramsAttr_ == nullptr) {
            paramsAttr_ = std::make_unique<std::vector<ParamAttr>>(paramAttr);
        }
    }

    std::vector<ParamAttr> *GetParamAttr() const
    {
        if (paramsAttr_ != nullptr) {
            return paramsAttr_.get();
        } else {
            return nullptr;
        }
    }

    size_t GetParametersCount() const
    {
        return paramCounter_;
    }

    VariableType GetReturnType() const
    {
        return returnType_;
    }

    ArgumentsOrder GetArgumentsOrder() const
    {
        return order_;
    }

    bool IsVariadicArgs() const
    {
        return VariadicArgsBit::Decode(kind_);
    }

    void SetVariadicArgs(bool variable)
    {
        VariadicArgsBit::Set<uint64_t>(variable, &kind_);
    }

    void SetNoTailCall(bool noTailCall)
    {
        NoTailCallBit::Set<uint64_t>(noTailCall, &kind_);
    }

    bool IsNoTailCall() const
    {
        return NoTailCallBit::Decode(kind_);
    }

    void SetTailCall(bool tailCall)
    {
        TailCallBit::Set<uint64_t>(tailCall, &kind_);
    }

    bool GetTailCall() const
    {
        return TailCallBit::Decode(kind_);
    }

    // When setting this flag to true
    // ensure the function doesn't cause GC,
    // throw exceptions, or lead to LAZY deopt.
    void SetGCLeafFunction(bool value)
    {
        GCLeafFunctionBit::Set<uint64_t>(value, &kind_);
    }

    bool GetGCLeafFunction() const
    {
        return GCLeafFunctionBit::Decode(kind_);
    }

    TargetKind GetTargetKind() const
    {
        return TargetKindBit::Decode(kind_);
    }

    void SetTargetKind(TargetKind kind)
    {
        TargetKindBit::Set<uint64_t>(kind, &kind_);
    }

    CallConv GetCallConv() const
    {
        return CallConvBit::Decode(kind_);
    }

    void SetCallConv(CallConv cc)
    {
        CallConvBit::Set<uint64_t>(cc, &kind_);
    }

    const std::string &GetName() const
    {
        return name_;
    }

    void SetName(const std::string &str)
    {
        name_ = str;
    }

    void SetConstructor(TargetConstructor ctor)
    {
        constructor_ = ctor;
    }

    TargetConstructor GetConstructor() const
    {
        return constructor_;
    }

    bool HasConstructor() const
    {
        return constructor_ != nullptr;
    }

    int GetID() const
    {
        return id_;
    }

    void SetID(int id)
    {
        id_ = id;
    }

    bool IsStwCopyStub() const
    {
        return isStwCopyStub_;
    }

    void SetStwCopyStub(bool flag)
    {
        isStwCopyStub_ = flag;
    }

private:
    std::string name_;
    size_t paramCounter_ {0};
    int id_ {-1};
    ArgumentsOrder order_ {ArgumentsOrder::DEFAULT_ORDER};
    VariableType returnType_ {VariableType::VOID()};
    std::unique_ptr<std::vector<VariableType>> paramsType_ {nullptr};
    std::unique_ptr<std::vector<ParamAttr>> paramsAttr_ {nullptr};
    TargetConstructor constructor_ {nullptr};
    uint64_t kind_ {0};
    bool isStwCopyStub_ {false};
};

#define EXPLICIT_CALL_SIGNATURE_LIST(V)         \
    V(Add)                                      \
    V(Sub)                                      \
    V(Mul)                                      \
    V(MulGCTest)                                \
    V(Div)                                      \
    V(Mod)                                      \
    V(TypeOf)                                   \
    V(Equal)                                    \
    V(NotEqual)                                 \
    V(StrictEqual)                              \
    V(StrictNotEqual)                           \
    V(Less)                                     \
    V(LessEq)                                   \
    V(Greater)                                  \
    V(GreaterEq)                                \
    V(Shl)                                      \
    V(Shr)                                      \
    V(Ashr)                                     \
    V(And)                                      \
    V(Or)                                       \
    V(Xor)                                      \
    V(IsIn)                                     \
    V(Instanceof)                               \
    V(OrdinaryHasInstance)                      \
    V(Inc)                                      \
    V(Dec)                                      \
    V(Neg)                                      \
    V(Not)                                      \
    V(ToBooleanTrue)                            \
    V(ToBooleanFalse)                           \
    V(SetPropertyByName)                        \
    V(DeprecatedSetPropertyByName)              \
    V(SetPropertyByNameWithOwn)                 \
    V(SetPropertyByValue)                       \
    V(DeprecatedSetPropertyByValue)             \
    V(TryLdGlobalByName)                        \
    V(TryStGlobalByName)                        \
    V(LdGlobalVar)                              \
    V(StGlobalVar)                              \
    V(StOwnByIndex)                             \
    V(StOwnByValue)                             \
    V(StOwnByName)                              \
    V(StOwnByValueWithNameSet)                  \
    V(StOwnByNameWithNameSet)                   \
    V(StObjByIndex)                             \
    V(LdObjByIndex)                             \
    V(JSTaggedValueHasProperty)                 \
    V(SetPropertyByValueWithOwn)                \
    V(GetPropertyByName)                        \
    V(SetPropertyByNameWithMega)                \
    V(GetPropertyByNameWithMega)                \
    V(DeprecatedGetPropertyByName)              \
    V(GetPropertyByIndex)                       \
    V(SetPropertyByIndex)                       \
    V(SetPropertyByIndexWithOwn)                \
    V(GetPropertyByValue)                       \
    V(DeprecatedGetPropertyByValue)             \
    V(TryLoadICByName)                          \
    V(TryLoadICByValue)                         \
    V(TryStoreICByName)                         \
    V(TryStoreICByValue)                        \
    V(SetValueWithBarrier)                      \
    V(SetNonSValueWithBarrier)                  \
    V(SetSValueWithBarrier)                     \
    V(NewLexicalEnv)                            \
    V(CopyRestArgs)                             \
    V(CreateObjectHavingMethod)                 \
    V(GetUnmappedArgs)                          \
    V(GetCallSpreadArgs)                        \
    V(NewThisObjectChecked)                     \
    V(ConstructorCheck)                         \
    V(CreateEmptyArray)                         \
    V(CreateArrayWithBuffer)                    \
    V(NewJSObject)                              \
    V(FastNewThisObject)                        \
    V(FastSuperAllocateThis)                    \
    V(GetTaggedArrayPtrTest)                    \
    V(BytecodeHandler)                          \
    V(Builtins)                                 \
    V(BuiltinsWithArgv)                         \
    V(BytecodeDebuggerHandler)                  \
    V(CallRuntime)                              \
    V(AsmInterpreterEntry)                      \
    V(CallArg0AndCheckToBaseline)               \
    V(CallArg1AndCheckToBaseline)               \
    V(CallArgs2AndCheckToBaseline)              \
    V(CallArgs3AndCheckToBaseline)              \
    V(CallThisArg0AndCheckToBaseline)           \
    V(CallThisArg1AndCheckToBaseline)           \
    V(CallThisArgs2AndCheckToBaseline)          \
    V(CallThisArgs3AndCheckToBaseline)          \
    V(CallRangeAndCheckToBaseline)              \
    V(CallNewAndCheckToBaseline)                \
    V(SuperCallAndCheckToBaseline)              \
    V(CallThisRangeAndCheckToBaseline)          \
    V(ArkSteedCallEntry)                        \
    V(SteedCallAndPushArgv)                     \
    V(SteedCallWithArgVAndPushArgv)             \
    V(GeneratorReEnterAsmInterp)                \
    V(CallRuntimeWithArgv)                      \
    V(OptimizedCallAndPushArgv)                 \
    V(OptimizedFastCallAndPushArgv)             \
    V(AOTCallToAsmInterBridge)                  \
    V(FastCallToAsmInterBridge)                 \
    V(PushCallArg0AndDispatch)                  \
    V(PushCallArgsAndDispatchNative)            \
    V(PushCallArg1AndDispatch)                  \
    V(PushCallArgs2AndDispatch)                 \
    V(PushCallArgs3AndDispatch)                 \
    V(PushCallRangeAndDispatch)                 \
    V(PushCallRangeAndDispatchNative)           \
    V(PushCallThisRangeAndDispatch)             \
    V(PushCallThisArg0AndDispatch)              \
    V(PushCallThisArg1AndDispatch)              \
    V(PushCallThisArgs2AndDispatch)             \
    V(PushCallThisArgs3AndDispatch)             \
    V(PushCallNewAndDispatchNative)             \
    V(PushNewTargetAndDispatchNative)           \
    V(PushCallNewAndDispatch)                   \
    V(PushSuperCallAndDispatch)                 \
    V(CallGetter)                               \
    V(CallSetter)                               \
    V(CallContainersArgs2)                      \
    V(CallContainersArgs3)                      \
    V(JSCallWithArgV)                           \
    V(JSFastCallWithArgV)                       \
    V(JSFastCallWithArgVAndPushArgv)            \
    V(JSCallWithArgVAndPushArgv)                \
    V(SuperCallWithArgV)                        \
    V(ResumeRspAndDispatch)                     \
    V(ResumeRspAndReturn)                       \
    V(ResumeRspAndReturnBaseline)               \
    V(ResumeCaughtFrameAndDispatch)             \
    V(ResumeUncaughtFrameAndReturn)             \
    V(ResumeRspAndRollback)                     \
    V(BigIntEquals)                             \
    V(BigIntSameValueZero)                      \
    V(CallBigIntAsIntN)                         \
    V(CallBigIntAsUintN)                        \
    V(Dump)                                     \
    V(DebugDump)                                \
    V(DumpWithHint)                             \
    V(DebugDumpWithHint)                        \
    V(DebugPrint)                               \
    V(DebugPrintCustom)                         \
    V(DebugPrintInstruction)                    \
    V(CollectingOpcodes)                        \
    V(DebugOsrEntry)                            \
    V(Comment)                                  \
    V(FatalPrint)                               \
    V(FatalPrintCustom)                         \
    V(GetActualArgvNoGC)                        \
    V(InsertOldToNewRSet)                       \
    V(InsertLocalToShareRSet)                   \
    V(SetBitAtomic)                             \
    V(DoubleToInt)                              \
    V(SaturateTruncDoubleToInt32)            \
    V(FloatMod)                                 \
    V(FloatAcos)                                \
    V(FloatAcosh)                               \
    V(FloatAsin)                                \
    V(FloatAsinh)                               \
    V(FloatAtan)                                \
    V(FloatAtan2)                               \
    V(FloatAtanh)                               \
    V(FloatCos)                                 \
    V(FloatCosh)                                \
    V(FloatSin)                                 \
    V(FloatSinh)                                \
    V(FloatTan)                                 \
    V(FloatTanh)                                \
    V(FloatTrunc)                               \
    V(FloatLog)                                 \
    V(FloatLog2)                                \
    V(FloatLog10)                               \
    V(FloatLog1p)                               \
    V(FloatExp)                                 \
    V(FloatExpm1)                               \
    V(FloatCbrt)                                \
    V(FloatClz32)                               \
    V(FloatFloor)                               \
    V(FloatPow)                                 \
    V(FloatCeil)                                \
    V(CallDateNow)                              \
    V(UpdateFieldType)                          \
    V(MarkingBarrier)                           \
    V(SharedGCMarkingBarrier)                   \
    V(TryFillSweptRegion)                       \
    V(CMCGCMarkingBarrier)                      \
    V(CallArg0)                                 \
    V(CallArg1)                                 \
    V(CallArgs2)                                \
    V(CallArgs3)                                \
    V(CallThisRange)                            \
    V(CallRange)                                \
    V(JSCall)                                   \
    V(JSOptimizedCall)                          \
    V(JSOptimizedFastCall)                      \
    V(JSFunctionEntry)                          \
    V(OptimizedFastCallEntry)                   \
    V(JSProxyCallInternalWithArgV)              \
    V(JSObjectGetMethod)                        \
    V(JsProxyCallInternal)                      \
    V(JsBoundCallInternal)                      \
    V(LazyDeoptEntry)                           \
    V(DeoptHandlerAsm)                          \
    V(JSCallNew)                                \
    V(CallOptimized)                            \
    V(TimeClip)                                 \
    V(CalcTimeValue)                            \
    V(CallReturnWithArgv)                       \
    V(StartCallTimer)                           \
    V(EndCallTimer)                             \
    V(GetSingleCharCodeByIndex)                 \
    V(CreateStringBySingleCharCode)             \
    V(FastStringEqual)                          \
    V(FastStringAdd)                            \
    V(StringAdd)                                \
    V(DeleteObjectProperty)                     \
    V(Getpropiterator)                          \
    V(Getnextpropname)                          \
    V(CreateJSSetIterator)                      \
    V(CreateJSMapIterator)                      \
    V(JSMapGet)                                 \
    V(JSMapHas)                                 \
    V(JSMapKeys)                                \
    V(JSMapValues)                              \
    V(JSSetHas)                                 \
    V(JSSetAdd)                                 \
    V(JSProxyGetProperty)                       \
    V(JSProxySetProperty)                       \
    V(JSProxySetPropertyNoThrow)                \
    V(GrowElementsCapacity)                     \
    V(CreateJSTypedArrayEntries)                \
    V(CreateJSTypedArrayKeys)                   \
    V(CreateJSTypedArrayValues)                 \
    V(JSMapDelete)                              \
    V(JSSetDelete)                              \
    V(JSSetEntries)                             \
    V(JSHClassFindProtoTransitions)             \
    V(FinishObjSizeTracking)                    \
    V(NumberHelperStringToDouble)               \
    V(IntLexicographicCompare)                  \
    V(DoubleLexicographicCompare)               \
    V(FastArraySortString)                      \
    V(StringToNumber)                           \
    V(StringGetStart)                           \
    V(StringGetEnd)                             \
    V(ArrayTrim)                                \
    V(CopyTypedArrayBuffer)                     \
    V(OptimizedFastJmp)                         \
    V(CallArg0AndDispatchFromBaseline)          \
    V(CallArg1AndDispatchFromBaseline)          \
    V(CallArgs2AndDispatchFromBaseline)         \
    V(CallArgs3AndDispatchFromBaseline)         \
    V(CallThisArg0AndDispatchFromBaseline)      \
    V(CallThisArg1AndDispatchFromBaseline)      \
    V(CallThisArgs2AndDispatchFromBaseline)     \
    V(CallThisArgs3AndDispatchFromBaseline)     \
    V(CallRangeAndDispatchFromBaseline)         \
    V(CallNewAndDispatchFromBaseline)           \
    V(SuperCallAndDispatchFromBaseline)         \
    V(CallThisRangeAndDispatchFromBaseline)     \
    V(CallArg0AndCheckToBaselineFromBaseline)        \
    V(CallArg1AndCheckToBaselineFromBaseline)        \
    V(CallArgs2AndCheckToBaselineFromBaseline)       \
    V(CallArgs3AndCheckToBaselineFromBaseline)       \
    V(CallThisArg0AndCheckToBaselineFromBaseline)    \
    V(CallThisArg1AndCheckToBaselineFromBaseline)    \
    V(CallThisArgs2AndCheckToBaselineFromBaseline)   \
    V(CallThisArgs3AndCheckToBaselineFromBaseline)   \
    V(CallRangeAndCheckToBaselineFromBaseline)       \
    V(CallNewAndCheckToBaselineFromBaseline)         \
    V(SuperCallAndCheckToBaselineFromBaseline)       \
    V(CallThisRangeAndCheckToBaselineFromBaseline)   \
    V(SameValue)                                     \
    V(GetBaselineBuiltinFp)                          \
    V(StringIteratorNext)                            \
    V(Definefunc)                                    \
    V(DefineNormalFuncForJit)                        \
    V(DefineArrowFuncForJit)                         \
    V(DefineBaseConstructorForJit)                   \
    V(DefineField)                                   \
    V(CallArg0Stub)                                  \
    V(CallArg1Stub)                                  \
    V(CallArg2Stub)                                  \
    V(CallArg3Stub)                                  \
    V(CallThis0Stub)                                 \
    V(CallThis1Stub)                                 \
    V(CallThis2Stub)                                 \
    V(CallThis3Stub)                                 \
    V(NewFloat32ArrayWithNoArgs)                     \
    V(NewFloat32Array)                               \
    V(StringLoadElement)                             \
    V(GetStringFromConstPool)                        \
    V(GetObjectFromConstPool)                        \
    V(GetPrototype)                                  \
    V(FastCallSelector)                              \
    V(CheckSuperAndNew)                              \
    V(SuperCallAndConstructorCheck)                  \
    V(ConvertCharToInt32)                            \
    V(ConvertCharToDouble)                           \
    V(ConvertCharToString)                           \
    V(ASMFastWriteBarrier)                           \
    V(VerifyBarrier)                                 \
    V(SortTypedArray)                                \
    V(ReverseTypedArray)                             \
    V(IsFastRegExp)                                  \
    V(MapIteratorNext)                               \
    V(SetIteratorNext)                               \
    V(CreateLocalToShare)                            \
    V(CreateOldToNew)                                \
    V(BatchBarrier)                                  \
    V(CopyObjectPrimitive)                           \
    V(ObjectCopy)                                    \
    V(ArrayIteratorNext)                             \
    V(GetIterator)                                   \
    V(MoveBarrierInRegion)                           \
    V(FillObject)                                    \
    V(MoveBarrierCrossRegion)                        \
    V(ReverseArray)                                  \
    V(LrInt)                                         \
    V(FindEntryFromNameDictionary)                   \
    V(ReverseBarrier)                                \
    V(FindPatchModule)                               \
    V(FatalPrintMisstakenResolvedBinding)            \
    V(LoadNativeModuleFailed)                        \
    V(GetExternalModuleVar)                          \
    V(GetValueWithBarrier)                           \
    V(LdLexVar)                                      \
    V(StLexVar)                                      \
    V(ReadBarrier)                                   \
    V(ComputeStringHashcode)                         \
    V(CopyCallTarget)                                \
    V(CopyArgvArray)                                 \
    V(MarkRSetCardTable)                             \
    V(MarkInBuffer)                                  \
    V(BatchMarkInBuffer)                             \
    V(LoadBarrierCopyBack)                           \
    V(CMCSetValueWithBarrier)                        \
    V(CheckObjectForCMS)

#define DECL_CALL_SIGNATURE(name)                                  \
class name##CallSignature final {                                  \
    public:                                                        \
        static void Initialize(CallSignature *descriptor);         \
    };
EXPLICIT_CALL_SIGNATURE_LIST(DECL_CALL_SIGNATURE)

// NOLINTNEXTLINE(cppcoreguidelines-macro-usage)
#define DEF_CALL_SIGNATURE(name)                                  \
    void name##CallSignature::Initialize([[maybe_unused]] CallSignature *callSign)
}  // namespace panda::ecmascript::kungfu
#endif  // ECMASCRIPT_COMPILER_CALL_SIGNATURE_H