1
0
mirror of https://github.com/jojo61/vdr-plugin-softhdcuvid.git synced 2023-10-10 13:37:41 +02:00

Support for libplacebo API Version 106

Support for LIBPLACEBO with opengl -> needs API >= 106
This commit is contained in:
jojo61 2021-01-10 13:55:09 +01:00
parent 184cc1aa05
commit a7471e8800
3 changed files with 293 additions and 114 deletions

102
Makefile
View File

@ -9,7 +9,7 @@
### Configuration (edit this for your needs) ### Configuration (edit this for your needs)
# config as needed # comment out if not needed
# what kind of decoder do we make - # what kind of decoder do we make -
# if VAAPI is enabled the pluginname is softhdvaapi # if VAAPI is enabled the pluginname is softhdvaapi
@ -20,21 +20,29 @@ CUVID ?= 0
# if you enable DRM then the plugin will only run without X server # if you enable DRM then the plugin will only run without X server
# only valid for VAAPI # only valid for VAAPI
# does not work with libplacebo
DRM ?= 0 DRM ?= 0
# use libplacebo - available for both decoders but not for DRM # use libplacebo -
# available for all decoders but for DRM you need LIBPLACEBO_GL
LIBPLACEBO ?= 1 LIBPLACEBO ?= 1
LIBPLACEBO_GL ?= 0
# use YADIF deint - only available with cuvid # use YADIF deint - only available with cuvid
#YADIF=1 #YADIF=1
# use gamma correction
#GAMMA ?= 0
CONFIG := #-DDEBUG # remove # to enable debug output CONFIG := #-DDEBUG # remove # to enable debug output
#--------------------- no more config needed past this point-------------------------------- #--------------------- no more config needed past this point--------------------------------
# sanitize selections -------- # sanitize selections --------
@ -70,6 +78,8 @@ endif # MAKECMDGOALS!=indent
endif # MAKECMDGOALS!=clean endif # MAKECMDGOALS!=clean
#-------------------------- #--------------------------
PLUGIN = softhdcuvid PLUGIN = softhdcuvid
# support OPENGLOSD always needed # support OPENGLOSD always needed
@ -146,33 +156,7 @@ APIVERSION = $(call PKGCFG,apiversion)
### Parse config ### Parse softhddevice config
ifeq ($(VAAPI),1)
CONFIG += -DVAAPI
#LIBPLACEBO=1
PLUGIN = softhdvaapi
LIBS += -lEGL
endif
ifeq ($(DRM),1)
PLUGIN = softhddrm
CONFIG += -DUSE_DRM -DVAAPI
LIBPLACEBO=0
_CFLAGS += $(shell pkg-config --cflags libdrm)
LIBS += -lgbm -ldrm
LIBS += -lEGL
endif
ifeq ($(CUVID),1)
CONFIG += -DUSE_PIP # PIP support
CONFIG += -DCUVID # enable CUVID decoder
LIBS += -lEGL -lGL
ifeq ($(YADIF),1)
CONFIG += -DYADIF # Yadif only with CUVID
endif
endif
ifeq ($(ALSA),1) ifeq ($(ALSA),1)
CONFIG += -DUSE_ALSA CONFIG += -DUSE_ALSA
@ -201,8 +185,45 @@ _CFLAGS += $(shell pkg-config --cflags freetype2)
LIBS += $(shell pkg-config --libs freetype2) LIBS += $(shell pkg-config --libs freetype2)
endif endif
ifeq ($(VAAPI),1)
CONFIG += -DVAAPI
#LIBPLACEBO=1
PLUGIN = softhdvaapi
endif
ifeq ($(LIBPLACEBO_GL),1)
CONFIG += -DPLACEBO_GL -DPLACEBO
LIBS += -lepoxy
LIBS += -lplacebo
else
LIBS += -lEGL
endif
ifeq ($(LIBPLACEBO),1) ifeq ($(LIBPLACEBO),1)
CONFIG += -DPLACEBO CONFIG += -DPLACEBO
LIBS += -lEGL
LIBS += -lplacebo
endif
ifeq ($(DRM),1)
PLUGIN = softhddrm
CONFIG += -DUSE_DRM -DVAAPI
_CFLAGS += $(shell pkg-config --cflags libdrm)
LIBS += -lgbm -ldrm -lEGL
endif
ifeq ($(CUVID),1)
CONFIG += -DUSE_PIP # PIP support
CONFIG += -DCUVID # enable CUVID decoder
LIBS += -lEGL -lGL
ifeq ($(YADIF),1)
CONFIG += -DYADIF # Yadif only with CUVID
endif
endif
ifeq ($(GAMMA),1)
CONFIG += -DGAMMA
endif endif
@ -278,15 +299,15 @@ endif
_CFLAGS += $(shell pkg-config --cflags x11 x11-xcb xcb xcb-icccm) _CFLAGS += $(shell pkg-config --cflags x11 x11-xcb xcb xcb-icccm)
LIBS += -lrt $(shell pkg-config --libs x11 x11-xcb xcb xcb-icccm) LIBS += -lrt $(shell pkg-config --libs x11 x11-xcb xcb xcb-icccm)
#_CFLAGS += -I/usr/local/cuda/include
_CFLAGS += -I./opengl -I./ _CFLAGS += -I./opengl -I./
LIBS += -L/usr/lib64 LIBS += -L/usr/lib64
LIBS += -L/usr/local/cuda/lib64
ifeq ($(LIBPLACEBO),1)
LIBS += -lplacebo
endif
ifeq ($(CUVID),1) ifeq ($(CUVID),1)
#LIBS += -lcuda -L/usr/local/cuda/targets/x86_64-linux/lib -lcudart -lnvcuvid
LIBS += -lcuda -lnvcuvid LIBS += -lcuda -lnvcuvid
endif endif
@ -308,9 +329,14 @@ override CFLAGS += $(_CFLAGS) $(DEFINES) $(INCLUDES) \
### The object files (add further files here): ### The object files (add further files here):
OBJS = softhdcuvid.o softhddev.o video.o audio.o codec.o ringbuffer.o OBJS = softhdcuvid.o softhddev.o video.o audio.o codec.o ringbuffer.o openglosd.o
ifeq ($(OPENGLOSD),1) ifeq ($(GAMMA),1)
OBJS += openglosd.o OBJS += colorramp.o
ifeq ($(DRM),1)
OBJS += gamma-drm.o
else
OBJS += gamma-vidmode.o
endif
endif endif
SRCS = $(wildcard $(OBJS:.o=.c)) *.cpp SRCS = $(wildcard $(OBJS:.o=.c)) *.cpp
@ -387,7 +413,9 @@ HDRS= $(wildcard *.h)
indent: indent:
for i in $(SRCS) $(HDRS); do \ for i in $(SRCS) $(HDRS); do \
VERSION_CONTROL=none indent $$i; \ indent $$i; \
unexpand -a $$i | sed -e s/constconst/const/ > $$i.up; \
mv $$i.up $$i; \
done done
video_test: video.c Makefile video_test: video.c Makefile

