/*
 * Copyright 2022 Google LLC.
 *
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 */

#ifndef skgpu_VulkanMemoryAllocator_DEFINED
#define skgpu_VulkanMemoryAllocator_DEFINED

#include "include/core/SkRefCnt.h"
#include "include/gpu/vk/VulkanTypes.h"
#include "include/private/gpu/vk/SkiaVulkan.h"

#include <cstdint>
#include <utility>

namespace skgpu {

class VulkanMemoryAllocator : public SkRefCnt {
public:
    enum AllocationPropertyFlags {
        kNone_AllocationPropertyFlag                = 0b0000,
        // Allocation will be placed in its own VkDeviceMemory and not suballocated from some larger
        // block.
        kDedicatedAllocation_AllocationPropertyFlag = 0b0001,
        // Says that the backing memory can only be accessed by the device. Additionally the device
        // may lazily allocate the memory. This cannot be used with buffers that will be host
        // visible. Setting this flag does not guarantee that we will allocate memory that respects
        // it, but we will try to prefer memory that can respect it.
        kLazyAllocation_AllocationPropertyFlag      = 0b0010,
        // The allocation will be mapped immediately and stay mapped until it is destroyed. This
        // flag is only valid for buffers which are host visible (i.e. must have a usage other than
        // BufferUsage::kGpuOnly).
        kPersistentlyMapped_AllocationPropertyFlag  = 0b0100,
        // Allocation can only be accessed by the device using a protected context.
        kProtected_AllocationPropertyFlag           = 0b1000,
    };

    enum class BufferUsage {
        // Buffers that will only be accessed from the device (large const buffers) will always be
        // in device local memory.
        kGpuOnly,
        // Buffers that typically will be updated multiple times by the host and read on the gpu
        // (e.g. uniform or vertex buffers). CPU writes will generally be sequential in the buffer
        // and will try to take advantage of the write-combined nature of the gpu buffers. Thus this
        // will always be mappable and coherent memory, and it will prefer to be in device local
        // memory.
        kCpuWritesGpuReads,
        // Buffers that will be accessed on the host and copied to another GPU resource (transfer
        // buffers). Will always be mappable and coherent memory.
        kTransfersFromCpuToGpu,
        // Buffers which are typically writted to by the GPU and then read on the host. Will always
        // be mappable memory, and will prefer cached memory.
        kTransfersFromGpuToCpu,
    };

    virtual VkResult allocateImageMemory(VkImage image,
                                         uint32_t allocationPropertyFlags,
                                         skgpu::VulkanBackendMemory* memory) = 0;

    virtual VkResult allocateBufferMemory(VkBuffer buffer,
                                          BufferUsage usage,
                                          uint32_t allocationPropertyFlags,
                                          skgpu::VulkanBackendMemory* memory) = 0;

    // Fills out the passed in skgpu::VulkanAlloc struct for the passed in
    // skgpu::VulkanBackendMemory.
    virtual void getAllocInfo(const skgpu::VulkanBackendMemory&, skgpu::VulkanAlloc*) const = 0;

    // Maps the entire allocation and returns a pointer to the start of the allocation. The
    // implementation may map more memory than just the allocation, but the returned pointer must
    // point at the start of the memory for the requested allocation.
    virtual void* mapMemory(const skgpu::VulkanBackendMemory&) { return nullptr; }
    virtual VkResult mapMemory(const skgpu::VulkanBackendMemory& memory, void** data) {
        *data = this->mapMemory(memory);
        // VK_ERROR_INITIALIZATION_FAILED is a bogus result to return from this function, but it is
        // just something to return that is not VK_SUCCESS and can't be interpreted by a caller to
        // mean something specific happened like device lost or oom. This will be removed once we
        // update clients to implement this virtual.
        return *data ? VK_SUCCESS : VK_ERROR_INITIALIZATION_FAILED;
    }
    virtual void unmapMemory(const skgpu::VulkanBackendMemory&) = 0;

    // The following two calls are used for managing non-coherent memory. The offset is relative to
    // the start of the allocation and not the underlying VkDeviceMemory. Additionaly the client
    // must make sure that the offset + size passed in is less that or equal to the allocation size.
    // It is the responsibility of the implementation to make sure all alignment requirements are
    // followed. The client should not have to deal with any sort of alignment issues.
    virtual void flushMappedMemory(const skgpu::VulkanBackendMemory&, VkDeviceSize, VkDeviceSize) {}
    virtual VkResult flushMemory(const skgpu::VulkanBackendMemory& memory,
                                 VkDeviceSize offset,
                                 VkDeviceSize size) {
        this->flushMappedMemory(memory, offset, size);
        return VK_SUCCESS;
    }
    virtual void invalidateMappedMemory(const skgpu::VulkanBackendMemory&,
                                        VkDeviceSize,
                                        VkDeviceSize) {}
    virtual VkResult invalidateMemory(const skgpu::VulkanBackendMemory& memory,
                                      VkDeviceSize offset,
                                      VkDeviceSize size) {
        this->invalidateMappedMemory(memory, offset, size);
        return VK_SUCCESS;
    }

    virtual void freeMemory(const skgpu::VulkanBackendMemory&) = 0;

    // Returns the total amount of memory that is allocated as well as total
    // amount of memory in use by an allocation from this allocator.
    // Return 1st param is total allocated memory, 2nd is total used memory.
    virtual std::pair<uint64_t, uint64_t> totalAllocatedAndUsedMemory() const = 0;
};

} // namespace skgpu

#endif // skgpu_VulkanMemoryAllocator_DEFINED
