/*
 *
 *    Copyright (c) 2020 Project CHIP Authors
 *    Copyright (c) 2018 Nest Labs, Inc.
 *
 *    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.
 */

/**
 *    @file
 *          Defines the public interface for the Device Layer PlatformManager object.
 */

#pragma once

#include <platform/AttributeList.h>
#include <platform/CHIPDeviceBuildConfig.h>
#include <platform/CHIPDeviceEvent.h>
#include <system/PlatformEventSupport.h>
#include <system/SystemLayer.h>

namespace chip {

namespace Dnssd {
class DiscoveryImplPlatform;
}

namespace DeviceLayer {

static constexpr size_t kMaxCalendarTypes = 12;

class PlatformManagerImpl;
class ConnectivityManagerImpl;
class ConfigurationManagerImpl;
class DeviceControlServer;
class TraitManager;
class ThreadStackManagerImpl;
class TimeSyncManager;

namespace Internal {
class BLEManagerImpl;
template <class>
class GenericConfigurationManagerImpl;
template <class>
class GenericPlatformManagerImpl;
template <class>
class GenericPlatformManagerImpl_FreeRTOS;
template <class>
class GenericPlatformManagerImpl_POSIX;
template <class>
class GenericPlatformManagerImpl_Zephyr;
template <class>
class GenericConnectivityManagerImpl_Thread;
template <class>
class GenericThreadStackManagerImpl_OpenThread;
template <class>
class GenericThreadStackManagerImpl_OpenThread_LwIP;
} // namespace Internal

/**
 * Defines the delegate class of Platform Manager to notify platform updates.
 */
class PlatformManagerDelegate
{
public:
    virtual ~PlatformManagerDelegate() {}

    /**
     * @brief
     *   Called by the current Node after completing a boot or reboot process.
     */
    virtual void OnStartUp(uint32_t softwareVersion) {}

    /**
     * @brief
     *   Called by the current Node prior to any orderly shutdown sequence on a
     *   best-effort basis.
     */
    virtual void OnShutDown() {}
};

/**
 * Provides features for initializing and interacting with the chip network
 * stack on a chip-enabled device.
 */
class PlatformManager
{
    using ImplClass = ::chip::DeviceLayer::PlatformManagerImpl;

public:
    // ===== Members that define the public interface of the PlatformManager

    typedef void (*EventHandlerFunct)(const ChipDeviceEvent * event, intptr_t arg);

    /**
     * InitChipStack() initializes the PlatformManager.  After calling that, a
     * consumer is allowed to call either StartEventLoopTask or RunEventLoop to
     * process pending work.  Calling both is not allowed: it must be one or the
     * other.
     */
    CHIP_ERROR InitChipStack();
    CHIP_ERROR AddEventHandler(EventHandlerFunct handler, intptr_t arg = 0);
    void RemoveEventHandler(EventHandlerFunct handler, intptr_t arg = 0);
    void SetDelegate(PlatformManagerDelegate * delegate) { mDelegate = delegate; }
    PlatformManagerDelegate * GetDelegate() const { return mDelegate; }

    /**
     * Should be called after initializing all layers of the Matter stack to
     * run all needed post-startup actions.
     */
    void HandleServerStarted();

    /**
     * Should be called before shutting down the Matter stack or restarting the
     * application to run all needed pre-shutdown actions.
     */
    void HandleServerShuttingDown();

    /**
     * ScheduleWork can be called after InitChipStack has been called.  Calls
     * that happen before either StartEventLoopTask or RunEventLoop will queue
     * the work up but that work will NOT run until one of those functions is
     * called.
     *
     * ScheduleWork can be called safely on any thread without locking the
     * stack.  When called from a thread that is not doing the stack work item
     * processing, the callback function may be called (on the work item
     * processing thread) before ScheduleWork returns.
     */
    void ScheduleWork(AsyncWorkFunct workFunct, intptr_t arg = 0);

    /**
     * Process work items until StopEventLoopTask is called.  RunEventLoop will
     * not return until work item processing is stopped.  Once it returns it
     * guarantees that no more work items will be processed unless there's
     * another call to RunEventLoop.
     *
     * Consumers that call RunEventLoop must not call StartEventLoopTask.
     *
     * Consumers that call RunEventLoop must ensure that RunEventLoop returns
     * before calling Shutdown.
     */
    void RunEventLoop();

    /**
     * Process work items until StopEventLoopTask is called.
     *
     * StartEventLoopTask processes items asynchronously.  It can return before
     * any items are processed, or after some items have been processed, or
     * while an item is being processed, or even after StopEventLoopTask() has
     * been called (e.g. if ScheduleWork() was called before StartEventLoopTask
     * was called, with a work item that calls StopEventLoopTask).
     *
     * Consumers that call StartEventLoopTask must not call RunEventLoop.
     *
     * Consumers that call StartEventLoopTask must ensure that they call
     * StopEventLoopTask before calling Shutdown.
     */
    CHIP_ERROR StartEventLoopTask();

