/*
 * This file is part of FFmpeg.
 *
 * FFmpeg is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * FFmpeg is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with FFmpeg; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
 */

#include "config.h"

#if !defined(_WIN32_WINNT) || _WIN32_WINNT < 0x0A00
#undef _WIN32_WINNT
#define _WIN32_WINNT 0x0A00
#endif

#include <windows.h>

#define COBJMACROS

#include <initguid.h>
#include <d3d11.h>
#include <dxgi1_2.h>
#if HAVE_IDXGIOUTPUT5
#include <dxgi1_5.h>
#endif

#include "libavutil/mem.h"
#include "libavutil/opt.h"
#include "libavutil/time.h"
#include "libavutil/avstring.h"
#include "libavutil/avassert.h"
#include "libavutil/hwcontext.h"
#include "libavutil/hwcontext_d3d11va.h"
#include "compat/w32dlfcn.h"
#include "avfilter.h"
#include "internal.h"
#include "video.h"

#include "vsrc_ddagrab_shaders.h"

// avutil/time.h takes and returns time in microseconds
#define TIMER_RES 1000000
#define TIMER_RES64 INT64_C(1000000)

typedef struct DdagrabContext {
    const AVClass *class;

    AVBufferRef *device_ref;
    AVHWDeviceContext *device_ctx;
    AVD3D11VADeviceContext *device_hwctx;

    AVBufferRef *frames_ref;
    AVHWFramesContext *frames_ctx;
    AVD3D11VAFramesContext *frames_hwctx;

    DXGI_OUTPUT_DESC output_desc;
    IDXGIOutputDuplication *dxgi_outdupl;
    AVFrame *last_frame;

    int mouse_x, mouse_y;
    ID3D11Texture2D *mouse_texture;
    ID3D11ShaderResourceView* mouse_resource_view;
    ID3D11Texture2D *mouse_xor_texture;
    ID3D11ShaderResourceView* mouse_xor_resource_view;

    AVRational time_base;
    int64_t time_frame;
    int64_t time_timeout;
    int64_t first_pts;

    DXGI_FORMAT raw_format;
    int raw_width;
    int raw_height;

    ID3D11Texture2D *probed_texture;
    ID3D11Texture2D *buffer_texture;

    ID3D11VertexShader *vertex_shader;
    ID3D11InputLayout *input_layout;
    ID3D11PixelShader *pixel_shader;
    ID3D11Buffer *const_buffer;
    ID3D11SamplerState *sampler_state;
    ID3D11BlendState *blend_state;
    ID3D11BlendState *blend_state_xor;

    int        output_idx;
    int        draw_mouse;
    AVRational framerate;
    int        width;
    int        height;
    int        offset_x;
    int        offset_y;
    int        out_fmt;
    int        allow_fallback;
    int        force_fmt;
    int        dup_frames;
} DdagrabContext;

#define OFFSET(x) offsetof(DdagrabContext, x)
#define FLAGS AV_OPT_FLAG_VIDEO_PARAM|AV_OPT_FLAG_FILTERING_PARAM
static const AVOption ddagrab_options[] = {
    { "output_idx", "dda output index to capture", OFFSET(output_idx), AV_OPT_TYPE_INT,        { .i64 = 0    },       0, INT_MAX, FLAGS },
    { "draw_mouse", "draw the mouse pointer",      OFFSET(draw_mouse), AV_OPT_TYPE_BOOL,       { .i64 = 1    },       0,       1, FLAGS },
    { "framerate",  "set video frame rate",        OFFSET(framerate),  AV_OPT_TYPE_VIDEO_RATE, { .str = "30" },       0, INT_MAX, FLAGS },
    { "video_size", "set video frame size",        OFFSET(width),      AV_OPT_TYPE_IMAGE_SIZE, { .str = NULL },       0,       0, FLAGS },
    { "offset_x",   "capture area x offset",       OFFSET(offset_x),   AV_OPT_TYPE_INT,        { .i64 = 0    }, INT_MIN, INT_MAX, FLAGS },
    { "offset_y",   "capture area y offset",       OFFSET(offset_y),   AV_OPT_TYPE_INT,        { .i64 = 0    }, INT_MIN, INT_MAX, FLAGS },
    { "output_fmt", "desired output format",       OFFSET(out_fmt),    AV_OPT_TYPE_INT,        { .i64 = DXGI_FORMAT_B8G8R8A8_UNORM },    0, INT_MAX, FLAGS, .unit = "output_fmt" },
    { "auto",       "let dda pick its preferred format", 0,            AV_OPT_TYPE_CONST,      { .i64 = 0 },                             0, INT_MAX, FLAGS, .unit = "output_fmt" },
    { "8bit",       "only output default 8 Bit format",  0,            AV_OPT_TYPE_CONST,      { .i64 = DXGI_FORMAT_B8G8R8A8_UNORM },    0, INT_MAX, FLAGS, .unit = "output_fmt" },
    { "bgra",       "only output 8 Bit BGRA",            0,            AV_OPT_TYPE_CONST,      { .i64 = DXGI_FORMAT_B8G8R8A8_UNORM },    0, INT_MAX, FLAGS, .unit = "output_fmt" },
    { "10bit",      "only output default 10 Bit format", 0,            AV_OPT_TYPE_CONST,      { .i64 = DXGI_FORMAT_R10G10B10A2_UNORM }, 0, INT_MAX, FLAGS, .unit = "output_fmt" },
    { "x2bgr10",    "only output 10 Bit X2BGR10",        0,            AV_OPT_TYPE_CONST,      { .i64 = DXGI_FORMAT_R10G10B10A2_UNORM }, 0, INT_MAX, FLAGS, .unit = "output_fmt" },
    { "16bit",      "only output default 16 Bit format", 0,            AV_OPT_TYPE_CONST,      { .i64 = DXGI_FORMAT_R16G16B16A16_FLOAT },0, INT_MAX, FLAGS, .unit = "output_fmt" },
    { "rgbaf16",    "only output 16 Bit RGBAF16",        0,            AV_OPT_TYPE_CONST,      { .i64 = DXGI_FORMAT_R16G16B16A16_FLOAT },0, INT_MAX, FLAGS, .unit = "output_fmt" },
    { "allow_fallback", "don't error on fallback to default 8 Bit format",
                                                   OFFSET(allow_fallback), AV_OPT_TYPE_BOOL,   { .i64 = 0    },       0,       1, FLAGS },
    { "force_fmt",  "exclude BGRA from format list (experimental, discouraged by Microsoft)",
                                                   OFFSET(force_fmt),  AV_OPT_TYPE_BOOL,       { .i64 = 0    },       0,       1, FLAGS },
    { "dup_frames", "duplicate frames to maintain framerate",
                                                   OFFSET(dup_frames), AV_OPT_TYPE_BOOL,       { .i64 = 1    },       0,       1, FLAGS },
    { NULL }
};

