// Copyright (c) Huawei Technologies Co., Ltd. 2025. All rights reserved.
// This source file is part of the Cangjie project, licensed under Apache-2.0
// with Runtime Library Exception.
//
// See https://cangjie-lang.cn/pages/LICENSE for license information.

// The Cangjie API is in Beta. For details on its capabilities and limitations, please refer to the README file.


#ifndef MRT_SIGNAL_STACK_H
#define MRT_SIGNAL_STACK_H

#include <csignal>

#include "Base/Log.h"
#include "Base/LogFile.h"

#ifdef __APPLE__
#define _NSIG NSIG
using sighandler_t = sig_t;
#endif

namespace MapleRuntime {

constexpr uint64_t SIGNAL_STACK_ALLOW_NORETURN = 0x1UL;

class SignalStack {
public:
    SignalStack() noexcept : isMark(false), isUserSigHandler(false) {}

    bool IsMarked() { return isMark; }

    void MarkSig(int signal)
    {
        if (!isMark) {
            Register(signal);
            isMark = true;
        }
    }

    bool IsUserSigHandler() { return isUserSigHandler; }

    void SetUserSigHandler(bool flag)
    {
        isUserSigHandler = flag;
    }

    void Register(int signal);

    struct sigaction GetAction();
    void SetAction(const struct sigaction* newAction);

    void AddHandler(SignalAction* sa);
    void RemoveHandler(bool (*fn)(int, siginfo_t*, void*));

    static void Handler(int signal, siginfo_t* siginfo, void* ucontextRaw);
    static void HandlerImpl(void* args);
    static void InitializeSignalStack();
    static SignalStack* GetStacks() { return stacks; }
    struct sigaction sigAction;
private:
    bool isMark;

    bool isUserSigHandler;

    std::vector<SignalAction> handlerStack;
#ifdef __APPLE__
    static SignalStack stacks[NSIG];
#else
    static SignalStack stacks[_NSIG];
#endif
};
} // namespace MapleRuntime
#endif // MRT_SIGNAL_STACK_H