    /**
     * Stop processing of work items by the event loop.
     *
     * If called from outside work item processing, StopEventLoopTask guarantees
     * that any currently-executing work item completes execution and no more
     * work items will run after StopEventLoopTask returns.  This is generally
     * how StopEventLoopTask is used in conjunction with StartEventLoopTask.
     *
     * If called from inside work item processing, StopEventLoopTask makes no
     * guarantees about exactly when work item processing will stop.  What it
     * does guarantee is that if it is used this way in conjunction with
     * RunEventLoop then all work item processing will stop before RunEventLoop
     * returns.
     */
    CHIP_ERROR StopEventLoopTask();
    void LockChipStack();
    bool TryLockChipStack();
    void UnlockChipStack();
    void Shutdown();

#if CHIP_STACK_LOCK_TRACKING_ENABLED
    bool IsChipStackLockedByCurrentThread() const;
#endif

    /*
     * PostEvent can be called safely on any thread without locking the stack.
     * When called from a thread that is not doing the stack work item
     * processing, the event might get dispatched (on the work item processing
     * thread) before PostEvent returns.
     */
    [[nodiscard]] CHIP_ERROR PostEvent(const ChipDeviceEvent * event);
    void PostEventOrDie(const ChipDeviceEvent * event);

private:
    bool mInitialized                   = false;
    PlatformManagerDelegate * mDelegate = nullptr;

    // ===== Members for internal use by the following friends.

    friend class PlatformManagerImpl;
    friend class ConnectivityManagerImpl;
    friend class ConfigurationManagerImpl;
    friend class DeviceControlServer;
    friend class Dnssd::DiscoveryImplPlatform;
    friend class FailSafeContext;
    friend class TraitManager;
    friend class ThreadStackManagerImpl;
    friend class TimeSyncManager;
    friend class Internal::BLEManagerImpl;
    template <class>
    friend class Internal::GenericPlatformManagerImpl;
    template <class>
    friend class Internal::GenericPlatformManagerImpl_FreeRTOS;
    template <class>
    friend class Internal::GenericPlatformManagerImpl_POSIX;
    template <class>
    friend class Internal::GenericPlatformManagerImpl_Zephyr;
    template <class>
    friend class Internal::GenericConnectivityManagerImpl_Thread;
    template <class>
    friend class Internal::GenericThreadStackManagerImpl_OpenThread;
    template <class>
    friend class Internal::GenericThreadStackManagerImpl_OpenThread_LwIP;
    template <class>
    friend class Internal::GenericConfigurationManagerImpl;
    friend class System::PlatformEventing;

    void DispatchEvent(const ChipDeviceEvent * event);
    CHIP_ERROR StartChipTimer(System::Clock::Timeout duration);

protected:
    // Construction/destruction limited to subclasses.
    PlatformManager()  = default;
    ~PlatformManager() = default;

    // No copy, move or assignment.
    PlatformManager(const PlatformManager &)  = delete;
    PlatformManager(const PlatformManager &&) = delete;
    PlatformManager & operator=(const PlatformManager &) = delete;
};

/**
 * Returns the public interface of the PlatformManager singleton object.
 *
 * chip applications should use this to access features of the PlatformManager object
 * that are common to all platforms.
 */
extern PlatformManager & PlatformMgr();

/**
 * Returns the platform-specific implementation of the PlatformManager singleton object.
 *
 * chip applications can use this to gain access to features of the PlatformManager
 * that are specific to the selected platform.
 */
extern PlatformManagerImpl & PlatformMgrImpl();

/**
 * @brief
 * RAII locking for PlatformManager to simplify management of
 * LockChipStack()/UnlockChipStack calls.
 */
class StackLock
{
public:
    StackLock() { PlatformMgr().LockChipStack(); }

    ~StackLock() { PlatformMgr().UnlockChipStack(); }
};

/**
 * @brief
 * RAII unlocking for PlatformManager to simplify management of
 * LockChipStack()/UnlockChipStack calls.
 */
class StackUnlock
{
public:
    StackUnlock() { PlatformMgr().UnlockChipStack(); }
    ~StackUnlock() { PlatformMgr().LockChipStack(); }
};

} // namespace DeviceLayer
} // namespace chip

/* Include a header file containing the implementation of the ConfigurationManager
 * object for the selected platform.
 */
#ifdef EXTERNAL_PLATFORMMANAGERIMPL_HEADER
#include EXTERNAL_PLATFORMMANAGERIMPL_HEADER
#elif defined(CHIP_DEVICE_LAYER_TARGET)
#define PLATFORMMANAGERIMPL_HEADER <platform/CHIP_DEVICE_LAYER_TARGET/PlatformManagerImpl.h>
#include PLATFORMMANAGERIMPL_HEADER
#endif // defined(CHIP_DEVICE_LAYER_TARGET)