AVFILTER_DEFINE_CLASS(ddagrab);

static inline void release_resource(void *resource)
{
    IUnknown **resp = (IUnknown**)resource;
    if (*resp) {
        IUnknown_Release(*resp);
        *resp = NULL;
    }
}

static av_cold void ddagrab_uninit(AVFilterContext *avctx)
{
    DdagrabContext *dda = avctx->priv;

    release_resource(&dda->blend_state);
    release_resource(&dda->blend_state_xor);
    release_resource(&dda->sampler_state);
    release_resource(&dda->pixel_shader);
    release_resource(&dda->input_layout);
    release_resource(&dda->vertex_shader);
    release_resource(&dda->const_buffer);

    release_resource(&dda->probed_texture);
    release_resource(&dda->buffer_texture);

    release_resource(&dda->dxgi_outdupl);
    release_resource(&dda->mouse_resource_view);
    release_resource(&dda->mouse_texture);
    release_resource(&dda->mouse_xor_resource_view);
    release_resource(&dda->mouse_xor_texture);

    av_frame_free(&dda->last_frame);
    av_buffer_unref(&dda->frames_ref);
    av_buffer_unref(&dda->device_ref);
}

static av_cold int init_dxgi_dda(AVFilterContext *avctx)
{
    DdagrabContext *dda = avctx->priv;
    IDXGIDevice *dxgi_device = NULL;
    IDXGIAdapter *dxgi_adapter = NULL;
    IDXGIOutput *dxgi_output = NULL;
    IDXGIOutput1 *dxgi_output1 = NULL;
#if HAVE_IDXGIOUTPUT5 && HAVE_DPI_AWARENESS_CONTEXT
    IDXGIOutput5 *dxgi_output5 = NULL;

    typedef DPI_AWARENESS_CONTEXT (*set_thread_dpi_t)(DPI_AWARENESS_CONTEXT);
    set_thread_dpi_t set_thread_dpi;
    HMODULE user32_module;
#endif
    int w, h;
    HRESULT hr;

    hr = ID3D11Device_QueryInterface(dda->device_hwctx->device, &IID_IDXGIDevice, (void**)&dxgi_device);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "Failed querying IDXGIDevice\n");
        return AVERROR_EXTERNAL;
    }

    hr = IDXGIDevice_GetParent(dxgi_device, &IID_IDXGIAdapter, (void**)&dxgi_adapter);
    IDXGIDevice_Release(dxgi_device);
    dxgi_device = NULL;
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "Failed getting parent IDXGIAdapter\n");
        return AVERROR_EXTERNAL;
    }

    hr = IDXGIAdapter_EnumOutputs(dxgi_adapter, dda->output_idx, &dxgi_output);
    IDXGIAdapter_Release(dxgi_adapter);
    dxgi_adapter = NULL;
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "Failed to enumerate DXGI output %d\n", dda->output_idx);
        return AVERROR_EXTERNAL;
    }

    hr = IDXGIOutput_GetDesc(dxgi_output, &dda->output_desc);
    if (FAILED(hr)) {
        IDXGIOutput_Release(dxgi_output);
        av_log(avctx, AV_LOG_ERROR, "Failed getting output description\n");
        return AVERROR_EXTERNAL;
    }

#if HAVE_IDXGIOUTPUT5 && HAVE_DPI_AWARENESS_CONTEXT
    user32_module = dlopen("user32.dll", 0);
    if (!user32_module) {
        av_log(avctx, AV_LOG_ERROR, "Failed loading user32.dll\n");
        return AVERROR_EXTERNAL;
    }

    set_thread_dpi = (set_thread_dpi_t)dlsym(user32_module, "SetThreadDpiAwarenessContext");

    if (set_thread_dpi)
        hr = IDXGIOutput_QueryInterface(dxgi_output, &IID_IDXGIOutput5, (void**)&dxgi_output5);

    if (set_thread_dpi && SUCCEEDED(hr)) {
        DPI_AWARENESS_CONTEXT prev_dpi_ctx;
        DXGI_FORMAT formats[] = {
            DXGI_FORMAT_R16G16B16A16_FLOAT,
            DXGI_FORMAT_R10G10B10A2_UNORM,
            DXGI_FORMAT_B8G8R8A8_UNORM
        };
        int nb_formats = FF_ARRAY_ELEMS(formats);

        if(dda->out_fmt == DXGI_FORMAT_B8G8R8A8_UNORM) {
            formats[0] = DXGI_FORMAT_B8G8R8A8_UNORM;
            nb_formats = 1;
        } else if (dda->out_fmt) {
            formats[0] = dda->out_fmt;
            formats[1] = DXGI_FORMAT_B8G8R8A8_UNORM;
            nb_formats = dda->force_fmt ? 1 : 2;
        }

        IDXGIOutput_Release(dxgi_output);
        dxgi_output = NULL;

        prev_dpi_ctx = set_thread_dpi(DPI_AWARENESS_CONTEXT_PER_MONITOR_AWARE_V2);
        if (!prev_dpi_ctx)
            av_log(avctx, AV_LOG_WARNING, "Failed enabling DPI awareness for DDA\n");

        hr = IDXGIOutput5_DuplicateOutput1(dxgi_output5,
            (IUnknown*)dda->device_hwctx->device,
            0,
            nb_formats,
            formats,
            &dda->dxgi_outdupl);
        IDXGIOutput5_Release(dxgi_output5);
        dxgi_output5 = NULL;

        if (prev_dpi_ctx)
            set_thread_dpi(prev_dpi_ctx);

        dlclose(user32_module);
        user32_module = NULL;
        set_thread_dpi = NULL;

        av_log(avctx, AV_LOG_DEBUG, "Using IDXGIOutput5 interface\n");
    } else {
        dlclose(user32_module);
        user32_module = NULL;
        set_thread_dpi = NULL;

        av_log(avctx, AV_LOG_DEBUG, "Falling back to IDXGIOutput1\n");
#else
    {
#endif
        if (dda->out_fmt && dda->out_fmt != DXGI_FORMAT_B8G8R8A8_UNORM && (!dda->allow_fallback || dda->force_fmt)) {
            av_log(avctx, AV_LOG_ERROR, "Only 8 bit output supported with legacy API\n");
            return AVERROR(ENOTSUP);
        }

        hr = IDXGIOutput_QueryInterface(dxgi_output, &IID_IDXGIOutput1, (void**)&dxgi_output1);
        IDXGIOutput_Release(dxgi_output);
        dxgi_output = NULL;
        if (FAILED(hr)) {
            av_log(avctx, AV_LOG_ERROR, "Failed querying IDXGIOutput1\n");
            return AVERROR_EXTERNAL;
        }

        hr = IDXGIOutput1_DuplicateOutput(dxgi_output1,
            (IUnknown*)dda->device_hwctx->device,
            &dda->dxgi_outdupl);
        IDXGIOutput1_Release(dxgi_output1);
        dxgi_output1 = NULL;
    }

    if (hr == DXGI_ERROR_NOT_CURRENTLY_AVAILABLE) {
        av_log(avctx, AV_LOG_ERROR, "Too many open duplication sessions\n");
        return AVERROR(EBUSY);
    } else if (hr == DXGI_ERROR_UNSUPPORTED) {
        av_log(avctx, AV_LOG_ERROR, "Selected output not supported\n");
        return AVERROR_EXTERNAL;
    } else if (hr == E_INVALIDARG) {
        av_log(avctx, AV_LOG_ERROR, "Invalid output duplication argument\n");
        return AVERROR(EINVAL);
    } else if (hr == E_ACCESSDENIED) {
        av_log(avctx, AV_LOG_ERROR, "Desktop duplication access denied\n");
        return AVERROR(EPERM);
    } else if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "Failed duplicating output\n");
        return AVERROR_EXTERNAL;
    }

    w = dda->output_desc.DesktopCoordinates.right - dda->output_desc.DesktopCoordinates.left;
    h = dda->output_desc.DesktopCoordinates.bottom - dda->output_desc.DesktopCoordinates.top;
    av_log(avctx, AV_LOG_VERBOSE, "Opened dxgi output %d with dimensions %dx%d\n", dda->output_idx, w, h);

    return 0;
}

