/*
 * Copyright © 2020, VideoLAN and dav1d authors
 * All rights reserved.
 *
 * 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.
 *
 * 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 OWNER 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 "dp_renderer.h"

#ifdef HAVE_RENDERER_PLACEBO
#include <assert.h>

#include <libplacebo/renderer.h>
#include <libplacebo/utils/dav1d.h>

#ifdef HAVE_PLACEBO_VULKAN
# include <libplacebo/vulkan.h>
# include <SDL_vulkan.h>
#endif
#ifdef HAVE_PLACEBO_OPENGL
# include <libplacebo/opengl.h>
# include <SDL_opengl.h>
#endif


/**
 * Renderer context for libplacebo
 */
typedef struct renderer_priv_ctx
{
    // SDL window
    SDL_Window *win;
    // Placebo log
    pl_log log;
    // Placebo renderer
    pl_renderer renderer;
#ifdef HAVE_PLACEBO_VULKAN
    // Placebo Vulkan handle
    pl_vulkan vk;
    // Placebo Vulkan instance
    pl_vk_inst vk_inst;
    // Vulkan surface
    VkSurfaceKHR surf;
#endif
#ifdef HAVE_PLACEBO_OPENGL
    // Placebo OpenGL handle
    pl_opengl gl;
#endif
    // Placebo GPU
    pl_gpu gpu;
    // Placebo swapchain
    pl_swapchain swapchain;
    // Lock protecting access to the texture
    SDL_mutex *lock;
    // Image to render, and planes backing them
    struct pl_frame image;
    pl_tex plane_tex[3];
} Dav1dPlayRendererPrivateContext;

static Dav1dPlayRendererPrivateContext*
    placebo_renderer_create_common(int window_flags)
{
    // Create Window
    SDL_Window *sdlwin = dp_create_sdl_window(window_flags | SDL_WINDOW_RESIZABLE);
    if (sdlwin == NULL)
        return NULL;

    // Alloc
    Dav1dPlayRendererPrivateContext *const rd_priv_ctx =
        calloc(1, sizeof(Dav1dPlayRendererPrivateContext));
    if (rd_priv_ctx == NULL)
        return NULL;

    rd_priv_ctx->win = sdlwin;

    // Init libplacebo
    rd_priv_ctx->log = pl_log_create(PL_API_VER, pl_log_params(
        .log_cb     = pl_log_color,
#ifndef NDEBUG
        .log_level  = PL_LOG_DEBUG,
#else
        .log_level  = PL_LOG_WARN,
#endif
    ));
    if (rd_priv_ctx->log == NULL) {
        free(rd_priv_ctx);
        return NULL;
    }

    // Create Mutex
    rd_priv_ctx->lock = SDL_CreateMutex();
    if (rd_priv_ctx->lock == NULL) {
        fprintf(stderr, "SDL_CreateMutex failed: %s\n", SDL_GetError());
        pl_log_destroy(&rd_priv_ctx->log);
        free(rd_priv_ctx);
        return NULL;
    }

    return rd_priv_ctx;
}

#ifdef HAVE_PLACEBO_OPENGL
static void *placebo_renderer_create_gl(void)
{
    SDL_Window *sdlwin = NULL;
    SDL_GL_SetAttribute(SDL_GL_CONTEXT_FLAGS, SDL_GL_CONTEXT_DEBUG_FLAG);

    // Common init
    Dav1dPlayRendererPrivateContext *rd_priv_ctx =
        placebo_renderer_create_common(SDL_WINDOW_OPENGL);

    if (rd_priv_ctx == NULL)
        return NULL;
    sdlwin = rd_priv_ctx->win;

    SDL_GLContext glcontext = SDL_GL_CreateContext(sdlwin);
    SDL_GL_MakeCurrent(sdlwin, glcontext);

    rd_priv_ctx->gl = pl_opengl_create(rd_priv_ctx->log, pl_opengl_params(
#ifndef NDEBUG
        .debug = true,
#endif
    ));
    if (!rd_priv_ctx->gl) {
        fprintf(stderr, "Failed creating opengl device!\n");
        exit(2);
    }

    rd_priv_ctx->swapchain = pl_opengl_create_swapchain(rd_priv_ctx->gl,
        pl_opengl_swapchain_params(
            .swap_buffers = (void (*)(void *)) SDL_GL_SwapWindow,
            .priv = sdlwin,
        ));

    if (!rd_priv_ctx->swapchain) {
        fprintf(stderr, "Failed creating opengl swapchain!\n");
        exit(2);
    }

    int w = WINDOW_WIDTH, h = WINDOW_HEIGHT;
    SDL_GL_GetDrawableSize(sdlwin, &w, &h);

    if (!pl_swapchain_resize(rd_priv_ctx->swapchain, &w, &h)) {
        fprintf(stderr, "Failed resizing vulkan swapchain!\n");
        exit(2);
    }

    rd_priv_ctx->gpu = rd_priv_ctx->gl->gpu;

    if (w != WINDOW_WIDTH || h != WINDOW_HEIGHT)
        printf("Note: window dimensions differ (got %dx%d)\n", w, h);

    return rd_priv_ctx;
}
#endif