namespace chip {
namespace DeviceLayer {

#if CHIP_STACK_LOCK_TRACKING_ENABLED
inline bool PlatformManager::IsChipStackLockedByCurrentThread() const
{
    return static_cast<const ImplClass *>(this)->_IsChipStackLockedByCurrentThread();
}
#endif

inline CHIP_ERROR PlatformManager::InitChipStack()
{
    // NOTE: this is NOT thread safe and cannot be as the chip stack lock is prepared by
    // InitChipStack itself on many platforms.
    //
    // In the future, this could be moved into specific platform code (where it can
    // be made thread safe). In general however, init twice
    // is likely a logic error and we may want to avoid that path anyway. Likely to
    // be done once code stabilizes a bit more.
    if (mInitialized)
    {
        return CHIP_NO_ERROR;
    }

    CHIP_ERROR err = static_cast<ImplClass *>(this)->_InitChipStack();
    mInitialized   = (err == CHIP_NO_ERROR);
    return err;
}

inline CHIP_ERROR PlatformManager::AddEventHandler(EventHandlerFunct handler, intptr_t arg)
{
    return static_cast<ImplClass *>(this)->_AddEventHandler(handler, arg);
}

inline void PlatformManager::RemoveEventHandler(EventHandlerFunct handler, intptr_t arg)
{
    static_cast<ImplClass *>(this)->_RemoveEventHandler(handler, arg);
}

inline void PlatformManager::HandleServerStarted()
{
    static_cast<ImplClass *>(this)->_HandleServerStarted();
}

inline void PlatformManager::HandleServerShuttingDown()
{
    static_cast<ImplClass *>(this)->_HandleServerShuttingDown();
}

inline void PlatformManager::ScheduleWork(AsyncWorkFunct workFunct, intptr_t arg)
{
    static_cast<ImplClass *>(this)->_ScheduleWork(workFunct, arg);
}

inline void PlatformManager::RunEventLoop()
{
    static_cast<ImplClass *>(this)->_RunEventLoop();
}

/**
 * @brief
 *  Starts the stack on its own task with an associated event queue
 *  to dispatch and handle events posted to that task.
 *
 *  This is thread-safe.
 *  This is *NOT SAFE* to call from within the CHIP event loop since it can grab the stack lock.
 */
inline CHIP_ERROR PlatformManager::StartEventLoopTask()
{
    return static_cast<ImplClass *>(this)->_StartEventLoopTask();
}

/**
 * @brief
 *  This will trigger the event loop to exit and block till it has exited the loop.
 *  This prevents the processing of any further events in the queue.
 *
 *  Additionally, this stops the CHIP task if the following criteria are met:
 *      1. One was created earlier through a call to StartEventLoopTask
 *      2. This call isn't being made from that task.
 *
 *  This is safe to call from any task.
 *  This is safe to call from within the CHIP event loop.
 *
 */
inline CHIP_ERROR PlatformManager::StopEventLoopTask()
{
    return static_cast<ImplClass *>(this)->_StopEventLoopTask();
}

/**
 * @brief
 *   Shuts down and cleans up the main objects in the CHIP stack.
 *   This DOES NOT stop the chip thread or event queue from running.
 *
 */
inline void PlatformManager::Shutdown()
{
    static_cast<ImplClass *>(this)->_Shutdown();
    mInitialized = false;
}

inline void PlatformManager::LockChipStack()
{
    static_cast<ImplClass *>(this)->_LockChipStack();
}

inline bool PlatformManager::TryLockChipStack()
{
    return static_cast<ImplClass *>(this)->_TryLockChipStack();
}

inline void PlatformManager::UnlockChipStack()
{
    static_cast<ImplClass *>(this)->_UnlockChipStack();
}

inline CHIP_ERROR PlatformManager::PostEvent(const ChipDeviceEvent * event)
{
    return static_cast<ImplClass *>(this)->_PostEvent(event);
}

inline void PlatformManager::PostEventOrDie(const ChipDeviceEvent * event)
{
    CHIP_ERROR status = static_cast<ImplClass *>(this)->_PostEvent(event);
    VerifyOrDieWithMsg(status == CHIP_NO_ERROR, DeviceLayer, "Failed to post event %d: %" CHIP_ERROR_FORMAT,
                       static_cast<int>(event->Type), status.Format());
}

inline void PlatformManager::DispatchEvent(const ChipDeviceEvent * event)
{
    static_cast<ImplClass *>(this)->_DispatchEvent(event);
}

inline CHIP_ERROR PlatformManager::StartChipTimer(System::Clock::Timeout duration)
{
    return static_cast<ImplClass *>(this)->_StartChipTimer(duration);
}

} // namespace DeviceLayer
} // namespace chip