typedef struct ConstBufferData
{
    float width;
    float height;

    uint64_t padding;
} ConstBufferData;

static const D3D11_INPUT_ELEMENT_DESC vertex_shader_input_layout[] =
{
    { "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0,  0, D3D11_INPUT_PER_VERTEX_DATA, 0 },
    { "TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT,    0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 }
};

static av_cold int init_render_resources(AVFilterContext *avctx)
{
    DdagrabContext *dda = avctx->priv;
    ID3D11Device *dev = dda->device_hwctx->device;
    D3D11_SAMPLER_DESC sampler_desc = { 0 };
    D3D11_BLEND_DESC blend_desc = { 0 };
    D3D11_BUFFER_DESC buffer_desc = { 0 };
    D3D11_SUBRESOURCE_DATA buffer_data = { 0 };
    ConstBufferData const_data = { 0 };
    HRESULT hr;

    hr = ID3D11Device_CreateVertexShader(dev,
        vertex_shader_bytes,
        FF_ARRAY_ELEMS(vertex_shader_bytes),
        NULL,
        &dda->vertex_shader);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "CreateVertexShader failed: %lx\n", hr);
        return AVERROR_EXTERNAL;
    }

    hr = ID3D11Device_CreateInputLayout(dev,
        vertex_shader_input_layout,
        FF_ARRAY_ELEMS(vertex_shader_input_layout),
        vertex_shader_bytes,
        FF_ARRAY_ELEMS(vertex_shader_bytes),
        &dda->input_layout);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "CreateInputLayout failed: %lx\n", hr);
        return AVERROR_EXTERNAL;
    }

    hr = ID3D11Device_CreatePixelShader(dev,
        pixel_shader_bytes,
        FF_ARRAY_ELEMS(pixel_shader_bytes),
        NULL,
        &dda->pixel_shader);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "CreatePixelShader failed: %lx\n", hr);
        return AVERROR_EXTERNAL;
    }

    const_data = (ConstBufferData){ dda->width, dda->height };

    buffer_data.pSysMem = &const_data;
    buffer_desc.ByteWidth = sizeof(const_data);
    buffer_desc.Usage = D3D11_USAGE_IMMUTABLE;
    buffer_desc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
    hr = ID3D11Device_CreateBuffer(dev,
        &buffer_desc,
        &buffer_data,
        &dda->const_buffer);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "CreateBuffer const buffer failed: %lx\n", hr);
        return AVERROR_EXTERNAL;
    }

    sampler_desc.Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR;
    sampler_desc.AddressU = D3D11_TEXTURE_ADDRESS_CLAMP;
    sampler_desc.AddressV = D3D11_TEXTURE_ADDRESS_CLAMP;
    sampler_desc.AddressW = D3D11_TEXTURE_ADDRESS_CLAMP;
    sampler_desc.ComparisonFunc = D3D11_COMPARISON_NEVER;
    hr = ID3D11Device_CreateSamplerState(dev,
        &sampler_desc,
        &dda->sampler_state);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "CreateSamplerState failed: %lx\n", hr);
        return AVERROR_EXTERNAL;
    }

    blend_desc.AlphaToCoverageEnable = FALSE;
    blend_desc.IndependentBlendEnable = FALSE;
    blend_desc.RenderTarget[0].BlendEnable = TRUE;
    blend_desc.RenderTarget[0].SrcBlend = D3D11_BLEND_SRC_ALPHA;
    blend_desc.RenderTarget[0].DestBlend = D3D11_BLEND_INV_SRC_ALPHA;
    blend_desc.RenderTarget[0].BlendOp = D3D11_BLEND_OP_ADD;
    blend_desc.RenderTarget[0].SrcBlendAlpha = D3D11_BLEND_ONE;
    blend_desc.RenderTarget[0].DestBlendAlpha = D3D11_BLEND_ZERO;
    blend_desc.RenderTarget[0].BlendOpAlpha = D3D11_BLEND_OP_ADD;
    blend_desc.RenderTarget[0].RenderTargetWriteMask = D3D11_COLOR_WRITE_ENABLE_ALL;
    hr = ID3D11Device_CreateBlendState(dev,
        &blend_desc,
        &dda->blend_state);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "CreateBlendState failed: %lx\n", hr);
        return AVERROR_EXTERNAL;
    }

    blend_desc.RenderTarget[0].SrcBlend = D3D11_BLEND_INV_DEST_COLOR;
    blend_desc.RenderTarget[0].DestBlend = D3D11_BLEND_INV_SRC_COLOR;
    hr = ID3D11Device_CreateBlendState(dev,
        &blend_desc,
        &dda->blend_state_xor);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "CreateBlendState (xor) failed: %lx\n", hr);
        return AVERROR_EXTERNAL;
    }

    return 0;
}

