distribution/packages/games/native/moonlight/patches/RG552/001-rotation.patch
2022-05-28 09:43:16 -07:00

179 lines
5.7 KiB
Diff

--- moonlight-orig/cmake/FindRockchip.cmake 2022-05-26 15:41:01.746182723 -0700
+++ areascout-moonlight/cmake/FindRockchip.cmake 2022-05-26 15:39:28.741230073 -0700
@@ -8,7 +8,13 @@
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 @@
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})
--- moonlight-orig/src/video/rk.c 2022-05-26 15:41:01.750182764 -0700
+++ areascout-moonlight/src/video/rk.c 2022-05-26 15:39:28.749230155 -0700
@@ -37,9 +37,11 @@
#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
@@ -50,6 +52,8 @@
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;
@@ -82,6 +86,7 @@
void *display_thread(void *param) {
+ static int index = 0;
int ret;
while (!frm_eos) {
@@ -98,8 +103,9 @@
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);
@@ -114,10 +120,13 @@
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) {
@@ -141,7 +150,15 @@
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;
@@ -157,6 +174,47 @@
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);
@@ -224,6 +282,15 @@
// 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);
@@ -363,6 +430,10 @@
// 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);
@@ -446,6 +517,8 @@
mpp_destroy(mpi_ctx);
free(pkt_buf);
+ c_RkRgaDeInit();
+
drmModeFreePlane(ovr);
drmModeFreePlaneResources(plane_resources);
drmModeFreeEncoder(encoder);