// Copyright 2017 The Dawn Authors
//
// 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.

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

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

namespace dawn::native::vulkan {

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

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

void FencedDeleter::DeleteWhenUnused(VkSwapchainKHR swapChain) {
    mSwapChainsToDelete.Enqueue(swapChain, mDevice->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 (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 (VkSampler sampler : mSamplersToDelete.IterateUpTo(completedSerial)) {
        mDevice->fn.DestroySampler(vkDevice, sampler, nullptr);
    }
    mSamplersToDelete.ClearUpTo(completedSerial);
}

}  // namespace dawn::native::vulkan