static av_cold int ddagrab_init(AVFilterContext *avctx)
{
    DdagrabContext *dda = avctx->priv;

    dda->last_frame = av_frame_alloc();
    if (!dda->last_frame)
        return AVERROR(ENOMEM);

    dda->mouse_x = -1;
    dda->mouse_y = -1;

    return 0;
}

static int create_d3d11_pointer_tex(AVFilterContext *avctx,
                                    uint8_t *buf,
                                    DXGI_OUTDUPL_POINTER_SHAPE_INFO *shape_info,
                                    ID3D11Texture2D **out_tex,
                                    ID3D11ShaderResourceView **res_view)
{
    DdagrabContext *dda = avctx->priv;
    D3D11_TEXTURE2D_DESC desc = { 0 };
    D3D11_SUBRESOURCE_DATA init_data = { 0 };
    D3D11_SHADER_RESOURCE_VIEW_DESC resource_desc = { 0 };
    HRESULT hr;

    desc.MipLevels = 1;
    desc.ArraySize = 1;
    desc.Format = DXGI_FORMAT_B8G8R8A8_UNORM;
    desc.SampleDesc.Count = 1;
    desc.SampleDesc.Quality = 0;
    desc.Usage = D3D11_USAGE_IMMUTABLE;
    desc.BindFlags = D3D11_BIND_SHADER_RESOURCE;

    desc.Width = shape_info->Width;
    desc.Height = shape_info->Height;

    init_data.pSysMem = buf;
    init_data.SysMemPitch = shape_info->Pitch;

    resource_desc.Format = desc.Format;
    resource_desc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D;
    resource_desc.Texture2D.MostDetailedMip = 0;
    resource_desc.Texture2D.MipLevels = 1;

    hr = ID3D11Device_CreateTexture2D(dda->device_hwctx->device,
        &desc,
        &init_data,
        out_tex);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "Failed creating pointer texture\n");
        return AVERROR_EXTERNAL;
    }

    hr = ID3D11Device_CreateShaderResourceView(dda->device_hwctx->device,
        (ID3D11Resource*)*out_tex,
        &resource_desc,
        res_view);
    if (FAILED(hr)) {
        release_resource(out_tex);
        av_log(avctx, AV_LOG_ERROR, "CreateShaderResourceView for mouse failed: %lx\n", hr);
        return AVERROR_EXTERNAL;
    }

    return 0;
}

static int convert_mono_buffer(uint8_t *input, uint8_t **rgba_out, uint8_t **xor_out, int *_width, int *_height, int *_pitch)
{
    int width = *_width, height = *_height, pitch = *_pitch;
    int real_height = height / 2;
    int size = real_height * pitch;

    uint8_t *output = av_malloc(real_height * width * 4);
    uint8_t *output_xor = av_malloc(real_height * width * 4);

    int y, x;

    if (!output || !output_xor) {
        av_free(output);
        av_free(output_xor);
        return AVERROR(ENOMEM);
    }

    for (y = 0; y < real_height; y++) {
        for (x = 0; x < width; x++) {
            int in_pos = (y * pitch) + (x / 8);
            int out_pos = 4 * ((y * width) + x);
            int and_val = (input[in_pos] >> (7 - (x % 8))) & 1;
            int xor_val = (input[in_pos + size] >> (7 - (x % 8))) & 1;

            if (!and_val && !xor_val) {
                // solid black
                memset(&output[out_pos], 0, 4);
                output[out_pos + 3] = 0xFF;

                // transparent
                memset(&output_xor[out_pos], 0, 4);
            } else if (and_val && !xor_val) {
                // transparent
                memset(&output[out_pos], 0, 4);

                // transparent
                memset(&output_xor[out_pos], 0, 4);
            } else if (!and_val && xor_val) {
                // solid white
                memset(&output[out_pos], 0xFF, 4);

                // transparent
                memset(&output_xor[out_pos], 0, 4);
            } else if (and_val && xor_val) {
                // transparent
                memset(&output[out_pos], 0, 4);

                // solid white -> invert color
                memset(&output_xor[out_pos], 0xFF, 4);
            }
        }
    }

    *_pitch = width * 4;
    *_height = real_height;
    *rgba_out = output;
    *xor_out = output_xor;

    return 0;
}

static int fixup_color_mask(uint8_t *input, uint8_t **rgba_out, uint8_t **xor_out, int width, int height, int pitch)
{
    int size = height * pitch;
    uint8_t *output = av_malloc(size);
    uint8_t *output_xor = av_malloc(size);
    int x, y;

    if (!output || !output_xor) {
        av_free(output);
        av_free(output_xor);
        return AVERROR(ENOMEM);
    }

    memcpy(output, input, size);
    memcpy(output_xor, input, size);

    for (y = 0; y < height; y++) {
        for (x = 0; x < width; x++) {
            int pos = (y*pitch) + (4*x) + 3;
            output[pos] = input[pos] ? 0 : 0xFF;
            output_xor[pos] = input[pos] ? 0xFF : 0;
        }
    }

    *rgba_out = output;
    *xor_out = output_xor;

    return 0;
}