#ifdef HAVE_PLACEBO_VULKAN
static void *placebo_renderer_create_vk(void)
{
    SDL_Window *sdlwin = NULL;

    // Common init
    Dav1dPlayRendererPrivateContext *rd_priv_ctx =
        placebo_renderer_create_common(SDL_WINDOW_VULKAN);

    if (rd_priv_ctx == NULL)
        return NULL;
    sdlwin = rd_priv_ctx->win;

    // Init Vulkan
    unsigned num = 0;
    if (!SDL_Vulkan_GetInstanceExtensions(sdlwin, &num, NULL)) {
        fprintf(stderr, "Failed enumerating Vulkan extensions: %s\n", SDL_GetError());
        exit(1);
    }

    const char **extensions = malloc(num * sizeof(const char *));
    assert(extensions);

    SDL_bool ok = SDL_Vulkan_GetInstanceExtensions(sdlwin, &num, extensions);
    if (!ok) {
        fprintf(stderr, "Failed getting Vk instance extensions\n");
        exit(1);
    }

    if (num > 0) {
        printf("Requesting %d additional Vulkan extensions:\n", num);
        for (unsigned i = 0; i < num; i++)
            printf("    %s\n", extensions[i]);
    }

    rd_priv_ctx->vk_inst = pl_vk_inst_create(rd_priv_ctx->log, pl_vk_inst_params(
        .extensions = extensions,
        .num_extensions = num,
    ));
    if (!rd_priv_ctx->vk_inst) {
        fprintf(stderr, "Failed creating Vulkan instance!\n");
        exit(1);
    }
    free(extensions);

    if (!SDL_Vulkan_CreateSurface(sdlwin, rd_priv_ctx->vk_inst->instance, &rd_priv_ctx->surf)) {
        fprintf(stderr, "Failed creating vulkan surface: %s\n", SDL_GetError());
        exit(1);
    }

    rd_priv_ctx->vk = pl_vulkan_create(rd_priv_ctx->log, pl_vulkan_params(
        .instance = rd_priv_ctx->vk_inst->instance,
        .surface = rd_priv_ctx->surf,
        .allow_software = true,
    ));
    if (!rd_priv_ctx->vk) {
        fprintf(stderr, "Failed creating vulkan device!\n");
        exit(2);
    }

    // Create swapchain
    rd_priv_ctx->swapchain = pl_vulkan_create_swapchain(rd_priv_ctx->vk,
        pl_vulkan_swapchain_params(
            .surface = rd_priv_ctx->surf,
            .present_mode = VK_PRESENT_MODE_IMMEDIATE_KHR,
        ));

    if (!rd_priv_ctx->swapchain) {
        fprintf(stderr, "Failed creating vulkan swapchain!\n");
        exit(2);
    }

    int w = WINDOW_WIDTH, h = WINDOW_HEIGHT;
    if (!pl_swapchain_resize(rd_priv_ctx->swapchain, &w, &h)) {
        fprintf(stderr, "Failed resizing vulkan swapchain!\n");
        exit(2);
    }

    rd_priv_ctx->gpu = rd_priv_ctx->vk->gpu;

    if (w != WINDOW_WIDTH || h != WINDOW_HEIGHT)
        printf("Note: window dimensions differ (got %dx%d)\n", w, h);

    return rd_priv_ctx;
}
#endif

static void placebo_renderer_destroy(void *cookie)
{
    Dav1dPlayRendererPrivateContext *rd_priv_ctx = cookie;
    assert(rd_priv_ctx != NULL);

    pl_renderer_destroy(&(rd_priv_ctx->renderer));
    pl_swapchain_destroy(&(rd_priv_ctx->swapchain));
    for (int i = 0; i < 3; i++)
        pl_tex_destroy(rd_priv_ctx->gpu, &(rd_priv_ctx->plane_tex[i]));

#ifdef HAVE_PLACEBO_VULKAN
    if (rd_priv_ctx->vk) {
        pl_vulkan_destroy(&(rd_priv_ctx->vk));
        vkDestroySurfaceKHR(rd_priv_ctx->vk_inst->instance, rd_priv_ctx->surf, NULL);
        pl_vk_inst_destroy(&(rd_priv_ctx->vk_inst));
    }
#endif
#ifdef HAVE_PLACEBO_OPENGL
    if (rd_priv_ctx->gl)
        pl_opengl_destroy(&(rd_priv_ctx->gl));
#endif

    SDL_DestroyWindow(rd_priv_ctx->win);

    pl_log_destroy(&rd_priv_ctx->log);
}

