// Copyright (c) 2021, NVIDIA CORPORATION. All rights reserved.
//
// NVIDIA CORPORATION and its licensors retain all intellectual property
// and proprietary rights in and to this software, related documentation
// and any modifications thereto.  Any use, reproduction, disclosure or
// distribution of this software and related documentation without an express
// license agreement from NVIDIA CORPORATION is strictly prohibited.
//

#pragma once

#pragma message("omni/graph/io/IDirtyID.h is deprecated. Include omni/graph/core/IDirtyID.h instead.")

#define OMNI_GRAPH_IO_DEPRECATED [[deprecated("Use the counterpart in the omni::graph::core namespace instead.")]]

#include <carb/Interface.h>

#include <stddef.h>
#include <stdint.h>

namespace omni
{
namespace graph
{
namespace io
{
using DirtyIDType OMNI_GRAPH_IO_DEPRECATED = uint64_t;
OMNI_GRAPH_IO_DEPRECATED static constexpr DirtyIDType kInvalidDirtyID = ~DirtyIDType(0);
OMNI_GRAPH_IO_DEPRECATED static constexpr size_t kFunctionSize = sizeof(void (*)());

struct OMNI_GRAPH_IO_DEPRECATED IDirtyID
{
    CARB_PLUGIN_INTERFACE("omni::graph::io::IDirtyID", 1, 0);

    /**
     * @return The next dirty ID, atomically incrementing the counter inside.
     */
    DirtyIDType(CARB_ABI* getNextDirtyID)() = nullptr;
};
// Update this every time a new ABI function is added, to ensure one isn't accidentally added in the middle
static_assert(offsetof(IDirtyID, getNextDirtyID) == 0 * kFunctionSize,
              "New IDirtyID ABI methods must be added at the end");

// DEPRECATED, BundlePrims class caches iDirtyID interface internally
// This must be instantiated in every extension that uses it, similar to Token::iToken.
// The exact location doesn't matter too much, though the PluginInterface.cpp is probably the best option.
OMNI_GRAPH_IO_DEPRECATED extern const IDirtyID* iDirtyID;

template <typename PREVIOUS_T>
OMNI_GRAPH_IO_DEPRECATED inline bool checkDirtyIDChanged(PREVIOUS_T& previousID, DirtyIDType newID)
{
    if (newID != previousID)
    {
        previousID = newID;
        return true;
    }
    // Equal, but if they're invalid, still treat them as changed
    return (newID == kInvalidDirtyID);
}

}
}
}