static int update_mouse_pointer(AVFilterContext *avctx, DXGI_OUTDUPL_FRAME_INFO *frame_info)
{
    DdagrabContext *dda = avctx->priv;
    HRESULT hr;
    int ret, ret2;

    if (frame_info->LastMouseUpdateTime.QuadPart == 0)
        return 0;

    if (frame_info->PointerPosition.Visible) {
        switch (dda->output_desc.Rotation) {
        case DXGI_MODE_ROTATION_ROTATE90:
            dda->mouse_x = frame_info->PointerPosition.Position.y;
            dda->mouse_y = dda->output_desc.DesktopCoordinates.right - dda->output_desc.DesktopCoordinates.left - frame_info->PointerPosition.Position.x - 1;
            break;
        case DXGI_MODE_ROTATION_ROTATE180:
            dda->mouse_x = dda->output_desc.DesktopCoordinates.right - dda->output_desc.DesktopCoordinates.left - frame_info->PointerPosition.Position.x - 1;
            dda->mouse_y = dda->output_desc.DesktopCoordinates.bottom - dda->output_desc.DesktopCoordinates.top - frame_info->PointerPosition.Position.y - 1;
            break;
        case DXGI_MODE_ROTATION_ROTATE270:
            dda->mouse_x = dda->output_desc.DesktopCoordinates.bottom - dda->output_desc.DesktopCoordinates.top - frame_info->PointerPosition.Position.y - 1;
            dda->mouse_y = frame_info->PointerPosition.Position.x;
            break;
        default:
            dda->mouse_x = frame_info->PointerPosition.Position.x;
            dda->mouse_y = frame_info->PointerPosition.Position.y;
        }
    } else {
        dda->mouse_x = dda->mouse_y = -1;
    }

    if (frame_info->PointerShapeBufferSize) {
        UINT size = frame_info->PointerShapeBufferSize;
        DXGI_OUTDUPL_POINTER_SHAPE_INFO shape_info;
        uint8_t *rgba_buf = NULL, *rgb_xor_buf = NULL;
        uint8_t *buf = av_malloc(size);
        if (!buf)
            return AVERROR(ENOMEM);

        hr = IDXGIOutputDuplication_GetFramePointerShape(dda->dxgi_outdupl,
            size,
            buf,
            &size,
            &shape_info);
        if (FAILED(hr)) {
            av_free(buf);
            av_log(avctx, AV_LOG_ERROR, "Failed getting pointer shape: %lx\n", hr);
            return AVERROR_EXTERNAL;
        }

        if (shape_info.Type == DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MONOCHROME) {
            ret = convert_mono_buffer(buf, &rgba_buf, &rgb_xor_buf, &shape_info.Width, &shape_info.Height, &shape_info.Pitch);
            av_freep(&buf);
            if (ret < 0)
                return ret;
        } else if (shape_info.Type == DXGI_OUTDUPL_POINTER_SHAPE_TYPE_MASKED_COLOR) {
            ret = fixup_color_mask(buf, &rgba_buf, &rgb_xor_buf, shape_info.Width, shape_info.Height, shape_info.Pitch);
            av_freep(&buf);
            if (ret < 0)
                return ret;
        } else if (shape_info.Type == DXGI_OUTDUPL_POINTER_SHAPE_TYPE_COLOR) {
            rgba_buf = buf;
            buf = NULL;
        } else {
            av_log(avctx, AV_LOG_WARNING, "Unsupported pointer shape type: %d\n", (int)shape_info.Type);
            av_freep(&buf);
            return 0;
        }

        release_resource(&dda->mouse_resource_view);
        release_resource(&dda->mouse_texture);
        release_resource(&dda->mouse_xor_resource_view);
        release_resource(&dda->mouse_xor_texture);

        ret = create_d3d11_pointer_tex(avctx, rgba_buf, &shape_info, &dda->mouse_texture, &dda->mouse_resource_view);
        ret2 = rgb_xor_buf ? create_d3d11_pointer_tex(avctx, rgb_xor_buf, &shape_info, &dda->mouse_xor_texture, &dda->mouse_xor_resource_view) : 0;
        av_freep(&rgba_buf);
        av_freep(&rgb_xor_buf);
        if (ret < 0)
            return ret;
        if (ret2 < 0)
            return ret2;

        av_log(avctx, AV_LOG_VERBOSE, "Updated pointer shape texture\n");
    }

    return 0;
}

static int next_frame_internal(AVFilterContext *avctx, ID3D11Texture2D **desktop_texture, int need_frame)
{
    DXGI_OUTDUPL_FRAME_INFO frame_info;
    DdagrabContext *dda = avctx->priv;
    IDXGIResource *desktop_resource = NULL;
    HRESULT hr;
    int ret;

    hr = IDXGIOutputDuplication_AcquireNextFrame(
        dda->dxgi_outdupl,
        dda->time_timeout,
        &frame_info,
        &desktop_resource);
    if (hr == DXGI_ERROR_WAIT_TIMEOUT) {
        return AVERROR(EAGAIN);
    } else if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "AcquireNextFrame failed: %lx\n", hr);
        return AVERROR_EXTERNAL;
    }

    if (dda->draw_mouse) {
        ret = update_mouse_pointer(avctx, &frame_info);
        if (ret < 0)
            goto error;
    }

    if (!frame_info.LastPresentTime.QuadPart || !frame_info.AccumulatedFrames) {
        if (need_frame) {
            ret = AVERROR(EAGAIN);
            goto error;
        }

        // Unforunately, we can't rely on the desktop_resource's format in this case.
        // The API might even return it in with a format that was not in the initial
        // list of supported formats, and it can change/flicker randomly.
        // To work around this, return an internal copy of the last valid texture we got.
        release_resource(&desktop_resource);

        // The initial probing should make this impossible.
        if (!dda->buffer_texture) {
            av_log(avctx, AV_LOG_ERROR, "No buffer texture while operating!\n");
            ret = AVERROR_BUG;
            goto error;
        }

        av_log(avctx, AV_LOG_TRACE, "Returning internal buffer for a frame!\n");
        ID3D11Texture2D_AddRef(dda->buffer_texture);
        *desktop_texture = dda->buffer_texture;
        return 0;
    }

    hr = IDXGIResource_QueryInterface(desktop_resource, &IID_ID3D11Texture2D, (void**)desktop_texture);
    release_resource(&desktop_resource);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "DXGIResource QueryInterface failed\n");
        ret = AVERROR_EXTERNAL;
        goto error;
    }

    if (!dda->buffer_texture) {
        D3D11_TEXTURE2D_DESC desc;
        ID3D11Texture2D_GetDesc(*desktop_texture, &desc);
        desc.Usage = D3D11_USAGE_DEFAULT;
        desc.BindFlags = 0;
        desc.CPUAccessFlags = 0;
        desc.MiscFlags = 0;

        hr = ID3D11Device_CreateTexture2D(dda->device_hwctx->device, &desc, NULL, &dda->buffer_texture);
        if (FAILED(hr)) {
            release_resource(desktop_texture);
            av_log(avctx, AV_LOG_ERROR, "Failed creating internal buffer texture.\n");
            ret = AVERROR(ENOMEM);
            goto error;
        }
    }

    ID3D11DeviceContext_CopyResource(dda->device_hwctx->device_context,
                                     (ID3D11Resource*)dda->buffer_texture,
                                     (ID3D11Resource*)*desktop_texture);

    return 0;

error:
    release_resource(&desktop_resource);

    hr = IDXGIOutputDuplication_ReleaseFrame(dda->dxgi_outdupl);
    if (FAILED(hr))
        av_log(avctx, AV_LOG_ERROR, "DDA error ReleaseFrame failed!\n");

    return ret;
}

