distribution/packages/games/native/moonlight/patches/001-rotation.patch

223 lines
7.5 KiB
Diff
Raw Normal View History

2022-05-26 22:14:52 +00:00
From fd0cff622860903d4146a15062cfb0ecce300b28 Mon Sep 17 00:00:00 2001
From: krishenriksen <info@krishenriksen.dk>
Date: Mon, 1 Feb 2021 09:21:07 +0700
Subject: [PATCH 1/2] Rotation and tearing fix on Rockchip video backend for
rg351p
---
cmake/FindRockchip.cmake | 10 ++++--
src/video/rk.c | 77 ++++++++++++++++++++++++++++++++++++++--
2 files changed, 83 insertions(+), 4 deletions(-)
diff --git a/cmake/FindRockchip.cmake b/cmake/FindRockchip.cmake
index 83764dd2..1ad3f938 100644
--- a/cmake/FindRockchip.cmake
+++ b/cmake/FindRockchip.cmake
@@ -8,7 +8,13 @@ find_library(DRM_LIBRARY
NAMES libdrm.so
DOC "Path to libdrm Library"
PATHS /usr/local/lib /usr/lib /usr/lib/aarch64-linux-gnu /usr/lib/arm-linux-gnueabihf)
-mark_as_advanced(DRM_INCLUDE_DIR)
+mark_as_advanced(DRM_LIBRARY)
+
+find_library(RGA_LIBRARY
+ NAMES librga.so
+ DOC "Path to librga Library"
+ PATHS /usr/local/lib /usr/lib /usr/lib/aarch64-linux-gnu /usr/lib/arm-linux-gnueabihf)
+mark_as_advanced(RGA_LIBRARY)
find_path(ROCKCHIP_INCLUDE_DIR
NAMES rk_mpi.h
@@ -26,4 +32,4 @@ include(${CMAKE_ROOT}/Modules/FindPackageHandleStandardArgs.cmake)
FIND_PACKAGE_HANDLE_STANDARD_ARGS(Rockchip DEFAULT_MSG ROCKCHIP_INCLUDE_DIR ROCKCHIP_LIBRARY)
set(ROCKCHIP_INCLUDE_DIRS ${ROCKCHIP_INCLUDE_DIR} ${DRM_INCLUDE_DIR})
-set(ROCKCHIP_LIBRARIES ${ROCKCHIP_LIBRARY} ${DRM_LIBRARY})
+set(ROCKCHIP_LIBRARIES ${ROCKCHIP_LIBRARY} ${DRM_LIBRARY} ${RGA_LIBRARY})
diff --git a/src/video/rk.c b/src/video/rk.c
index 44526443..af9451d7 100644
--- a/src/video/rk.c
+++ b/src/video/rk.c
@@ -37,15 +37,19 @@
#include <libdrm/drm_fourcc.h>
#include <rockchip/rk_mpi.h>
+#include <rga/RgaApi.h>
#define READ_BUF_SIZE 0x00100000
#define MAX_FRAMES 16
+#define MAX_DEST_BUFFERS 3
#define RK_H264 7
#define RK_H265 16777220
void *pkt_buf = NULL;
int fd;
int fb_id;
+int fb_id_rot[MAX_DEST_BUFFERS];
+int prime_fd_rot[MAX_DEST_BUFFERS];
uint32_t plane_id, crtc_id;
int frm_eos;
int crtc_width;
@@ -78,6 +82,7 @@ struct {
void *display_thread(void *param) {
+ static int index = 0;
int ret;
while (!frm_eos) {
@@ -94,8 +99,9 @@ void *display_thread(void *param) {
return NULL;
}
}
- _fb_id = fb_id;
+ _fb_id = fb_id_rot[index];
+ index = (index + 1) % MAX_DEST_BUFFERS;
fb_id = 0;
ret = pthread_mutex_unlock(&mutex);
assert(!ret);
@@ -110,10 +116,13 @@ void *display_thread(void *param) {
void *frame_thread(void *param) {
+ static int index = 0;
int count = 0;
int ret;
int i;
MppFrame frame = NULL;
+ rga_info_t src_info = {0};
+ rga_info_t dst_info = {0};
while (!frm_eos) {
@@ -137,7 +146,15 @@ void *frame_thread(void *param) {
RK_U32 ver_stride = mpp_frame_get_ver_stride(frame);
MppFrameFormat fmt = mpp_frame_get_fmt(frame);
assert((fmt == MPP_FMT_YUV420SP) || (fmt == MPP_FMT_YUV420SP_10BIT));
-
+ printf("Frame WxH=%dx%d WSxHs=%dx%d\n", frm_width, frm_height, hor_stride, ver_stride);
+
+#if 1
+ // position overlay, expand to full screen
+ fb_x = 0;
+ fb_y = 0;
+ fb_width = crtc_width;
+ fb_height = crtc_height;
+#else
// position overlay, scale to ratio
float crt_ratio = (float)crtc_width/crtc_height;
float frame_ratio = (float)frm_width/frm_height;
@@ -153,6 +170,47 @@ void *frame_thread(void *param) {
fb_x = 0;
fb_y = (crtc_height-fb_height)/2;
}
+#endif
+ for (int i = 0; i < MAX_DEST_BUFFERS; i++) {
+ // new DRM buffer for rotated screen
+ struct drm_mode_create_dumb dmcd2 = {0};
+ dmcd2.bpp = fmt==MPP_FMT_YUV420SP?8:10;
+ dmcd2.width = hor_stride;
+ dmcd2.height = ver_stride*2; // documentation say not v*2/3 but v*2 (additional info included)
+ do {
+ ret = ioctl(fd, DRM_IOCTL_MODE_CREATE_DUMB, &dmcd2);
+ } while (ret == -1 && (errno == EINTR || errno == EAGAIN));
+
+ struct drm_prime_handle dph2 = {0};
+ dph2.handle = dmcd2.handle;
+ dph2.fd = -1;
+ do {
+ ret = ioctl(fd, DRM_IOCTL_PRIME_HANDLE_TO_FD, &dph2);
+ } while (ret == -1 && (errno == EINTR || errno == EAGAIN));
+ assert(!ret);
+
+ prime_fd_rot[i] = dph2.fd;
+
+ uint32_t handles[4] = {0}, pitches[4] = {0}, offsets[4] = {0};
+ handles[0] = dmcd2.handle;
+ offsets[0] = 0;
+ pitches[0] = hor_stride;
+ handles[1] = dmcd2.handle;
+ offsets[1] = hor_stride * ver_stride;
+ pitches[1] = hor_stride;
+ ret = drmModeAddFB2(fd, frm_width, frm_height, fmt==MPP_FMT_YUV420SP?DRM_FORMAT_NV12:DRM_FORMAT_NV12_10, handles, pitches, offsets, &fb_id_rot[i], 0);
+ assert(!ret);
+ }
+ // setup rotation
+ src_info.mmuFlag = 1;
+ src_info.rotation = HAL_TRANSFORM_ROT_270;
+
+ rga_set_rect(&src_info.rect, 0, 0, frm_width, frm_height, mpp_frame_get_hor_stride(frame), mpp_frame_get_ver_stride(frame), RK_FORMAT_YCbCr_420_SP);
+
+ dst_info.fd = prime_fd_rot[index];
+ dst_info.mmuFlag = 1;
+
+ rga_set_rect(&dst_info.rect, 0, 0, frm_width, frm_height, mpp_frame_get_hor_stride(frame), mpp_frame_get_ver_stride(frame), RK_FORMAT_YCbCr_420_SP);
// create new external frame group and allocate (commit flow) new DRM buffers and DRM FB
assert(!mpi_frm_grp);
@@ -220,6 +278,15 @@ void *frame_thread(void *param) {
// send DRM FB to display thread
ret = pthread_mutex_lock(&mutex);
assert(!ret);
+
+ src_info.fd = frame_to_drm[i].prime_fd;
+ dst_info.fd = prime_fd_rot[index];
+ index = (index + 1) % MAX_DEST_BUFFERS;
+
+ if (c_RkRgaBlit(&src_info, &dst_info, NULL) < 0) {
+ fprintf(stderr, "Failed to do rga blit\n");
+ }
+
fb_id = frame_to_drm[i].fb_id;
ret = pthread_cond_signal(&cond);
assert(!ret);
@@ -359,6 +426,10 @@ int rk_setup(int videoFormat, int width, int height, int redrawRate, void* conte
// hide cursor by move in left lower corner
drmModeMoveCursor(fd, crtc_id, 0, crtc_height);
+ // RGA Setup
+
+ c_RkRgaInit();
+
// MPI SETUP
pkt_buf = malloc(READ_BUF_SIZE);
@@ -442,6 +513,8 @@ void rk_cleanup() {
mpp_destroy(mpi_ctx);
free(pkt_buf);
+ c_RkRgaDeInit();
+
drmModeFreePlane(ovr);
drmModeFreePlaneResources(plane_resources);
drmModeFreeEncoder(encoder);
From a812c83ea9946e08854443e4c1ace8a5cb78eb3a Mon Sep 17 00:00:00 2001
From: Kris Henriksen <github@krishenriksen>
Date: Mon, 1 Feb 2021 02:47:54 +0000
Subject: [PATCH 2/2] added required mode for rockchip
---
src/video/rk.c | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/src/video/rk.c b/src/video/rk.c
index af9451d7..e40f2c60 100644
--- a/src/video/rk.c
+++ b/src/video/rk.c
@@ -36,6 +36,13 @@
#include <xf86drmMode.h>
#include <libdrm/drm_fourcc.h>
+#define DRM_FORMAT_NV12_10 fourcc_code('N', 'A', '1', '2') /* 2x2 subsampled Cr:Cb plane */
+#define DRM_FORMAT_NV21_10 fourcc_code('N', 'A', '2', '1') /* 2x2 subsampled Cb:Cr plane */
+#define DRM_FORMAT_NV16_10 fourcc_code('N', 'A', '1', '6') /* 2x1 subsampled Cr:Cb plane */
+#define DRM_FORMAT_NV61_10 fourcc_code('N', 'A', '6', '1') /* 2x1 subsampled Cb:Cr plane */
+#define DRM_FORMAT_NV24_10 fourcc_code('N', 'A', '2', '4') /* non-subsampled Cr:Cb plane */
+#define DRM_FORMAT_NV42_10 fourcc_code('N', 'A', '4', '2') /* non-subsampled Cb:Cr plane */
+
#include <rockchip/rk_mpi.h>
#include <rga/RgaApi.h>