#define LOG_TAG "NanohubHAL_Test"

#include <cstddef>
#include <cstdint>
#include <functional>
#include <iostream>
#include <iomanip>
#include <map>
#include <memory>
#include <cstddef>
#include <cstdint>
#include <mutex>
#include <vector>

#include <dlfcn.h>
#include <signal.h>
#include <unistd.h>

#include <sys/endian.h>
#include <utils/Log.h>

#include <hardware/hardware.h>
#include <hardware/context_hub.h>
#include <nanohub/nanoapp.h>

inline std::ostream &operator << (std::ostream &os, const hub_app_name_t &appId)
{
    char vendor[6];
    __be64 beAppId = htobe64(appId.id);
    uint32_t seqId = appId.id & NANOAPP_VENDOR_ALL_APPS;

    std::ios::fmtflags f(os.flags());
    memcpy(vendor, (void*)&beAppId, sizeof(vendor) - 1);
    vendor[sizeof(vendor) - 1] = 0;
    if (strlen(vendor) == 5)
        os << vendor << ", " << std::hex << std::setw(6)  << seqId;
    else
        os << "#" << std::hex << appId.id;
    os.flags(f);

    return os;
}

void dumpBuffer(std::ostream &os, const char *pfx, const hub_app_name_t &appId, uint32_t evtId, const void *data, size_t len, int status)
{
    const uint8_t *p = static_cast<const uint8_t *>(data);
    os << pfx << ": [ID=" << appId << "; SZ=" << std::dec << len;
    if (evtId)
        os << "; EVT=" << std::hex << evtId;
    os << "]:" << std::hex;
    for (size_t i = 0; i < len; ++i) {
        os << " "  << std::setfill('0') << std::setw(2) << (unsigned int)p[i];
    }
    if (status) {
        os << "; status=" << status << " [" << std::setfill('0') << std::setw(8) << status << "]";
    }
}

class CHub
{
public:
    class IClient {
    public:
        virtual void onMessage(const hub_message_t &msg) = 0;
        virtual ~IClient(){}
    };
    class Client : IClient {
        CHub *mParent;
        const context_hub_t *mHub;
        std::function<void(const hub_message_t &)> mHandler;

    public:
        explicit Client(const context_hub_t *hub, CHub *parent) {
            mHub = hub;
            mParent = parent;
        }
        ~Client() = default;

        void setHandler(std::function<void(const hub_message_t &)> handler) {
            mHandler = handler;
        }
        void onMessage(const hub_message_t &msg) {
            if ((bool)mHandler == true) {
                mHandler(msg);
            }
        }
        void sendMessage(const hub_message_t &msg) {
            mParent->sendMessage(mHub->hub_id, msg);
        }
        void sendToSystem(uint32_t typ, void *data, uint32_t len) {
            mParent->sendMessage(mHub->hub_id, mHub->os_app_name, typ, data, len);
        }
        void sendToApp(hub_app_name_t app, void *data, uint32_t len) {
            mParent->sendMessage(mHub->hub_id, app, 0, data, len);
        }
        const hub_app_name_t getSystemApp() const { return mHub->os_app_name; }
    };
private:
    static int contextHubCallback(uint32_t id, const hub_message_t *msg, void *cookie)
    {
        CHub *hub = static_cast<CHub*>(cookie);
        hub->onMessage(id, msg);
        return 0;
    }

    CHub() {
        hw_get_module(CONTEXT_HUB_MODULE_ID, (const hw_module_t **)&mMod);
        if (!mMod)
            return;
        mMod->subscribe_messages(0, contextHubCallback, this);
        mHubArraySize = mMod->get_hubs(mMod, &mHubArray);
        for (size_t i = 0; i < mHubArraySize; ++i) {
            auto item = &mHubArray[i];
            mHubs[item->hub_id] = std::unique_ptr<Client>(new Client(item, this));
        }
    }

    ~CHub() {
        // destroy all clients first
        mHubs.clear();
        if (mMod != nullptr) {
            // unregister from HAL services
            mMod->subscribe_messages(0, nullptr, nullptr);
            // there is no hw_put_module(); release HAL fd directly
            dlclose(mMod->common.dso);
            mMod = nullptr;
        }
    }

    void onMessage(uint32_t hubId, const hub_message_t *msg) {
        Client *cli = getClientById(hubId);
        if (cli != nullptr && msg != nullptr) {
            cli->onMessage(*msg);
        }
    }

    int sendMessage(uint32_t id, const hub_message_t &msg) {
        return  (mMod != nullptr) ? mMod->send_message(id, &msg) : 0;
    }

    int sendMessage(uint32_t id, hub_app_name_t app, uint32_t typ, void *data, uint32_t len) {
        hub_message_t msg = {
            .app_name = app,
            .message_type = typ,
            .message = data,
            .message_len = len,
        };
        return sendMessage(id, msg);
    }

    Client *getClientById(size_t id) { return mHubs.count(id) ? mHubs[id].get() : nullptr; }

    context_hub_module_t *mMod = nullptr;
    const context_hub_t  *mHubArray = nullptr;
    size_t                mHubArraySize = 0;
    std::map <size_t, std::unique_ptr<Client> > mHubs;

public:
    static CHub *instantiate() {
        static CHub instance;

        return &instance;
    }
    Client *getClientByIndex(size_t idx) {
        return idx < mHubArraySize && mHubArray != nullptr ?
               getClientById(mHubArray[idx].hub_id) : nullptr;
    }
};