static int probe_output_format(AVFilterContext *avctx)
{
    DdagrabContext *dda = avctx->priv;
    D3D11_TEXTURE2D_DESC desc;
    int ret;

    av_assert1(!dda->probed_texture);

    do {
        ret = next_frame_internal(avctx, &dda->probed_texture, 1);
    } while(ret == AVERROR(EAGAIN));
    if (ret < 0)
        return ret;

    ID3D11Texture2D_GetDesc(dda->probed_texture, &desc);

    dda->raw_format = desc.Format;
    dda->raw_width = desc.Width;
    dda->raw_height = desc.Height;

    if (dda->width <= 0)
        dda->width = dda->raw_width;
    if (dda->height <= 0)
        dda->height = dda->raw_height;

    return 0;
}

static av_cold int init_hwframes_ctx(AVFilterContext *avctx)
{
    DdagrabContext *dda = avctx->priv;
    int ret = 0;

    dda->frames_ref = av_hwframe_ctx_alloc(dda->device_ref);
    if (!dda->frames_ref)
        return AVERROR(ENOMEM);
    dda->frames_ctx = (AVHWFramesContext*)dda->frames_ref->data;
    dda->frames_hwctx = (AVD3D11VAFramesContext*)dda->frames_ctx->hwctx;

    dda->frames_ctx->format    = AV_PIX_FMT_D3D11;
    dda->frames_ctx->width     = dda->width;
    dda->frames_ctx->height    = dda->height;

    switch (dda->raw_format) {
    case DXGI_FORMAT_B8G8R8A8_UNORM:
        av_log(avctx, AV_LOG_VERBOSE, "Probed 8 bit RGB frame format\n");
        dda->frames_ctx->sw_format = AV_PIX_FMT_BGRA;
        break;
    case DXGI_FORMAT_R10G10B10A2_UNORM:
        av_log(avctx, AV_LOG_VERBOSE, "Probed 10 bit RGB frame format\n");
        dda->frames_ctx->sw_format = AV_PIX_FMT_X2BGR10;
        break;
    case DXGI_FORMAT_R16G16B16A16_FLOAT:
        av_log(avctx, AV_LOG_VERBOSE, "Probed 16 bit float RGB frame format\n");
        dda->frames_ctx->sw_format = AV_PIX_FMT_RGBAF16;
        break;
    default:
        av_log(avctx, AV_LOG_ERROR, "Unexpected texture output format!\n");
        return AVERROR_BUG;
    }

    if (dda->draw_mouse)
        dda->frames_hwctx->BindFlags |= D3D11_BIND_RENDER_TARGET;

    ret = av_hwframe_ctx_init(dda->frames_ref);
    if (ret < 0) {
        av_log(avctx, AV_LOG_ERROR, "Failed to initialise hardware frames context: %d.\n", ret);
        goto fail;
    }

    return 0;
fail:
    av_buffer_unref(&dda->frames_ref);
    return ret;
}

static int ddagrab_config_props(AVFilterLink *outlink)
{
    AVFilterContext *avctx = outlink->src;
    DdagrabContext *dda = avctx->priv;
    int ret;

    if (avctx->hw_device_ctx) {
        dda->device_ctx = (AVHWDeviceContext*)avctx->hw_device_ctx->data;

        if (dda->device_ctx->type != AV_HWDEVICE_TYPE_D3D11VA) {
            av_log(avctx, AV_LOG_ERROR, "Non-D3D11VA input hw_device_ctx\n");
            return AVERROR(EINVAL);
        }

        dda->device_ref = av_buffer_ref(avctx->hw_device_ctx);
        if (!dda->device_ref)
            return AVERROR(ENOMEM);

        av_log(avctx, AV_LOG_VERBOSE, "Using provided hw_device_ctx\n");
    } else {
        ret = av_hwdevice_ctx_create(&dda->device_ref, AV_HWDEVICE_TYPE_D3D11VA, NULL, NULL, 0);
        if (ret < 0) {
            av_log(avctx, AV_LOG_ERROR, "Failed to create D3D11VA device.\n");
            return ret;
        }

        dda->device_ctx = (AVHWDeviceContext*)dda->device_ref->data;

        av_log(avctx, AV_LOG_VERBOSE, "Created internal hw_device_ctx\n");
    }

    dda->device_hwctx = (AVD3D11VADeviceContext*)dda->device_ctx->hwctx;

    ret = init_dxgi_dda(avctx);
    if (ret < 0)
        return ret;

    ret = probe_output_format(avctx);
    if (ret < 0)
        return ret;

    if (dda->out_fmt && dda->raw_format != dda->out_fmt && (!dda->allow_fallback || dda->force_fmt)) {
        av_log(avctx, AV_LOG_ERROR, "Requested output format unavailable.\n");
        return AVERROR(ENOTSUP);
    }

    dda->width -= FFMAX(dda->width - dda->raw_width + dda->offset_x, 0);
    dda->height -= FFMAX(dda->height - dda->raw_height + dda->offset_y, 0);

    dda->time_base  = av_inv_q(dda->framerate);
    dda->time_frame = av_gettime_relative() / av_q2d(dda->time_base);
    dda->time_timeout = av_rescale_q(1, dda->time_base, (AVRational) { 1, 1000 }) / 2;

    if (dda->draw_mouse) {
        ret = init_render_resources(avctx);
        if (ret < 0)
            return ret;
    }

    ret = init_hwframes_ctx(avctx);
    if (ret < 0)
        return ret;

    outlink->hw_frames_ctx = av_buffer_ref(dda->frames_ref);
    if (!outlink->hw_frames_ctx)
        return AVERROR(ENOMEM);

    outlink->w = dda->width;
    outlink->h = dda->height;
    outlink->time_base = (AVRational){1, TIMER_RES};
    outlink->frame_rate = dda->framerate;

    return 0;
}