static void placebo_render(void *cookie, const Dav1dPlaySettings *settings)
{
    Dav1dPlayRendererPrivateContext *rd_priv_ctx = cookie;
    assert(rd_priv_ctx != NULL);

    SDL_LockMutex(rd_priv_ctx->lock);
    if (!rd_priv_ctx->image.num_planes) {
        SDL_UnlockMutex(rd_priv_ctx->lock);
        return;
    }

    // Prepare rendering
    if (rd_priv_ctx->renderer == NULL) {
        rd_priv_ctx->renderer = pl_renderer_create(rd_priv_ctx->log, rd_priv_ctx->gpu);
    }

    struct pl_swapchain_frame frame;
    bool ok = pl_swapchain_start_frame(rd_priv_ctx->swapchain, &frame);
    if (!ok) {
        SDL_UnlockMutex(rd_priv_ctx->lock);
        return;
    }

    struct pl_frame target;
    pl_frame_from_swapchain(&target, &frame);
    pl_rect2df_aspect_copy(&target.crop, &rd_priv_ctx->image.crop, 0.0);
    if (pl_frame_is_cropped(&target))
        pl_tex_clear(rd_priv_ctx->gpu, frame.fbo, (float[4]){ 0.0 });

    if (!pl_render_image(rd_priv_ctx->renderer, &rd_priv_ctx->image, &target,
                         settings->highquality ? &pl_render_default_params
                                               : &pl_render_fast_params))
    {
        fprintf(stderr, "Failed rendering frame!\n");
        pl_tex_clear(rd_priv_ctx->gpu, frame.fbo, (float[4]){ 1.0 });
    }

    ok = pl_swapchain_submit_frame(rd_priv_ctx->swapchain);
    if (!ok) {
        fprintf(stderr, "Failed submitting frame!\n");
        SDL_UnlockMutex(rd_priv_ctx->lock);
        return;
    }

    pl_swapchain_swap_buffers(rd_priv_ctx->swapchain);
    SDL_UnlockMutex(rd_priv_ctx->lock);
}

static int placebo_upload_image(void *cookie, Dav1dPicture *dav1d_pic,
                                const Dav1dPlaySettings *settings)
{
    Dav1dPlayRendererPrivateContext *p = cookie;
    assert(p != NULL);
    int ret = 0;

    if (!dav1d_pic)
        return ret;

    SDL_LockMutex(p->lock);
    if (!pl_upload_dav1dpicture(p->gpu, &p->image, p->plane_tex, pl_dav1d_upload_params(
        .picture = dav1d_pic,
        .film_grain = settings->gpugrain,
        .gpu_allocated = settings->zerocopy,
        .asynchronous = true,
    )))
    {
        fprintf(stderr, "Failed uploading planes!\n");
        p->image = (struct pl_frame) {0};
        ret = -1;
    }
    SDL_UnlockMutex(p->lock);
    return ret;
}

static int placebo_alloc_pic(Dav1dPicture *const pic, void *cookie)
{
    Dav1dPlayRendererPrivateContext *rd_priv_ctx = cookie;
    assert(rd_priv_ctx != NULL);

    SDL_LockMutex(rd_priv_ctx->lock);
    int ret = pl_allocate_dav1dpicture(pic, (void *) rd_priv_ctx->gpu);
    SDL_UnlockMutex(rd_priv_ctx->lock);
    return ret;
}

static void placebo_release_pic(Dav1dPicture *pic, void *cookie)
{
    Dav1dPlayRendererPrivateContext *rd_priv_ctx = cookie;
    assert(rd_priv_ctx != NULL);

    SDL_LockMutex(rd_priv_ctx->lock);
    pl_release_dav1dpicture(pic, (void *) rd_priv_ctx->gpu);
    SDL_UnlockMutex(rd_priv_ctx->lock);
}

#ifdef HAVE_PLACEBO_VULKAN
const Dav1dPlayRenderInfo rdr_placebo_vk = {
    .name = "placebo-vk",
    .create_renderer = placebo_renderer_create_vk,
    .destroy_renderer = placebo_renderer_destroy,
    .render = placebo_render,
    .update_frame = placebo_upload_image,
    .alloc_pic = placebo_alloc_pic,
    .release_pic = placebo_release_pic,
    .supports_gpu_grain = 1,
};
#else
const Dav1dPlayRenderInfo rdr_placebo_vk = { NULL };
#endif

#ifdef HAVE_PLACEBO_OPENGL
const Dav1dPlayRenderInfo rdr_placebo_gl = {
    .name = "placebo-gl",
    .create_renderer = placebo_renderer_create_gl,
    .destroy_renderer = placebo_renderer_destroy,
    .render = placebo_render,
    .update_frame = placebo_upload_image,
    .supports_gpu_grain = 1,
};
#else
const Dav1dPlayRenderInfo rdr_placebo_gl = { NULL };
#endif

#else
const Dav1dPlayRenderInfo rdr_placebo_vk = { NULL };
const Dav1dPlayRenderInfo rdr_placebo_gl = { NULL };
#endif