class NanoClient
{
    CHub::Client *mClient;
    std::ostream &log;
    std::mutex lock;
    void onMessage(const hub_message_t &msg){
        std::lock_guard<std::mutex> _l(lock);
        dumpBuffer(log, "Rx", msg.app_name, msg.message_type, msg.message, msg.message_len, 0);
        log << std::endl;
    }
public:
    NanoClient(int idx = 0) : log(std::clog) {
        CHub *hub = CHub::instantiate();
        mClient = hub->getClientByIndex(idx);
        if (mClient)
            mClient->setHandler(std::function<void(const hub_message_t&)>([this] (const hub_message_t&msg) { onMessage(msg); }));
    }
    void sendMessage(const hub_message_t &msg) { mClient->sendMessage(msg); }
    void sendMessageToSystem(uint32_t cmd, void * data, size_t dataSize) {
        hub_message_t msg;
        msg.message = data;
        msg.message_len = dataSize;
        msg.message_type = cmd;
        msg.app_name = mClient->getSystemApp();
        {
            std::lock_guard<std::mutex> _l(lock);
            dumpBuffer(log, "TxCmd", msg.app_name, msg.message_type, msg.message, msg.message_len, 0);
            log << std::endl;
        }
        sendMessage(msg);
    }
    void sendMessageToApp(const hub_app_name_t appName, void * data, size_t dataSize, uint32_t msg_type) {
        hub_message_t msg;
        msg.message = data;
        msg.message_len = dataSize;
        msg.message_type = msg_type;
        msg.app_name = appName;
        {
            std::lock_guard<std::mutex> _l(lock);
            dumpBuffer(log, "TxMsg", msg.app_name, msg.message_type, msg.message, msg.message_len, 0);
            log << std::endl;
        }
        sendMessage(msg);
    }
};

void sigint_handler(int)
{
    exit(0);
}

int main(int argc, char *argv[])
{
    int opt;
    long cmd = 0;
    unsigned long msg = 0;
    uint64_t appId = 0;
    const char *appFileName = NULL;
    uint32_t fileSize = 0;

    while((opt = getopt(argc, argv, "c:i:a:m:")) != -1) {
        char *end = NULL;
        switch(opt) {
        case 'm':
            msg = strtoul(optarg, &end, 16);
            break;
        case 'c':
            cmd = strtol(optarg, &end, 10);
            break;
        case 'i':
            appId = strtoull(optarg, &end, 16);
            break;
        case 'a':
            appFileName = optarg;
            break;
        }
        if (end && *end != '\0') {
            std::clog << "Invalid argument: " << optarg << std::endl;
            return 1;
        }
    }

    NanoClient cli;

    std::vector<uint8_t> data;
    for (int i = optind; i < argc; ++i) {
        char *end;
        unsigned long v = strtoul(argv[i], &end, 16);
        // ignore any garbage after parsed hex value;
        // ignore the fact it may not fit 1 byte;
        // we're not testing user's ability to pass valid data,
        // we're testing the system ability to transfer data.
        data.push_back(v);
    }
    if (msg != 0) {
        // send APP message
        const hub_app_name_t app_name = { .id = appId };
        cli.sendMessageToApp(app_name, data.data(), data.size(), msg);
    } else {
        // send HAL command
        switch(cmd) {
        case CONTEXT_HUB_APPS_ENABLE:
        {
            apps_enable_request_t req;
            req.app_name.id = appId;
            cli.sendMessageToSystem(CONTEXT_HUB_APPS_ENABLE, &req, sizeof(req));
        }
        break;
        case CONTEXT_HUB_APPS_DISABLE:
        {
            apps_disable_request_t req;
            req.app_name.id = appId;
            cli.sendMessageToSystem(CONTEXT_HUB_APPS_DISABLE, &req, sizeof(req));
        }
        break;
        case CONTEXT_HUB_LOAD_APP:
        {
            load_app_request_t *req = NULL;
            if (appFileName)
                req = (load_app_request_t *)loadFile(appFileName, &fileSize);
            if (!req || fileSize < sizeof(*req) || req->app_binary.magic != NANOAPP_MAGIC) {
                std::clog << "Invalid nanoapp image: " <<
                             (appFileName != nullptr ? appFileName : "<NULL>") << std::endl;
                return 1;
            }
            cli.sendMessageToSystem(CONTEXT_HUB_LOAD_APP, req, fileSize);
            free(req);
        }
        break;
        case CONTEXT_HUB_UNLOAD_APP:
        {
            unload_app_request_t req;
            req.app_name.id = appId;
            cli.sendMessageToSystem(CONTEXT_HUB_UNLOAD_APP, &req, sizeof(req));
        }
        break;
        case CONTEXT_HUB_QUERY_APPS:
        {
            query_apps_request_t req;
            req.app_name.id = appId;
            cli.sendMessageToSystem(CONTEXT_HUB_QUERY_APPS, &req, sizeof(req));
        }
        break;
        case CONTEXT_HUB_QUERY_MEMORY:
        default:
            std::clog << "Unknown command: " << cmd << std::endl;
            break;
        }
    }

    signal(SIGINT, sigint_handler);
    while(1) {
        sleep(1);
    }
    return 0;
}