static int draw_mouse_pointer(AVFilterContext *avctx, AVFrame *frame)
{
    DdagrabContext *dda = avctx->priv;
    ID3D11DeviceContext *devctx = dda->device_hwctx->device_context;
    ID3D11Texture2D *frame_tex = (ID3D11Texture2D*)frame->data[0];
    D3D11_RENDER_TARGET_VIEW_DESC target_desc = { 0 };
    ID3D11RenderTargetView* target_view = NULL;
    ID3D11Buffer *mouse_vertex_buffer = NULL;
    D3D11_TEXTURE2D_DESC tex_desc;
    int num_vertices = 0;
    int x, y;
    HRESULT hr;
    int ret = 0;

    if (!dda->mouse_texture || dda->mouse_x < 0 || dda->mouse_y < 0)
        return 0;

    ID3D11Texture2D_GetDesc(dda->mouse_texture, &tex_desc);

    x = dda->mouse_x - dda->offset_x;
    y = dda->mouse_y - dda->offset_y;

    if (x >= dda->width || y >= dda->height ||
        -x >= (int)tex_desc.Width || -y >= (int)tex_desc.Height)
        return 0;

    target_desc.Format = dda->raw_format;
    target_desc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D;
    target_desc.Texture2D.MipSlice = 0;

    hr = ID3D11Device_CreateRenderTargetView(dda->device_hwctx->device,
        (ID3D11Resource*)frame_tex,
        &target_desc,
        &target_view);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "CreateRenderTargetView failed: %lx\n", hr);
        ret = AVERROR_EXTERNAL;
        goto end;
    }

    ID3D11DeviceContext_ClearState(devctx);

    {
        D3D11_VIEWPORT viewport = { 0 };
        viewport.Width = dda->width;
        viewport.Height = dda->height;
        viewport.MinDepth = 0.0f;
        viewport.MaxDepth = 1.0f;

        ID3D11DeviceContext_RSSetViewports(devctx, 1, &viewport);
    }

    {
        FLOAT vertices[] = {
            // x, y, z,  u, v
            x                 , y + tex_desc.Height, 0.0f,  0.0f, 1.0f,
            x                 , y                  , 0.0f,  0.0f, 0.0f,
            x + tex_desc.Width, y + tex_desc.Height, 0.0f,  1.0f, 1.0f,
            x + tex_desc.Width, y                  , 0.0f,  1.0f, 0.0f,
        };
        UINT stride = sizeof(FLOAT) * 5;
        UINT offset = 0;

        D3D11_SUBRESOURCE_DATA init_data = { 0 };
        D3D11_BUFFER_DESC buf_desc = { 0 };

        switch (dda->output_desc.Rotation) {
        case DXGI_MODE_ROTATION_ROTATE90:
            vertices[ 0] = x;                   vertices[ 1] = y;
            vertices[ 5] = x;                   vertices[ 6] = y - tex_desc.Width;
            vertices[10] = x + tex_desc.Height; vertices[11] = y;
            vertices[15] = x + tex_desc.Height; vertices[16] = y - tex_desc.Width;
            vertices[ 3] = 0.0f; vertices[ 4] = 0.0f;
            vertices[ 8] = 1.0f; vertices[ 9] = 0.0f;
            vertices[13] = 0.0f; vertices[14] = 1.0f;
            vertices[18] = 1.0f; vertices[19] = 1.0f;
            break;
        case DXGI_MODE_ROTATION_ROTATE180:
            vertices[ 0] = x - tex_desc.Width; vertices[ 1] = y;
            vertices[ 5] = x - tex_desc.Width; vertices[ 6] = y - tex_desc.Height;
            vertices[10] = x;                  vertices[11] = y;
            vertices[15] = x;                  vertices[16] = y - tex_desc.Height;
            vertices[ 3] = 1.0f; vertices[ 4] = 0.0f;
            vertices[ 8] = 1.0f; vertices[ 9] = 1.0f;
            vertices[13] = 0.0f; vertices[14] = 0.0f;
            vertices[18] = 0.0f; vertices[19] = 1.0f;
            break;
        case DXGI_MODE_ROTATION_ROTATE270:
            vertices[ 0] = x - tex_desc.Height; vertices[ 1] = y + tex_desc.Width;
            vertices[ 5] = x - tex_desc.Height; vertices[ 6] = y;
            vertices[10] = x;                   vertices[11] = y + tex_desc.Width;
            vertices[15] = x;                   vertices[16] = y;
            vertices[ 3] = 1.0f; vertices[ 4] = 1.0f;
            vertices[ 8] = 0.0f; vertices[ 9] = 1.0f;
            vertices[13] = 1.0f; vertices[14] = 0.0f;
            vertices[18] = 0.0f; vertices[19] = 0.0f;
            break;
        default:
            break;
        }

        num_vertices = sizeof(vertices) / (sizeof(FLOAT) * 5);

        buf_desc.Usage = D3D11_USAGE_DEFAULT;
        buf_desc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
        buf_desc.ByteWidth = sizeof(vertices);
        init_data.pSysMem = vertices;

        hr = ID3D11Device_CreateBuffer(dda->device_hwctx->device,
            &buf_desc,
            &init_data,
            &mouse_vertex_buffer);
        if (FAILED(hr)) {
            av_log(avctx, AV_LOG_ERROR, "CreateBuffer failed: %lx\n", hr);
            ret = AVERROR_EXTERNAL;
            goto end;
        }

        ID3D11DeviceContext_IASetVertexBuffers(devctx, 0, 1, &mouse_vertex_buffer, &stride, &offset);
        ID3D11DeviceContext_IASetInputLayout(devctx, dda->input_layout);
        ID3D11DeviceContext_IASetPrimitiveTopology(devctx, D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP);
    }

    ID3D11DeviceContext_VSSetShader(devctx, dda->vertex_shader, NULL, 0);
    ID3D11DeviceContext_VSSetConstantBuffers(devctx, 0, 1, &dda->const_buffer);
    ID3D11DeviceContext_PSSetSamplers(devctx, 0, 1, &dda->sampler_state);
    ID3D11DeviceContext_PSSetShaderResources(devctx, 0, 1, &dda->mouse_resource_view);
    ID3D11DeviceContext_PSSetShader(devctx, dda->pixel_shader, NULL, 0);

    ID3D11DeviceContext_OMSetBlendState(devctx, dda->blend_state, NULL, 0xFFFFFFFF);
    ID3D11DeviceContext_OMSetRenderTargets(devctx, 1, &target_view, NULL);

    ID3D11DeviceContext_Draw(devctx, num_vertices, 0);

    if (dda->mouse_xor_resource_view) {
        ID3D11DeviceContext_PSSetShaderResources(devctx, 0, 1, &dda->mouse_xor_resource_view);
        ID3D11DeviceContext_OMSetBlendState(devctx, dda->blend_state_xor, NULL, 0xFFFFFFFF);

        ID3D11DeviceContext_Draw(devctx, num_vertices, 0);
    }

end:
    release_resource(&mouse_vertex_buffer);
    release_resource(&target_view);

    return ret;
}