View File

@ -61,7 +61,7 @@ extern "C"
/// vdr-plugin version number. /// vdr-plugin version number.
/// Makefile extracts the version number for generating the file name /// Makefile extracts the version number for generating the file name
/// for the distribution archive. /// for the distribution archive.
static const char *const VERSION = "3.2.4" static const char *const VERSION = "3.3"
#ifdef GIT_REV #ifdef GIT_REV
"-GIT" GIT_REV "-GIT" GIT_REV
#endif #endif

255
video.c
View File

@ -38,8 +38,6 @@
/// @todo FIXME: use vaErrorStr for all VA-API errors. /// @todo FIXME: use vaErrorStr for all VA-API errors.
/// ///
//#define PLACEBO_GL
#define USE_XLIB_XCB ///< use xlib/xcb backend #define USE_XLIB_XCB ///< use xlib/xcb backend
#define noUSE_SCREENSAVER ///< support disable screensaver #define noUSE_SCREENSAVER ///< support disable screensaver
@ -131,7 +129,11 @@ typedef enum
#endif #endif
#ifdef USE_GLX #ifdef USE_GLX
#ifndef PLACEBO_GL
#include <GL/glew.h> #include <GL/glew.h>
#else
#include <epoxy/egl.h>
#endif
#include <GL/glu.h> #include <GL/glu.h>
#include <GL/glut.h> #include <GL/glut.h>
#include <GL/freeglut_ext.h> #include <GL/freeglut_ext.h>
@ -165,8 +167,11 @@ typedef enum
#include <assert.h> #include <assert.h>
// #define EGL_EGLEXT_PROTOTYPES // #define EGL_EGLEXT_PROTOTYPES
#if !defined PLACEBO_GL
#include <EGL/egl.h> #include <EGL/egl.h>
#include <EGL/eglext.h> #include <EGL/eglext.h>
#endif
#ifndef GL_OES_EGL_image #ifndef GL_OES_EGL_image
typedef void *GLeglImageOES; typedef void *GLeglImageOES;
#endif #endif
@ -690,8 +695,8 @@ static void VideoUpdateOutput(AVRational input_aspect_ratio, int input_width, in
// input not initialized yet, return immediately // input not initialized yet, return immediately
if (!input_aspect_ratio.num || !input_aspect_ratio.den) { if (!input_aspect_ratio.num || !input_aspect_ratio.den) {
output_width = video_width; *output_width = video_width;
output_height = video_height; *output_height = video_height;
return; return;
} }
#ifdef USE_DRM #ifdef USE_DRM
@ -820,6 +825,36 @@ static uint64_t test_time = 0;
} }
// printf("Video Locked for %d\n",(GetusTicks()-test_time)/1000); // printf("Video Locked for %d\n",(GetusTicks()-test_time)/1000);
#ifdef PLACEBO_GL
#define Lock_and_SharedContext\
{\
VideoThreadLock();\
eglMakeCurrent(eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, eglSharedContext);\
EglCheck();\
}
#define Unlock_and_NoContext {\
eglMakeCurrent(eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);\
EglCheck();\
VideoThreadUnlock();\
}
#define SharedContext\
{\
eglMakeCurrent(eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, eglSharedContext);\
EglCheck();\
}
#define NoContext {\
eglMakeCurrent(eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);\
EglCheck();\
}
#else
#ifdef PLACEBO
#define Lock_and_SharedContext {VideoThreadLock();}
#define Unlock_and_NoContext {VideoThreadUnlock();}
#define SharedContext {}
#define NoContext {}
#endif
#endif
//---------------------------------------------------------------------------- //----------------------------------------------------------------------------
// GLX // GLX
//---------------------------------------------------------------------------- //----------------------------------------------------------------------------
@ -1127,23 +1162,23 @@ static void EglInit(void)
int redSize, greenSize, blueSize, alphaSize; int redSize, greenSize, blueSize, alphaSize;
static int glewdone = 0; static int glewdone = 0;
#ifdef PLACEBO #if defined PLACEBO && !defined PLACEBO_GL
return; return;
#endif #endif
EGLContext context; EGLContext context;
// create egl context // create egl context
setenv("MESA_GL_VERSION_OVERRIDE", "3.3", 0); // setenv("MESA_GL_VERSION_OVERRIDE", "3.3", 0);
setenv("V3D_DOUBLE_BUFFER", "1", 0); // setenv("V3D_DOUBLE_BUFFER", "1", 0);
make_egl(); make_egl();
if (!glewdone) { if (!glewdone) {
GLenum err = glewInit(); GLenum err = glewInit();
glewdone = 1; glewdone = 1;
if (err != GLEW_OK) { // if (err != GLEW_OK) {
Debug(3, "Error: %s\n", glewGetErrorString(err)); // Debug(3, "Error: %s\n", glewGetErrorString(err));
} // }
} }
eglGetConfigAttrib(eglDisplay, eglConfig, EGL_BLUE_SIZE, &blueSize); eglGetConfigAttrib(eglDisplay, eglConfig, EGL_BLUE_SIZE, &blueSize);
@ -1155,6 +1190,7 @@ static void EglInit(void)
eglSharedContext = eglContext; eglSharedContext = eglContext;
context = eglCreateContext(eglDisplay, eglConfig, eglSharedContext, eglAttrs); context = eglCreateContext(eglDisplay, eglConfig, eglSharedContext, eglAttrs);
EglCheck(); EglCheck();
if (!context) { if (!context) {
Fatal(_("video/egl: can't create egl context\n")); Fatal(_("video/egl: can't create egl context\n"));
@ -1169,7 +1205,7 @@ static void EglInit(void)
static void EglExit(void) static void EglExit(void)
{ {
Debug(3, "video/egl: %s\n", __FUNCTION__); Debug(3, "video/egl: %s\n", __FUNCTION__);
#if defined PLACEBO #if defined PLACEBO && !defined PLACEBO_GL
return; return;
#endif #endif
@ -1577,13 +1613,17 @@ static void CuvidDestroySurfaces(CuvidDecoder * decoder)
close(decoder->pl_images[i].planes[j].texture->params.shared_mem.handle.fd); close(decoder->pl_images[i].planes[j].texture->params.shared_mem.handle.fd);
} }
#endif #endif
SharedContext;
pl_tex_destroy(p->gpu, &decoder->pl_images[i].planes[j].texture); pl_tex_destroy(p->gpu, &decoder->pl_images[i].planes[j].texture);
NoContext;
} }
#else #else
#ifdef CUVID #ifdef CUVID
checkCudaErrors(cu->cuGraphicsUnregisterResource(decoder->cu_res[i][j])); checkCudaErrors(cu->cuGraphicsUnregisterResource(decoder->cu_res[i][j]));
#endif #endif
#ifdef VAAPI #ifdef PLACEBO
if (p->hasdma_buf) {
#endif
if (decoder->images[i * Planes + j]) { if (decoder->images[i * Planes + j]) {
DestroyImageKHR(eglGetCurrentDisplay(), decoder->images[i * Planes + j]); DestroyImageKHR(eglGetCurrentDisplay(), decoder->images[i * Planes + j]);
if (decoder->fds[i * Planes + j]) if (decoder->fds[i * Planes + j])
@ -1591,6 +1631,8 @@ static void CuvidDestroySurfaces(CuvidDecoder * decoder)
} }
decoder->fds[i * Planes + j] = 0; decoder->fds[i * Planes + j] = 0;
decoder->images[i * Planes + j] = 0; decoder->images[i * Planes + j] = 0;
#ifdef PLACEBO
}
#endif #endif
#endif #endif
} }
@ -1671,6 +1713,7 @@ static void CuvidReleaseSurface(CuvidDecoder * decoder, int surface)
av_frame_free(&decoder->frames[surface]); av_frame_free(&decoder->frames[surface]);
} }
#ifdef PLACEBO #ifdef PLACEBO
SharedContext;
if (p->has_dma_buf) { if (p->has_dma_buf) {
if (decoder->pl_images[surface].planes[0].texture) { if (decoder->pl_images[surface].planes[0].texture) {
if (decoder->pl_images[surface].planes[0].texture->params.shared_mem.handle.fd) { if (decoder->pl_images[surface].planes[0].texture->params.shared_mem.handle.fd) {
@ -1685,6 +1728,7 @@ static void CuvidReleaseSurface(CuvidDecoder * decoder, int surface)
pl_tex_destroy(p->gpu, &decoder->pl_images[surface].planes[1].texture); pl_tex_destroy(p->gpu, &decoder->pl_images[surface].planes[1].texture);
} }
} }
NoContext;
#else #else
#ifdef VAAPI #ifdef VAAPI
if (decoder->images[surface * Planes]) { if (decoder->images[surface * Planes]) {
@ -1768,9 +1812,10 @@ static const struct mp_egl_config_attr mp_egl_attribs[] = {
}; };
const int mpgl_preferred_gl_versions[] = { const int mpgl_preferred_gl_versions[] = {
// 440, 460,
// 430, 440,
// 400, 430,
400,
330, 330,
320, 320,
310, 310,
@ -1807,12 +1852,12 @@ static bool create_context_cb(EGLDisplay display, int es_version, EGLContext * o
Fatal(_("Wrong ES version \n"));; Fatal(_("Wrong ES version \n"));;
} }
Debug(3, "Trying to create %s context.\n", name);
if (!eglBindAPI(api)) { if (!eglBindAPI(api)) {
Fatal(_(" Could not bind API!\n")); Fatal(_(" Could not bind API!\n"));
} }
Debug(3, "Trying to create %s context \n", name);
EGLint attributes8[] = { EGLint attributes8[] = {
EGL_SURFACE_TYPE, EGL_WINDOW_BIT, EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
EGL_RED_SIZE, 8, EGL_RED_SIZE, 8,
@ -1854,6 +1899,7 @@ static bool create_context_cb(EGLDisplay display, int es_version, EGLContext * o
num_configs = 0; num_configs = 0;
} }
} }
EGLConfig *configs = malloc(sizeof(EGLConfig) * num_configs); EGLConfig *configs = malloc(sizeof(EGLConfig) * num_configs);
if (!eglChooseConfig(display, attribs, configs, num_configs, &num_configs)) if (!eglChooseConfig(display, attribs, configs, num_configs, &num_configs))
@ -2221,6 +2267,7 @@ void createTextureDst(CuvidDecoder * decoder, int anz, unsigned int size_x, unsi
struct pl_image *img; struct pl_image *img;
struct pl_plane *pl; struct pl_plane *pl;
SharedContext;
// printf("Create textures and planes %d %d\n",size_x,size_y); // printf("Create textures and planes %d %d\n",size_x,size_y);
Debug(3, "video/vulkan: create %d Textures Format %s w %d h %d \n", anz, Debug(3, "video/vulkan: create %d Textures Format %s w %d h %d \n", anz,
PixFmt == AV_PIX_FMT_NV12 ? "NV12" : "P010", size_x, size_y); PixFmt == AV_PIX_FMT_NV12 ? "NV12" : "P010", size_x, size_y);
@ -2257,9 +2304,12 @@ void createTextureDst(CuvidDecoder * decoder, int anz, unsigned int size_x, unsi
.format = fmt, .format = fmt,
.sampleable = true, .sampleable = true,
.host_writable = true, .host_writable = true,
.blit_dst = true,
.sample_mode = PL_TEX_SAMPLE_LINEAR, .sample_mode = PL_TEX_SAMPLE_LINEAR,
.address_mode = PL_TEX_ADDRESS_CLAMP, .address_mode = PL_TEX_ADDRESS_CLAMP,
#if !defined PLACEBO_GL
.export_handle = PL_HANDLE_FD, .export_handle = PL_HANDLE_FD,
#endif
}); });
} }
@ -2325,7 +2375,7 @@ void createTextureDst(CuvidDecoder * decoder, int anz, unsigned int size_x, unsi
img->height = size_y; img->height = size_y;
img->num_overlays = 0; img->num_overlays = 0;
} }
NoContext;
} }
#ifdef VAAPI #ifdef VAAPI
@ -2348,13 +2398,13 @@ void generateVAAPIImage(CuvidDecoder * decoder, int index, const AVFrame * frame
return; return;
} }
vaSyncSurface(decoder->VaDisplay, (unsigned int)frame->data[3]); vaSyncSurface(decoder->VaDisplay, (unsigned int)frame->data[3]);
VideoThreadLock(); Lock_and_SharedContext;
for (n = 0; n < 2; n++) { // Set DMA_BUF from VAAPI decoder to Textures for (n = 0; n < 2; n++) { // Set DMA_BUF from VAAPI decoder to Textures
int id = desc.layers[n].object_index[0]; int id = desc.layers[n].object_index[0];
int fd = desc.objects[id].fd; int fd = desc.objects[id].fd;
uint32_t size = desc.objects[id].size; uint32_t size = desc.objects[id].size;
uint32_t offset = desc.layers[n].offset[0]; uint32_t offset = desc.layers[n].offset[0];
const struct pl_fmt *fmt; struct pl_fmt *fmt;
if (fd == -1) { if (fd == -1) {
printf("Fehler beim Import von Surface %d\n", index); printf("Fehler beim Import von Surface %d\n", index);
@ -2367,6 +2417,10 @@ void generateVAAPIImage(CuvidDecoder * decoder, int index, const AVFrame * frame
fmt = pl_find_named_fmt(p->gpu, n == 0 ? "r16" : "rg16"); // 10 Bit YUV fmt = pl_find_named_fmt(p->gpu, n == 0 ? "r16" : "rg16"); // 10 Bit YUV
} }
#ifdef PLACEBO_GL
fmt->fourcc = desc.layers[n].drm_format;
#endif
struct pl_tex_params tex_params = { struct pl_tex_params tex_params = {
.w = n == 0 ? image_width : image_width / 2, .w = n == 0 ? image_width : image_width / 2,
.h = n == 0 ? image_height : image_height / 2, .h = n == 0 ? image_height : image_height / 2,
@ -2374,7 +2428,9 @@ void generateVAAPIImage(CuvidDecoder * decoder, int index, const AVFrame * frame
.format = fmt, .format = fmt,
.sampleable = true, .sampleable = true,
.host_writable = false, .host_writable = false,
.address_mode = PL_TEX_ADDRESS_CLAMP, .blit_dst = true,
.renderable = true,
.address_mode = PL_TEX_ADDRESS_CLAMP ,
.sample_mode = PL_TEX_SAMPLE_LINEAR, .sample_mode = PL_TEX_SAMPLE_LINEAR,
.import_handle = PL_HANDLE_DMA_BUF, .import_handle = PL_HANDLE_DMA_BUF,
.shared_mem = (struct pl_shared_mem) { .shared_mem = (struct pl_shared_mem) {
@ -2383,6 +2439,9 @@ void generateVAAPIImage(CuvidDecoder * decoder, int index, const AVFrame * frame
}, },
.size = size, .size = size,
.offset = offset, .offset = offset,
#ifdef PLACEBO_GL
.stride_w = desc.layers[n].pitch[0],
#endif
#if PL_API_VER > 87 #if PL_API_VER > 87
.drm_format_mod = DRM_FORMAT_MOD_INVALID, .drm_format_mod = DRM_FORMAT_MOD_INVALID,
#endif #endif
@ -2395,10 +2454,11 @@ void generateVAAPIImage(CuvidDecoder * decoder, int index, const AVFrame * frame
pl_tex_destroy(p->gpu, &decoder->pl_images[index].planes[n].texture); pl_tex_destroy(p->gpu, &decoder->pl_images[index].planes[n].texture);
} }
decoder->pl_images[index].planes[n].texture = pl_tex_create(p->gpu, &tex_params);
}
VideoThreadUnlock();
decoder->pl_images[index].planes[n].texture = pl_tex_create(p->gpu, &tex_params);
}
Unlock_and_NoContext;
} }
#endif #endif
@ -3116,14 +3176,22 @@ int get_RGB(CuvidDecoder * decoder)
.format = fmt, .format = fmt,
.sampleable = true, .sampleable = true,
.renderable = true, .renderable = true,
.blit_dst = true,
.host_readable = true, .host_readable = true,
.sample_mode = PL_TEX_SAMPLE_LINEAR, .sample_mode = PL_TEX_SAMPLE_LINEAR,
.address_mode = PL_TEX_ADDRESS_CLAMP, .address_mode = PL_TEX_ADDRESS_CLAMP,
}); });
#if PL_API_VER >= 100
target.crop.x0 = (float)decoder->OutputX * faktorx;
target.crop.y0 = (float)decoder->OutputY * faktory;
target.crop.x1 = (float)(decoder->OutputX + decoder->OutputWidth) * faktorx;
target.crop.y1 = (float)(decoder->OutputY + decoder->OutputHeight) * faktory;
#else
target.dst_rect.x0 = (float)decoder->OutputX * faktorx; target.dst_rect.x0 = (float)decoder->OutputX * faktorx;
target.dst_rect.y0 = (float)decoder->OutputY * faktory; target.dst_rect.y0 = (float)decoder->OutputY * faktory;
target.dst_rect.x1 = (float)(decoder->OutputX + decoder->OutputWidth) * faktorx; target.dst_rect.x1 = (float)(decoder->OutputX + decoder->OutputWidth) * faktorx;
target.dst_rect.y1 = (float)(decoder->OutputY + decoder->OutputHeight) * faktory; target.dst_rect.y1 = (float)(decoder->OutputY + decoder->OutputHeight) * faktory;
#endif
target.repr.sys = PL_COLOR_SYSTEM_RGB; target.repr.sys = PL_COLOR_SYSTEM_RGB;
target.repr.levels = PL_COLOR_LEVELS_PC; target.repr.levels = PL_COLOR_LEVELS_PC;
target.repr.alpha = PL_ALPHA_UNKNOWN; target.repr.alpha = PL_ALPHA_UNKNOWN;
@ -3786,35 +3854,76 @@ static void CuvidMixVideo(CuvidDecoder * decoder, __attribute__((unused))
break; break;
} }
// Source crop // Source crop
if (VideoScalerTest) { // right side defnied scaler if (VideoScalerTest) { // right side defined scaler
// pl_tex_clear(p->gpu,target->fbo,(float[4]){0}); // clear frame #if PL_API_VER >= 100
//Input crop
img->crop.x0 = video_src_rect.x1 / 2 + 1;
img->crop.y0 = video_src_rect.y0;
img->crop.x1 = video_src_rect.x1;
img->crop.y1 = video_src_rect.y1;
// Output scale
#ifdef PLACEBO_GL
target->crop.x0 = dst_video_rect.x1 / 2 + dst_video_rect.x0 / 2 + 1;
target->crop.y1 = dst_video_rect.y0;
target->crop.x1 = dst_video_rect.x1;
target->crop.y0 = dst_video_rect.y1;
#else
target->crop.x0 = dst_video_rect.x1 / 2 + dst_video_rect.x0 / 2 + 1;
target->crop.y0 = dst_video_rect.y0;
target->crop.x1 = dst_video_rect.x1;
target->crop.y1 = dst_video_rect.y1;
#endif
#else
// Input crop
img->src_rect.x0 = video_src_rect.x1 / 2 + 1; img->src_rect.x0 = video_src_rect.x1 / 2 + 1;
img->src_rect.y0 = video_src_rect.y0; img->src_rect.y0 = video_src_rect.y0;
img->src_rect.x1 = video_src_rect.x1; img->src_rect.x1 = video_src_rect.x1;
img->src_rect.y1 = video_src_rect.y1; img->src_rect.y1 = video_src_rect.y1;
// Output Scale
// Video aspect ratio
target->dst_rect.x0 = dst_video_rect.x1 / 2 + dst_video_rect.x0 / 2 + 1; target->dst_rect.x0 = dst_video_rect.x1 / 2 + dst_video_rect.x0 / 2 + 1;
target->dst_rect.y0 = dst_video_rect.y0; target->dst_rect.y0 = dst_video_rect.y0;
target->dst_rect.x1 = dst_video_rect.x1; target->dst_rect.x1 = dst_video_rect.x1;
target->dst_rect.y1 = dst_video_rect.y1; target->dst_rect.y1 = dst_video_rect.y1;
#endif
} else { } else {
#if PL_API_VER >= 100
img->crop.x0 = video_src_rect.x0;
img->crop.y0 = video_src_rect.y0;
img->crop.x1 = video_src_rect.x1;
img->crop.y1 = video_src_rect.y1;
#ifdef PLACEBO_GL
target->crop.x0 = dst_video_rect.x0;
target->crop.y1 = dst_video_rect.y0;
target->crop.x1 = dst_video_rect.x1;
target->crop.y0 = dst_video_rect.y1;
#else
target->crop.x0 = dst_video_rect.x0;
target->crop.y0 = dst_video_rect.y0;
target->crop.x1 = dst_video_rect.x1;
target->crop.y1 = dst_video_rect.y1;
#endif
#else
img->src_rect.x0 = video_src_rect.x0; img->src_rect.x0 = video_src_rect.x0;
img->src_rect.y0 = video_src_rect.y0; img->src_rect.y0 = video_src_rect.y0;
img->src_rect.x1 = video_src_rect.x1; img->src_rect.x1 = video_src_rect.x1;
img->src_rect.y1 = video_src_rect.y1; img->src_rect.y1 = video_src_rect.y1;
// Video aspect ratio
target->dst_rect.x0 = dst_video_rect.x0; target->dst_rect.x0 = dst_video_rect.x0;
target->dst_rect.y0 = dst_video_rect.y0; target->dst_rect.y0 = dst_video_rect.y0;
target->dst_rect.x1 = dst_video_rect.x1; target->dst_rect.x1 = dst_video_rect.x1;
target->dst_rect.y1 = dst_video_rect.y1; target->dst_rect.y1 = dst_video_rect.y1;
#endif
} }
#if PL_API_VER < 100
if (level == 0) if (level == 0)
pl_tex_clear(p->gpu, target->fbo, (float[4]) { 0 } pl_tex_clear(p->gpu, target->fbo, (float[4]) { 0 });
); #else
if (!level && pl_frame_is_cropped(target))
pl_frame_clear(p->gpu, target, (float[3]) {0} );
#endif
if (VideoColorBlindness) { if (VideoColorBlindness) {
switch (VideoColorBlindness) { switch (VideoColorBlindness) {
case 1: case 1:
@ -3881,10 +3990,12 @@ static void CuvidMixVideo(CuvidDecoder * decoder, __attribute__((unused))
} }
} }
render_params.hooks = &p->hook; render_params.hooks = &p->hook;
if (ovl) if (ovl || (video_src_rect.x1 > dst_video_rect.x1) || (video_src_rect.y1 > dst_video_rect.y1) ) {
render_params.num_hooks = 0; // no shaders when OSD activ render_params.num_hooks = 0; // no user shaders when OSD activ or downward scaling
else }
else {
render_params.num_hooks = p->num_shaders; render_params.num_hooks = p->num_shaders;
}
#endif #endif
if (decoder->newchannel && current == 0) { if (decoder->newchannel && current == 0) {
@ -3900,10 +4011,29 @@ static void CuvidMixVideo(CuvidDecoder * decoder, __attribute__((unused))
decoder->newchannel = 0; decoder->newchannel = 0;
if (!pl_render_image(p->renderer, &decoder->pl_images[current], target, &render_params)) { if (!pl_render_image(p->renderer, &decoder->pl_images[current], target, &render_params)) {
Debug(3, "Failed rendering frame!\n"); Debug(4, "Failed rendering frame!\n");
} }
if (VideoScalerTest) { // left side test scaler if (VideoScalerTest) { // left side test scaler
#if PL_API_VER >= 100
// Source crop
img->crop.x0 = video_src_rect.x0;
img->crop.y0 = video_src_rect.y0;
img->crop.x1 = video_src_rect.x1 / 2;
img->crop.y1 = video_src_rect.y1;
#ifdef PLACEBO_GL
target->crop.x0 = dst_video_rect.x0;
target->crop.y1 = dst_video_rect.y0;
target->crop.x1 = dst_video_rect.x1 / 2 + dst_video_rect.x0 / 2;
target->crop.y0 = dst_video_rect.y1;
#else
// Video aspect ratio
target->crop.x0 = dst_video_rect.x0;
target->crop.y0 = dst_video_rect.y0;
target->crop.x1 = dst_video_rect.x1 / 2 + dst_video_rect.x0 / 2;
target->crop.y1 = dst_video_rect.y1;
#endif
#else
// Source crop // Source crop
img->src_rect.x0 = video_src_rect.x0; img->src_rect.x0 = video_src_rect.x0;
img->src_rect.y0 = video_src_rect.y0; img->src_rect.y0 = video_src_rect.y0;
@ -3915,6 +4045,7 @@ static void CuvidMixVideo(CuvidDecoder * decoder, __attribute__((unused))
target->dst_rect.y0 = dst_video_rect.y0; target->dst_rect.y0 = dst_video_rect.y0;
target->dst_rect.x1 = dst_video_rect.x1 / 2 + dst_video_rect.x0 / 2; target->dst_rect.x1 = dst_video_rect.x1 / 2 + dst_video_rect.x0 / 2;
target->dst_rect.y1 = dst_video_rect.y1; target->dst_rect.y1 = dst_video_rect.y1;
#endif
render_params.upscaler = pl_named_filters[VideoScalerTest - 1].filter; render_params.upscaler = pl_named_filters[VideoScalerTest - 1].filter;
render_params.downscaler = pl_named_filters[VideoScalerTest - 1].filter; render_params.downscaler = pl_named_filters[VideoScalerTest - 1].filter;
@ -3922,7 +4053,7 @@ static void CuvidMixVideo(CuvidDecoder * decoder, __attribute__((unused))
p->renderertest = pl_renderer_create(p->ctx, p->gpu); p->renderertest = pl_renderer_create(p->ctx, p->gpu);
if (!pl_render_image(p->renderertest, &decoder->pl_images[current], target, &render_params)) { if (!pl_render_image(p->renderertest, &decoder->pl_images[current], target, &render_params)) {
Debug(3, "Failed rendering frame!\n"); Debug(4, "Failed rendering frame!\n");
} }
} else if (p->renderertest) { } else if (p->renderertest) {
pl_renderer_destroy(&p->renderertest); pl_renderer_destroy(&p->renderertest);
@ -3978,11 +4109,18 @@ void make_osd_overlay(int x, int y, int width, int height)
pl->repr.alpha = PL_ALPHA_INDEPENDENT; pl->repr.alpha = PL_ALPHA_INDEPENDENT;
memcpy(&osdoverlay.color, &pl_color_space_srgb, sizeof(struct pl_color_space)); memcpy(&osdoverlay.color, &pl_color_space_srgb, sizeof(struct pl_color_space));
#ifdef PLACEBO_GL
pl->rect.x0 = x;
pl->rect.y1 = VideoWindowHeight - y ; // Boden von oben
pl->rect.x1 = x + width;
pl->rect.y0 = VideoWindowHeight - height - y;
#else
pl->rect.x0 = x; pl->rect.x0 = x;
pl->rect.y0 = VideoWindowHeight - y + offset; // Boden von oben pl->rect.y0 = VideoWindowHeight - y + offset; // Boden von oben
pl->rect.x1 = x + width; pl->rect.x1 = x + width;
pl->rect.y1 = VideoWindowHeight - height - y + offset; pl->rect.y1 = VideoWindowHeight - height - y + offset;
#endif
} }
#endif #endif
/// ///
@ -4093,6 +4231,7 @@ static void CuvidDisplayFrame(void)
#ifdef VAAPI #ifdef VAAPI
VideoThreadLock(); VideoThreadLock();
#endif #endif
pl_render_target_from_swapchain(&target, &frame); // make target frame pl_render_target_from_swapchain(&target, &frame); // make target frame
if (VideoSurfaceModesChanged) { if (VideoSurfaceModesChanged) {
@ -4260,17 +4399,15 @@ static void CuvidDisplayFrame(void)
glActiveTexture(GL_TEXTURE0); glActiveTexture(GL_TEXTURE0);
// eglMakeCurrent(eglDisplay, eglSurface, eglSurface, eglThreadContext); // eglMakeCurrent(eglDisplay, eglSurface, eglSurface, eglThreadContext);
} }
#endif #endif
#ifdef PLACEBO
//#ifdef VAAPI #if defined PLACEBO // && !defined PLACEBO_GL
// first_time = GetusTicks(); // first_time = GetusTicks();
if (!pl_swapchain_submit_frame(p->swapchain)) if (!pl_swapchain_submit_frame(p->swapchain))
Fatal(_("Failed to submit swapchain buffer\n")); Fatal(_("Failed to submit swapchain buffer\n"));
pl_swapchain_swap_buffers(p->swapchain); // swap buffers pl_swapchain_swap_buffers(p->swapchain); // swap buffers
NoContext;
//#endif
VideoThreadUnlock(); VideoThreadUnlock();
#else // not PLACEBO #else // not PLACEBO
#ifdef CUVID #ifdef CUVID
@ -4297,18 +4434,12 @@ static void CuvidDisplayFrame(void)
#ifdef PLACEBO_GL #ifdef PLACEBO_GL
CuvidSwapBuffer() { CuvidSwapBuffer() {
#ifdef CUVID
glXGetVideoSyncSGI(&Count); // get current frame
glXSwapBuffers(XlibDisplay, VideoWindow);
glXMakeCurrent(XlibDisplay, None, NULL);
#else
#ifndef USE_DRM #ifndef USE_DRM
eglSwapBuffers(eglDisplay, eglSurface); eglSwapBuffers(eglDisplay, eglSurface);
eglMakeCurrent(eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT); // eglMakeCurrent(eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, EGL_NO_CONTEXT);
#else #else
drm_swap_buffers(); drm_swap_buffers();
#endif #endif
#endif
} }
#endif #endif
@ -5338,16 +5469,27 @@ void InitPlacebo()
} }
#ifdef PLACEBO_GL #ifdef PLACEBO_GL
// eglMakeCurrent(eglDisplay, EGL_NO_SURFACE, EGL_NO_SURFACE, eglSharedContext);
struct pl_opengl_params params = pl_opengl_default_params; struct pl_opengl_params params = pl_opengl_default_params;
params.egl_display = eglDisplay;
params.egl_context = eglContext;
p->gl = pl_opengl_create(p->ctx, &params); p->gl = pl_opengl_create(p->ctx, &params);
if (!p->gl)
Fatal(_("Failed to create placebo opengl \n"));
p->swapchain = pl_opengl_create_swapchain(p->gl, &(struct pl_opengl_swapchain_params) { p->swapchain = pl_opengl_create_swapchain(p->gl, &(struct pl_opengl_swapchain_params) {
.swap_buffers = (void (*)(void *)) CuvidSwapBuffer, .swap_buffers = (void (*)(void *)) CuvidSwapBuffer,
.priv = NULL, .framebuffer.flipped = true,
.framebuffer.id = 0,
.max_swapchain_depth = 2,
.priv = VideoWindow,
}); });
p->gpu = p->gl->gpu; p->gpu = p->gl->gpu;
#else #else
struct pl_vulkan_params params; struct pl_vulkan_params params;
struct pl_vk_inst_params iparams = pl_vk_inst_default_params; struct pl_vk_inst_params iparams = pl_vk_inst_default_params;
@ -5514,11 +5656,13 @@ void exit_display()
static void *VideoHandlerThread(void *dummy) static void *VideoHandlerThread(void *dummy)
{ {
#ifdef VAAPI
EGLint contextAttrs[] = { EGLint contextAttrs[] = {
EGL_CONTEXT_CLIENT_VERSION, 3, EGL_CONTEXT_CLIENT_VERSION, 3,
EGL_NONE EGL_NONE
}; };
#endif
int redSize, greenSize, blueSize, alphaSize;
prctl(PR_SET_NAME, "video display", 0, 0, 0); prctl(PR_SET_NAME, "video display", 0, 0, 0);
#ifdef GAMMA #ifdef GAMMA
@ -5534,7 +5678,14 @@ static void *VideoHandlerThread(void *dummy)
} }
#endif #endif
#if (defined VAAPI && !defined PLACEBO) || (defined VAAPI && defined PLACEBO_GL) #if (defined VAAPI && !defined PLACEBO) || (defined VAAPI && defined PLACEBO_GL)
#ifdef PLACEBO_GL
if (!eglBindAPI(EGL_OPENGL_API)) {
Fatal(_(" Could not bind API!\n"));
}
eglThreadContext = eglCreateContext(eglDisplay, eglConfig, eglSharedContext, eglAttrs);
#else
eglThreadContext = eglCreateContext(eglDisplay, eglConfig, eglSharedContext, contextAttrs); eglThreadContext = eglCreateContext(eglDisplay, eglConfig, eglSharedContext, contextAttrs);
#endif
if (!eglThreadContext) { if (!eglThreadContext) {
EglCheck(); EglCheck();
Fatal(_("video/egl: can't create thread egl context\n")); Fatal(_("video/egl: can't create thread egl context\n"));
@ -7017,7 +7168,7 @@ void VideoInit(const char *display_name)
//xcb_prefetch_maximum_request_length(Connection); //xcb_prefetch_maximum_request_length(Connection);
xcb_flush(Connection); xcb_flush(Connection);
#endif #endif
#ifdef PLACEBO_ #ifdef PLACEBO_NOT
InitPlacebo(); InitPlacebo();
#endif #endif