// Copyright 2017 The Dawn & Tint Authors
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are met:
//
// 1. Redistributions of source code must retain the above copyright notice, this
//    list of conditions and the following disclaimer.
//
// 2. Redistributions in binary form must reproduce the above copyright notice,
//    this list of conditions and the following disclaimer in the documentation
//    and/or other materials provided with the distribution.
//
// 3. Neither the name of the copyright holder nor the names of its
//    contributors may be used to endorse or promote products derived from
//    this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
// OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

#include "dawn/native/vulkan/FencedDeleter.h"

#include "dawn/native/Queue.h"
#include "dawn/native/vulkan/DeviceVk.h"

namespace dawn::native::vulkan {

FencedDeleter::FencedDeleter(Device* device) : mDevice(device) {}

FencedDeleter::~FencedDeleter() {
    DAWN_ASSERT(mBuffersToDelete.Empty());
    DAWN_ASSERT(mDescriptorPoolsToDelete.Empty());
    DAWN_ASSERT(mFencesToDelete.Empty());
    DAWN_ASSERT(mFramebuffersToDelete.Empty());
    DAWN_ASSERT(mImagesToDelete.Empty());
    DAWN_ASSERT(mImageViewsToDelete.Empty());
    DAWN_ASSERT(mMemoriesToDelete.Empty());
    DAWN_ASSERT(mPipelinesToDelete.Empty());
    DAWN_ASSERT(mPipelineLayoutsToDelete.Empty());
    DAWN_ASSERT(mQueryPoolsToDelete.Empty());
    DAWN_ASSERT(mRenderPassesToDelete.Empty());
    DAWN_ASSERT(mSamplerYcbcrConversionsToDelete.Empty());
    DAWN_ASSERT(mSamplersToDelete.Empty());
    DAWN_ASSERT(mSemaphoresToDelete.Empty());
    DAWN_ASSERT(mShaderModulesToDelete.Empty());
    DAWN_ASSERT(mSurfacesToDelete.Empty());
    DAWN_ASSERT(mSwapChainsToDelete.Empty());
}

void FencedDeleter::DeleteWhenUnused(VkBuffer buffer) {
    mBuffersToDelete.Enqueue(buffer, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkDescriptorPool pool) {
    mDescriptorPoolsToDelete.Enqueue(pool, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkDeviceMemory memory) {
    mMemoriesToDelete.Enqueue(memory, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkFence fence) {
    mFencesToDelete.Enqueue(fence, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkFramebuffer framebuffer) {
    mFramebuffersToDelete.Enqueue(framebuffer, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkImage image) {
    mImagesToDelete.Enqueue(image, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkImageView view) {
    mImageViewsToDelete.Enqueue(view, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkPipeline pipeline) {
    mPipelinesToDelete.Enqueue(pipeline, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkPipelineLayout layout) {
    mPipelineLayoutsToDelete.Enqueue(layout, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkQueryPool querypool) {
    mQueryPoolsToDelete.Enqueue(querypool, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkRenderPass renderPass) {
    mRenderPassesToDelete.Enqueue(renderPass, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkSamplerYcbcrConversion samplerYcbcrConversion) {
    mSamplerYcbcrConversionsToDelete.Enqueue(samplerYcbcrConversion,
                                             mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkSampler sampler) {
    mSamplersToDelete.Enqueue(sampler, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkSemaphore semaphore) {
    mSemaphoresToDelete.Enqueue(semaphore, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkShaderModule module) {
    mShaderModulesToDelete.Enqueue(module, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkSurfaceKHR surface) {
    mSurfacesToDelete.Enqueue(surface, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::DeleteWhenUnused(VkSwapchainKHR swapChain) {
    mSwapChainsToDelete.Enqueue(swapChain, mDevice->GetQueue()->GetPendingCommandSerial());
}

void FencedDeleter::Tick(ExecutionSerial completedSerial) {
    VkDevice vkDevice = mDevice->GetVkDevice();
    VkInstance instance = mDevice->GetVkInstance();

    // Buffers and images must be deleted before memories because it is invalid to free memory
    // that still have resources bound to it.
    for (VkBuffer buffer : mBuffersToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyBuffer(vkDevice, buffer, nullptr);
    }
    mBuffersToDelete.ClearUpTo(completedSerial);
    for (VkImage image : mImagesToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyImage(vkDevice, image, nullptr);
    }
    mImagesToDelete.ClearUpTo(completedSerial);

    for (VkDeviceMemory memory : mMemoriesToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.FreeMemory(vkDevice, memory, nullptr);
    }
    mMemoriesToDelete.ClearUpTo(completedSerial);

    for (VkPipelineLayout layout : mPipelineLayoutsToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyPipelineLayout(vkDevice, layout, nullptr);
    }
    mPipelineLayoutsToDelete.ClearUpTo(completedSerial);

    for (VkRenderPass renderPass : mRenderPassesToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyRenderPass(vkDevice, renderPass, nullptr);
    }
    mRenderPassesToDelete.ClearUpTo(completedSerial);

    for (VkFence fence : mFencesToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyFence(vkDevice, fence, nullptr);
    }
    mFencesToDelete.ClearUpTo(completedSerial);

    for (VkFramebuffer framebuffer : mFramebuffersToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyFramebuffer(vkDevice, framebuffer, nullptr);
    }
    mFramebuffersToDelete.ClearUpTo(completedSerial);

    for (VkImageView view : mImageViewsToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyImageView(vkDevice, view, nullptr);
    }
    mImageViewsToDelete.ClearUpTo(completedSerial);

    for (VkShaderModule module : mShaderModulesToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyShaderModule(vkDevice, module, nullptr);
    }
    mShaderModulesToDelete.ClearUpTo(completedSerial);

    for (VkPipeline pipeline : mPipelinesToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyPipeline(vkDevice, pipeline, nullptr);
    }
    mPipelinesToDelete.ClearUpTo(completedSerial);

    // Vulkan swapchains must be destroyed before their corresponding VkSurface
    for (VkSwapchainKHR swapChain : mSwapChainsToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroySwapchainKHR(vkDevice, swapChain, nullptr);
    }
    mSwapChainsToDelete.ClearUpTo(completedSerial);
    for (VkSurfaceKHR surface : mSurfacesToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroySurfaceKHR(instance, surface, nullptr);
    }
    mSurfacesToDelete.ClearUpTo(completedSerial);

    for (VkSemaphore semaphore : mSemaphoresToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroySemaphore(vkDevice, semaphore, nullptr);
    }
    mSemaphoresToDelete.ClearUpTo(completedSerial);

    for (VkDescriptorPool pool : mDescriptorPoolsToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyDescriptorPool(vkDevice, pool, nullptr);
    }
    mDescriptorPoolsToDelete.ClearUpTo(completedSerial);

    for (VkQueryPool pool : mQueryPoolsToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroyQueryPool(vkDevice, pool, nullptr);
    }
    mQueryPoolsToDelete.ClearUpTo(completedSerial);

    for (VkSamplerYcbcrConversion samplerYcbcrConversion :
         mSamplerYcbcrConversionsToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroySamplerYcbcrConversion(vkDevice, samplerYcbcrConversion, nullptr);
    }
    mSamplerYcbcrConversionsToDelete.ClearUpTo(completedSerial);

    for (VkSampler sampler : mSamplersToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroySampler(vkDevice, sampler, nullptr);
    }
    mSamplersToDelete.ClearUpTo(completedSerial);
}

}  // namespace dawn::native::vulkan