static int ddagrab_request_frame(AVFilterLink *outlink)
{
    AVFilterContext *avctx = outlink->src;
    DdagrabContext *dda = avctx->priv;

    ID3D11Texture2D *cur_texture = NULL;
    D3D11_TEXTURE2D_DESC desc = { 0 };
    D3D11_BOX box = { 0 };

    int64_t time_frame = dda->time_frame;
    int64_t now, delay;
    AVFrame *frame = NULL;
    HRESULT hr;
    int ret;

    /* time_frame is in units of microseconds divided by the time_base.
     * This means that adding a clean 1M to it is the equivalent of adding
     * 1M*time_base microseconds to it, except it avoids all rounding error.
     * The only time rounding error occurs is when multiplying to calculate
     * the delay. So any rounding error there corrects itself over time.
     */
    time_frame += TIMER_RES64;
    for (;;) {
        now = av_gettime_relative();
        delay = time_frame * av_q2d(dda->time_base) - now;
        if (delay <= 0) {
            if (delay < -TIMER_RES64 * av_q2d(dda->time_base)) {
                time_frame += TIMER_RES64;
            }
            break;
        }
        av_usleep(delay);
    }

    if (!dda->first_pts)
        dda->first_pts = now;
    now -= dda->first_pts;

    if (!dda->probed_texture) {
        do {
            ret = next_frame_internal(avctx, &cur_texture, 0);
        } while (ret == AVERROR(EAGAIN) && !dda->dup_frames);
    } else {
        cur_texture = dda->probed_texture;
        dda->probed_texture = NULL;
        ret = 0;
    }

    if (ret == AVERROR(EAGAIN) && dda->last_frame->buf[0]) {
        frame = av_frame_alloc();
        if (!frame)
            return AVERROR(ENOMEM);

        ret = av_frame_ref(frame, dda->last_frame);
        if (ret < 0) {
            av_frame_free(&frame);
            return ret;
        }

        av_log(avctx, AV_LOG_DEBUG, "Duplicated output frame\n");

        goto frame_done;
    } else if (ret == AVERROR(EAGAIN)) {
        av_log(avctx, AV_LOG_VERBOSE, "Initial DDA AcquireNextFrame timeout!\n");
        return AVERROR(EAGAIN);
    } else if (ret < 0) {
        return ret;
    }

    // AcquireNextFrame sometimes has bursts of delay.
    // This increases accuracy of the timestamp, but might upset consumers due to more jittery framerate?
    now = av_gettime_relative() - dda->first_pts;

    ID3D11Texture2D_GetDesc(cur_texture, &desc);
    if (desc.Format != dda->raw_format ||
        (int)desc.Width != dda->raw_width ||
        (int)desc.Height != dda->raw_height) {
        av_log(avctx, AV_LOG_ERROR, "Output parameters changed!\n");
        ret = AVERROR_OUTPUT_CHANGED;
        goto fail;
    }

    frame = ff_get_video_buffer(outlink, dda->width, dda->height);
    if (!frame) {
        ret = AVERROR(ENOMEM);
        goto fail;
    }

    box.left = dda->offset_x;
    box.top = dda->offset_y;
    box.right = box.left + dda->width;
    box.bottom = box.top + dda->height;
    box.front = 0;
    box.back = 1;

    ID3D11DeviceContext_CopySubresourceRegion(
        dda->device_hwctx->device_context,
        (ID3D11Resource*)frame->data[0], (UINT)(intptr_t)frame->data[1],
        0, 0, 0,
        (ID3D11Resource*)cur_texture, 0,
        &box);

    release_resource(&cur_texture);

    hr = IDXGIOutputDuplication_ReleaseFrame(dda->dxgi_outdupl);
    if (FAILED(hr)) {
        av_log(avctx, AV_LOG_ERROR, "DDA ReleaseFrame failed!\n");
        ret = AVERROR_EXTERNAL;
        goto fail;
    }

    if (dda->draw_mouse) {
        ret = draw_mouse_pointer(avctx, frame);
        if (ret < 0)
            goto fail;
    }

    frame->sample_aspect_ratio = (AVRational){1, 1};

    if (desc.Format == DXGI_FORMAT_B8G8R8A8_UNORM ||
        desc.Format == DXGI_FORMAT_R10G10B10A2_UNORM) {
        // According to MSDN, all integer formats contain sRGB image data
        frame->color_range     = AVCOL_RANGE_JPEG;
        frame->color_primaries = AVCOL_PRI_BT709;
        frame->color_trc       = AVCOL_TRC_IEC61966_2_1;
        frame->colorspace      = AVCOL_SPC_RGB;
    } else if(desc.Format == DXGI_FORMAT_R16G16B16A16_FLOAT) {
        // According to MSDN, all floating point formats contain sRGB image data with linear 1.0 gamma.
        frame->color_range     = AVCOL_RANGE_JPEG;
        frame->color_primaries = AVCOL_PRI_BT709;
        frame->color_trc       = AVCOL_TRC_LINEAR;
        frame->colorspace      = AVCOL_SPC_RGB;
    } else {
        ret = AVERROR_BUG;
        goto fail;
    }

    ret = av_frame_replace(dda->last_frame, frame);
    if (ret < 0)
        return ret;

frame_done:
    frame->pts = now;
    dda->time_frame = time_frame;

    return ff_filter_frame(outlink, frame);

fail:
    if (frame)
        av_frame_free(&frame);

    if (cur_texture)
        IDXGIOutputDuplication_ReleaseFrame(dda->dxgi_outdupl);

    release_resource(&cur_texture);
    return ret;
}

static const AVFilterPad ddagrab_outputs[] = {
    {
        .name          = "default",
        .type          = AVMEDIA_TYPE_VIDEO,
        .request_frame = ddagrab_request_frame,
        .config_props  = ddagrab_config_props,
    },
};

const AVFilter ff_vsrc_ddagrab = {
    .name          = "ddagrab",
    .description   = NULL_IF_CONFIG_SMALL("Grab Windows Desktop images using Desktop Duplication API"),
    .priv_size     = sizeof(DdagrabContext),
    .priv_class    = &ddagrab_class,
    .init          = ddagrab_init,
    .uninit        = ddagrab_uninit,
    .inputs        = NULL,
    FILTER_OUTPUTS(ddagrab_outputs),
    FILTER_SINGLE_PIXFMT(AV_PIX_FMT_D3D11),
    .flags_internal = FF_FILTER_FLAG_HWFRAME_AWARE,
    .flags          = AVFILTER_FLAG_HWDEVICE,
};
