xref: /OK3568_Linux_fs/external/rockit/mpi/example/mod/test_mpi_rgn.cpp (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1 /*
2  * Copyright 2021 Rockchip Electronics Co. LTD
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17 #undef DBG_MOD_ID
18 #define DBG_MOD_ID       RK_ID_RGN
19 
20 #include <unistd.h>
21 #include <string.h>
22 #include <stdlib.h>
23 #include <pthread.h>
24 
25 #include "rk_debug.h"
26 #include "rk_type.h"
27 #include "rk_mpi_rgn.h"
28 #include "rk_mpi_sys.h"
29 #include "rk_mpi_cal.h"
30 #include "rk_comm_vpss.h"
31 #include "rk_mpi_vpss.h"
32 #include "rk_mpi_mmz.h"
33 
34 #include "test_comm_bmp.h"
35 #include "test_comm_argparse.h"
36 #include "test_comm_utils.h"
37 #include "test_comm_rgn.h"
38 #include "test_comm_venc.h"
39 #include "test_comm_vpss.h"
40 
41 /* PixFormat: big-edian:BGRA8888 => A:bit31~bit24 R:bit23~bit16 G:bit15~bit8 B:bit7~bit0 */
42 const RK_U32 u32BGRA8888ColorTblUser[RGN_CLUT_NUM] = {
43     // transparency/gray/red/earthy yellow /blue
44     0x00ffffff, 0xff5e6060, 0xffe9491e, 0xfff4bc1f, 0xff1ca2dd, 0xff87bd43,
45     0xffff1f1f, 0xff0000af, 0xff0000d7, 0xff0000ff, 0xff005f00, 0xff005f5f,
46     0xff005f87, 0xff005faf, 0xff005fd7, 0xff005fff, 0xff008000, 0xff008080,
47     0xff008700, 0xff00875f, 0xff008787, 0xff0087af, 0xff0087d7, 0xff0087ff,
48     0xff00af00, 0xff00af5f, 0xff00af87, 0xff00afaf, 0xff00afd7, 0xff00afff,
49     0xff00d700, 0xff00d75f, 0xff00d787, 0xff00d7af, 0xff00d7d7, 0xff00d7ff,
50     0xff00ff00, 0xff00ff28, 0xff00ff5f, 0xff00ff87, 0xff00ffaf, 0xff00ffd7,
51     0xff00ffff, 0xff00ffff, 0xff080808, 0xff121212, 0xff1c1c1c, 0xff262626,
52     0xff303030, 0xff3a3a3a, 0xff444444, 0xff4e4e4e, 0xff585858, 0xff5f0000,
53     0xff5f005f, 0xff5f0087, 0xff5f00af, 0xff5f00d7, 0xff5f00ff, 0xff5f5f00,
54     0xff5f5f5f, 0xff5f5f87, 0xff5f5faf, 0xff5f5fd7, 0xff5f5fff, 0xff5f8700,
55     0xff5f875f, 0xff5f8787, 0xff5f87af, 0xff5f87d7, 0xff5f87ff, 0xff5faf00,
56     0xff5faf5f, 0xff5faf87, 0xff5fafaf, 0xff5fafd7, 0xff5fafff, 0xff5fd700,
57     0xff5fd75f, 0xff5fd787, 0xff5fd7af, 0xff5fd7d7, 0xff5fd7ff, 0xff5fff00,
58     0xff5fff5f, 0xff5fff87, 0xff5fffaf, 0xff5fffd7, 0xff5fffff, 0xff626262,
59     0xff6c6c6c, 0xff767676, 0xff800000, 0xff800080, 0xff808000, 0xff808080,
60     0xff808080, 0xff870000, 0xff87005f, 0xff870087, 0xff8700af, 0xff8700d7,
61     0xff8700ff, 0xff875f00, 0xff875f5f, 0xff875f87, 0xff875faf, 0xff875fd7,
62     0xff875fff, 0xff878700, 0xff87875f, 0xff878787, 0xff8787af, 0xff8787d7,
63     0xff8787ff, 0xff87af00, 0xff87af5f, 0xff87af87, 0xff87afaf, 0xff87afd7,
64     0xff87afff, 0xff87d700, 0xff87d75f, 0xff87d787, 0xff87d7af, 0xff87d7d7,
65     0xff87d7ff, 0xff87ff00, 0xff87ff5f, 0xff87ff87, 0xff87ffaf, 0xff87ffd7,
66     0xff87ffff, 0xff8a8a8a, 0xff949494, 0xff9e9e9e, 0xffa8a8a8, 0xffaf0000,
67     0xffaf005f, 0xffaf0087, 0xffaf00af, 0xffaf00d7, 0xffaf00ff, 0xffaf5f00,
68     0xffaf5f5f, 0xffaf5f87, 0xffaf5faf, 0xffaf5fd7, 0xffaf5fff, 0xffaf8700,
69     0xffaf875f, 0xffaf8787, 0xffaf87af, 0xffaf87d7, 0xffaf87ff, 0xffafaf00,
70     0xffafaf5f, 0xffafaf87, 0xffafafaf, 0xffafafd7, 0xffafafff, 0xffafd700,
71     0xffafd75f, 0xffafd787, 0xffafd7af, 0xffafd7d7, 0xffafd7ff, 0xffafff00,
72     0xffafff5f, 0xffafff87, 0xffafffaf, 0xffafffd7, 0xffafffff, 0xffb2b2b2,
73     0xffbcbcbc, 0xffc0c0c0, 0xffc6c6c6, 0xffd0d0d0, 0xffd70000, 0xffd7005f,
74     0xffd70087, 0xffd700af, 0xffd700d7, 0xffd700ff, 0xffd75f00, 0xffd75f5f,
75     0xffd75f87, 0xffd75faf, 0xffd75fd7, 0xffd75fff, 0xffd78700, 0xffd7875f,
76     0xffd78787, 0xffd787af, 0xffd787d7, 0xffd787ff, 0xffd7af00, 0xffd7af5f,
77     0xffd7af87, 0xffd7afaf, 0xffd7afd7, 0xffd7afff, 0xffd7d700, 0xffd7d75f,
78     0xffd7d787, 0xffd7d7af, 0xffd7d7d7, 0xffd7d7ff, 0xffd7ff00, 0xffd7ff5f,
79     0xffd7ff87, 0xffd7ffaf, 0xffd7ffd7, 0xffd7ffff, 0xffdadada, 0xffe4e4e4,
80     0xffeeeeee, 0xffff0000, 0xffff0028, 0xffff005f, 0xffff0087, 0xffff00af,
81     0xffff00d7, 0xffff00ff, 0xffff00ff, 0xffff5f00, 0xffff5f5f, 0xffff5f87,
82     0xffff5faf, 0xffff5fd7, 0xffff5fff, 0xffff8700, 0xffff875f, 0xffff8787,
83     0xffff87af, 0xffff87d7, 0xffff87ff, 0xffffaf00, 0xffffaf5f, 0xffffaf87,
84     0xffffafaf, 0xffffafd7, 0xffffafff, 0xffffd700, 0xffffd75f, 0xffffd787,
85     0xffffd7af, 0xffffd7d7, 0xffffd7ff, 0xffffff00, 0xffffff28, 0xffffff5f,
86     0xffffff87, 0xffffffaf, 0xffffffd7, 0xffffffff,
87 };
88 
89 typedef struct _rkTestRGNCtx {
90     const char *srcFileRawName;
91     const char *srcFileBmpName;
92     const char *dstSaveFileName;
93     RK_S32      s32Operation;
94     RK_S32      s32LoopCount;
95     RK_S32      s32RgnCount;
96     RECT_S      stRegion;
97     RK_U32      u32RawWidth;
98     RK_U32      u32RawHeight;
99     RK_U32      u32RawFormat;
100     RK_U32      u32BmpFormat;
101     RK_BOOL     bRgnQp;
102     RK_U32      u32ClutNum;
103     pthread_t   vencSendFrameTid;
104     pthread_t   vencGetStreamTid;
105     RK_U32      u32AttachMod;
106     RK_U32      u32CoverType;
107 } TEST_RGN_CTX_S;
108 
test_rgn_overlay_process(TEST_RGN_CTX_S * pstRgnCtx,MPP_CHN_S * pstMppChn)109 RK_S32 test_rgn_overlay_process(TEST_RGN_CTX_S *pstRgnCtx, MPP_CHN_S *pstMppChn) {
110     RK_S32          s32Ret       = RK_SUCCESS;
111     RGN_HANDLE      RgnHandle    = 0;
112     VENC_CHN        VencChn      = 0;
113     POINT_S         stPoint      = {0};
114     BITMAP_S        stBitmap;
115     RGN_ATTR_S      stRgnAttr;
116     RGN_CHN_ATTR_S  stRgnChnAttr;
117     VENC_ATTR_S     stVencAttr;
118     RK_BOOL         bShow;
119 
120     /****************************************
121      step 1: create overlay regions
122     ****************************************/
123     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
124         stRgnAttr.enType = OVERLAY_RGN;
125         stRgnAttr.unAttr.stOverlay.enPixelFmt = (PIXEL_FORMAT_E)pstRgnCtx->u32BmpFormat;
126         stRgnAttr.unAttr.stOverlay.stSize.u32Width  = pstRgnCtx->stRegion.u32Width;
127         stRgnAttr.unAttr.stOverlay.stSize.u32Height = pstRgnCtx->stRegion.u32Height;
128         stRgnAttr.unAttr.stOverlay.u32ClutNum = pstRgnCtx->u32ClutNum;
129         if (pstRgnCtx->u32ClutNum)
130             memcpy(stRgnAttr.unAttr.stOverlay.u32Clut, u32BGRA8888ColorTblUser, sizeof(u32BGRA8888ColorTblUser));
131 
132         RgnHandle = i;
133 
134         s32Ret = RK_MPI_RGN_Create(RgnHandle, &stRgnAttr);
135         if (RK_SUCCESS != s32Ret) {
136             RK_LOGE("RK_MPI_RGN_Create (%d) failed with %#x!", RgnHandle, s32Ret);
137             RK_MPI_RGN_Destroy(RgnHandle);
138             return RK_FAILURE;
139         }
140         RK_LOGI("The handle: %d, create success!", RgnHandle);
141     }
142 
143     /*********************************************
144      step 2: display overlay regions to groups
145     *********************************************/
146     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
147         RgnHandle = i;
148 
149         memset(&stRgnChnAttr, 0, sizeof(stRgnChnAttr));
150         stRgnChnAttr.bShow = RK_TRUE;
151         stRgnChnAttr.enType = OVERLAY_RGN;
152         stRgnChnAttr.unChnAttr.stOverlayChn.stPoint.s32X = pstRgnCtx->stRegion.s32X + 48 * i;
153         stRgnChnAttr.unChnAttr.stOverlayChn.stPoint.s32Y = pstRgnCtx->stRegion.s32Y + 48 * i;
154         stRgnChnAttr.unChnAttr.stOverlayChn.u32BgAlpha = 0;
155         stRgnChnAttr.unChnAttr.stOverlayChn.u32FgAlpha = 255;
156         stRgnChnAttr.unChnAttr.stOverlayChn.u32Layer = i;
157         stRgnChnAttr.unChnAttr.stOverlayChn.stQpInfo.bEnable = pstRgnCtx->bRgnQp;
158         stRgnChnAttr.unChnAttr.stOverlayChn.stQpInfo.bForceIntra = RK_TRUE;
159         stRgnChnAttr.unChnAttr.stOverlayChn.stQpInfo.bAbsQp = RK_FALSE;
160         stRgnChnAttr.unChnAttr.stOverlayChn.stQpInfo.s32Qp = -10 * (i + 1);
161         s32Ret = RK_MPI_RGN_AttachToChn(RgnHandle, pstMppChn, &stRgnChnAttr);
162         if (RK_SUCCESS != s32Ret) {
163             RK_LOGE("RK_MPI_RGN_AttachToChn (%d) failed with %#x!", RgnHandle, s32Ret);
164             return RK_FAILURE;
165         }
166     }
167 
168     RK_LOGI("Display region to chn success!");
169     usleep(5000);
170 
171     /*********************************************
172      step 3: show bitmap
173     *********************************************/
174     RK_S64 s64ShowBmpStart = TEST_COMM_GetNowUs();
175     s32Ret = TEST_RGN_LoadBmp(pstRgnCtx->srcFileBmpName, &stBitmap,
176                              (PIXEL_FORMAT_E)pstRgnCtx->u32BmpFormat);
177     if (RK_SUCCESS != s32Ret) {
178         RK_LOGE("Load bmp failed with %#x!", s32Ret);
179         return RK_FAILURE;
180     }
181 
182     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
183         RgnHandle = i;
184 
185         s32Ret = RK_MPI_RGN_SetBitMap(RgnHandle, &stBitmap);
186         if (s32Ret != RK_SUCCESS) {
187             RK_LOGE("RK_MPI_RGN_SetBitMap failed with %#x!", s32Ret);
188             return RK_FAILURE;
189         }
190     }
191 
192     if (RK_NULL != stBitmap.pData) {
193         free(stBitmap.pData);
194         stBitmap.pData = NULL;
195     }
196     RK_S64 s64ShowBmpEnd = TEST_COMM_GetNowUs();
197 
198     RK_LOGI("Handle:%d, space time %lld us, load bmp success!", RgnHandle, s64ShowBmpEnd - s64ShowBmpStart);
199     usleep(1000000);
200 
201     /*********************************************
202      step 4: use update canvas interface
203     *********************************************/
204     s64ShowBmpStart = TEST_COMM_GetNowUs();
205     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
206         RGN_CANVAS_INFO_S stCanvasInfo;
207         RgnHandle = i;
208 
209         memset(&stCanvasInfo, 0, sizeof(RGN_CANVAS_INFO_S));
210 
211         s32Ret = RK_MPI_RGN_GetCanvasInfo(RgnHandle, &stCanvasInfo);
212         if (s32Ret != RK_SUCCESS) {
213             RK_LOGE("RK_MPI_RGN_GetCanvasInfo failed with %#x!", s32Ret);
214             return RK_FAILURE;
215         }
216         memset(reinterpret_cast<void *>(stCanvasInfo.u64VirAddr), 0xff,
217                 stCanvasInfo.u32VirWidth * 16 * (i + 1));
218         s32Ret = RK_MPI_RGN_UpdateCanvas(RgnHandle);
219         if (s32Ret != RK_SUCCESS) {
220             RK_LOGE("RK_MPI_RGN_UpdateCanvas failed with %#x!", s32Ret);
221             return RK_FAILURE;
222         }
223     }
224     s64ShowBmpEnd = TEST_COMM_GetNowUs();
225     RK_LOGI("Handle:%d, space time %lld us, update canvas success!", RgnHandle, s64ShowBmpEnd - s64ShowBmpStart);
226     usleep(1000000);
227 
228     /*********************************************
229      step 5: change overlay regions' position
230     *********************************************/
231     RK_S64 s64ChgPosStart = TEST_COMM_GetNowUs();
232     RgnHandle = 0;
233 
234     stPoint.s32X = 64;
235     stPoint.s32Y = 0;
236     s32Ret = TEST_RGN_ChangePosition(RgnHandle, pstMppChn, stPoint.s32X, stPoint.s32Y);
237     if (RK_SUCCESS != s32Ret) {
238         RK_LOGE("Change region(%d) position failed with %#x!", RgnHandle, s32Ret);
239         return RK_FAILURE;
240     }
241 
242     RK_S64 s64ChgPosEnd = TEST_COMM_GetNowUs();
243 
244     RK_LOGI("Handle:%d, space time %lld us, change point success,new point(x:%d,y:%d)!",
245         RgnHandle, s64ChgPosEnd - s64ChgPosStart, stPoint.s32X, stPoint.s32Y);
246     usleep(5000);
247 
248     /*********************************************
249      step 6: show or hide overlay regions
250     *********************************************/
251     RgnHandle = 0;
252     bShow = RK_FALSE;
253 
254     for (RK_S32 i = 0; i < 4; i++) {
255         s32Ret = TEST_RGN_ShowOrHide(RgnHandle, pstMppChn, bShow);
256         if (RK_SUCCESS != s32Ret) {
257             RK_LOGE("Region(%d) show failed with %#x!", RgnHandle, s32Ret);
258             return RK_FAILURE;
259         }
260         RK_LOGI("Handle:%d, %s osd success", RgnHandle, bShow ? "show" : "hide");
261 
262         bShow = bShow ? RK_FALSE : RK_TRUE;
263 
264         usleep(300000);
265     }
266 
267     /*********************************************
268      step 7: Detach osd from chn
269     *********************************************/
270     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
271         RgnHandle = i;
272         s32Ret = RK_MPI_RGN_DetachFromChn(RgnHandle, pstMppChn);
273         if (RK_SUCCESS != s32Ret) {
274             RK_LOGE("RK_MPI_RGN_DetachFrmChn (%d) failed with %#x!", RgnHandle, s32Ret);
275             return RK_FAILURE;
276         }
277 
278         RK_LOGI("Detach handle:%d from chn success", RgnHandle);
279         usleep(5000);
280     }
281 
282     /*********************************************
283      step 8: destory region
284     *********************************************/
285     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
286         RgnHandle = i;
287         s32Ret = RK_MPI_RGN_Destroy(RgnHandle);
288         if (RK_SUCCESS != s32Ret) {
289             RK_LOGE("RK_MPI_RGN_Destroy [%d] failed with %#x", RgnHandle, s32Ret);
290         }
291         RK_LOGI("Destory handle:%d success", RgnHandle);
292     }
293 
294     return s32Ret;
295 }
296 
test_rgn_cover_process(TEST_RGN_CTX_S * pstRgnCtx,MPP_CHN_S * pstMppChn)297 RK_S32 test_rgn_cover_process(TEST_RGN_CTX_S *pstRgnCtx, MPP_CHN_S *pstMppChn) {
298     RK_S32 s32Ret = RK_SUCCESS;
299     RGN_HANDLE coverHandle;
300     RGN_ATTR_S stCoverAttr;
301     RGN_CHN_ATTR_S stCoverChnAttr;
302 
303     memset(&stCoverAttr, 0, sizeof(stCoverAttr));
304     memset(&stCoverChnAttr, 0, sizeof(RGN_CHN_ATTR_S));
305 
306     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
307         coverHandle = i;
308         stCoverAttr.enType = COVER_RGN;
309         s32Ret = RK_MPI_RGN_Create(coverHandle, &stCoverAttr);
310         if (RK_SUCCESS != s32Ret) {
311             RK_LOGE("failed with %#x!", s32Ret);
312             return RK_FAILURE;
313         }
314 
315         stCoverChnAttr.bShow = RK_TRUE;
316         stCoverChnAttr.enType = COVER_RGN;
317         stCoverChnAttr.unChnAttr.stCoverChn.enCoverType = (RGN_COVER_TYPE_E)pstRgnCtx->u32CoverType;
318         if (pstRgnCtx->u32CoverType == AREA_RECT) {
319             stCoverChnAttr.unChnAttr.stCoverChn.stRect.s32X = pstRgnCtx->stRegion.s32X;
320             stCoverChnAttr.unChnAttr.stCoverChn.stRect.s32Y = pstRgnCtx->stRegion.s32Y;
321             stCoverChnAttr.unChnAttr.stCoverChn.stRect.u32Width = pstRgnCtx->stRegion.u32Width;
322             stCoverChnAttr.unChnAttr.stCoverChn.stRect.u32Height = pstRgnCtx->stRegion.u32Height;
323         } else {
324             stCoverChnAttr.unChnAttr.stCoverChn.stQuadRangle.stPoint[0].s32X =
325                                                             pstRgnCtx->stRegion.s32X;
326             stCoverChnAttr.unChnAttr.stCoverChn.stQuadRangle.stPoint[0].s32Y =
327                                                             pstRgnCtx->stRegion.s32Y;
328             stCoverChnAttr.unChnAttr.stCoverChn.stQuadRangle.stPoint[1].s32X =
329                                                             pstRgnCtx->stRegion.s32X + pstRgnCtx->stRegion.u32Width;
330             stCoverChnAttr.unChnAttr.stCoverChn.stQuadRangle.stPoint[1].s32Y =
331                                                             pstRgnCtx->stRegion.s32Y;
332             stCoverChnAttr.unChnAttr.stCoverChn.stQuadRangle.stPoint[2].s32X =
333                                                             pstRgnCtx->stRegion.s32X + pstRgnCtx->stRegion.u32Width;
334             stCoverChnAttr.unChnAttr.stCoverChn.stQuadRangle.stPoint[2].s32Y =
335                                                             pstRgnCtx->stRegion.s32Y + pstRgnCtx->stRegion.u32Height;
336             stCoverChnAttr.unChnAttr.stCoverChn.stQuadRangle.stPoint[3].s32X =
337                                                             pstRgnCtx->stRegion.s32X + pstRgnCtx->stRegion.u32Width * 2;
338             stCoverChnAttr.unChnAttr.stCoverChn.stQuadRangle.stPoint[3].s32Y =
339                                                             pstRgnCtx->stRegion.s32Y + pstRgnCtx->stRegion.u32Height;
340             stCoverChnAttr.unChnAttr.stCoverChn.stQuadRangle.bSolid = RK_TRUE;
341             stCoverChnAttr.unChnAttr.stCoverChn.stQuadRangle.u32Thick = 1;
342         }
343         stCoverChnAttr.unChnAttr.stCoverChn.u32Color = 0x00f800;
344         stCoverChnAttr.unChnAttr.stCoverChn.u32Layer = i;
345         s32Ret = RK_MPI_RGN_AttachToChn(coverHandle, pstMppChn, &stCoverChnAttr);
346         if (RK_SUCCESS != s32Ret) {
347             RK_LOGE("failed with %#x!", s32Ret);
348             goto AttachCover_failed;
349         }
350     }
351 
352     RK_LOGI("create an cover region and attach it to chn0");
353     usleep(1000000);
354 
355     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
356         coverHandle = i;
357         s32Ret = RK_MPI_RGN_GetDisplayAttr(coverHandle, pstMppChn, &stCoverChnAttr);
358         if (RK_SUCCESS != s32Ret) {
359             RK_LOGE("failed with %#x!", s32Ret);
360             goto exit;
361         }
362         if (pstRgnCtx->u32CoverType == AREA_RECT) {
363             stCoverChnAttr.unChnAttr.stCoverChn.stRect.s32X = 64 * i;
364             stCoverChnAttr.unChnAttr.stCoverChn.stRect.s32Y = 64 * i;
365             stCoverChnAttr.unChnAttr.stCoverChn.stRect.u32Width = 256;
366             stCoverChnAttr.unChnAttr.stCoverChn.stRect.u32Height = 256;
367         }
368         stCoverChnAttr.unChnAttr.stCoverChn.u32Color = 0x0000f8;
369         stCoverChnAttr.unChnAttr.stCoverChn.u32Layer = 1;
370         s32Ret = RK_MPI_RGN_SetDisplayAttr(coverHandle, pstMppChn, &stCoverChnAttr);
371         if (RK_SUCCESS != s32Ret) {
372             RK_LOGE("failed with %#x!", s32Ret);
373             goto exit;
374         }
375 
376         if (pstRgnCtx->u32CoverType == AREA_RECT) {
377             RK_LOGI("resize the cover region %d to <%d, %d, %d, %d>, color<0x%x>",
378                 i,
379                 stCoverChnAttr.unChnAttr.stCoverChn.stRect.s32X,
380                 stCoverChnAttr.unChnAttr.stCoverChn.stRect.s32Y,
381                 stCoverChnAttr.unChnAttr.stCoverChn.stRect.u32Width,
382                 stCoverChnAttr.unChnAttr.stCoverChn.stRect.u32Height,
383                 stCoverChnAttr.unChnAttr.stCoverChn.u32Color);
384         }
385     }
386     usleep(500000);
387 
388     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
389         coverHandle = i;
390         s32Ret = TEST_RGN_ShowOrHide(coverHandle, pstMppChn, RK_FALSE);
391     }
392     RK_LOGI("hide the cover and the overlay success");
393     usleep(500000);
394 
395     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
396         coverHandle = i;
397         s32Ret = TEST_RGN_ShowOrHide(coverHandle, pstMppChn, RK_TRUE);
398         if (RK_SUCCESS != s32Ret) {
399             RK_LOGE("failed with %#x!", s32Ret);
400             goto exit;
401         }
402     }
403 
404     RK_LOGI("show the cover and the overlay success");
405     usleep(500000);
406 
407 exit:
408     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
409         coverHandle = i;
410         RK_MPI_RGN_DetachFromChn(coverHandle, pstMppChn);
411     }
412 
413 AttachCover_failed:
414     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
415         coverHandle = i;
416         RK_MPI_RGN_Destroy(coverHandle);
417     }
418     return s32Ret;
419 }
420 
test_rgn_mosaic_process(TEST_RGN_CTX_S * pstRgnCtx,MPP_CHN_S * pstMppChn)421 RK_S32 test_rgn_mosaic_process(TEST_RGN_CTX_S *pstRgnCtx, MPP_CHN_S *pstMppChn) {
422     RK_S32 s32Ret = RK_SUCCESS;
423     RGN_HANDLE Handle;
424     RGN_ATTR_S stAttr;
425     RGN_CHN_ATTR_S stChnAttr;
426 
427     memset(&stAttr, 0, sizeof(RGN_ATTR_S));
428     memset(&stChnAttr, 0, sizeof(RGN_CHN_ATTR_S));
429 
430     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
431         Handle = i;
432         stAttr.enType = MOSAIC_RGN;
433         s32Ret = RK_MPI_RGN_Create(Handle, &stAttr);
434         if (RK_SUCCESS != s32Ret) {
435             RK_LOGE("failed with %#x!", s32Ret);
436             return RK_FAILURE;
437         }
438 
439         stChnAttr.bShow = RK_TRUE;
440         stChnAttr.enType = MOSAIC_RGN;
441         stChnAttr.unChnAttr.stMosaicChn.stRect.s32X = pstRgnCtx->stRegion.s32X;
442         stChnAttr.unChnAttr.stMosaicChn.stRect.s32Y = pstRgnCtx->stRegion.s32Y;
443         stChnAttr.unChnAttr.stMosaicChn.stRect.u32Width = pstRgnCtx->stRegion.u32Width;
444         stChnAttr.unChnAttr.stMosaicChn.stRect.u32Height = pstRgnCtx->stRegion.u32Height;
445         stChnAttr.unChnAttr.stMosaicChn.enBlkSize = MOSAIC_BLK_SIZE_8;
446         stChnAttr.unChnAttr.stMosaicChn.u32Layer = i;
447         s32Ret = RK_MPI_RGN_AttachToChn(Handle, pstMppChn, &stChnAttr);
448         if (RK_SUCCESS != s32Ret) {
449             RK_LOGE("failed with %#x!", s32Ret);
450             goto AttachCover_failed;
451         }
452     }
453 
454     RK_LOGI("create an cover region and attach it to chn0");
455     usleep(1000000);
456 
457     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
458         Handle = i;
459         RK_S32 s32Ret = TEST_RGN_ChangePosition(Handle, pstMppChn, 64 * i, 64 * i);
460         if (RK_SUCCESS != s32Ret) {
461             RK_LOGE("failed with %#x!", s32Ret);
462             goto exit;
463         }
464 
465         RK_LOGI("move the cover region %d to <%d, %d, %d, %d>, blk size<0x%x>",
466             i,
467             stChnAttr.unChnAttr.stCoverChn.stRect.s32X,
468             stChnAttr.unChnAttr.stCoverChn.stRect.s32Y,
469             stChnAttr.unChnAttr.stCoverChn.stRect.u32Width,
470             stChnAttr.unChnAttr.stCoverChn.stRect.u32Height,
471             stChnAttr.unChnAttr.stMosaicChn.enBlkSize);
472     }
473     usleep(500000);
474 
475     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
476         Handle = i;
477         s32Ret = TEST_RGN_ShowOrHide(Handle, pstMppChn, RK_FALSE);
478         if (RK_SUCCESS != s32Ret) {
479             RK_LOGE("failed with %#x!", s32Ret);
480             goto exit;
481         }
482     }
483     RK_LOGI("hide the cover and the overlay success");
484     usleep(500000);
485 
486     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
487         Handle = i;
488         s32Ret = TEST_RGN_ShowOrHide(Handle, pstMppChn, RK_TRUE);
489         if (RK_SUCCESS != s32Ret) {
490             RK_LOGE("failed with %#x!", s32Ret);
491             goto exit;
492         }
493     }
494 
495     RK_LOGI("show the cover and the overlay success");
496     usleep(500000);
497 
498 exit:
499     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
500         Handle = i;
501         RK_MPI_RGN_DetachFromChn(Handle, pstMppChn);
502     }
503 AttachCover_failed:
504     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
505         Handle = i;
506         RK_MPI_RGN_Destroy(Handle);
507     }
508     return s32Ret;
509 }
510 
test_rgn_draw_line_process(TEST_RGN_CTX_S * pstRgnCtx,MPP_CHN_S * pstMppChn)511 RK_S32 test_rgn_draw_line_process(TEST_RGN_CTX_S *pstRgnCtx, MPP_CHN_S *pstMppChn) {
512     RK_S32 s32Ret = RK_SUCCESS;
513     RGN_HANDLE Handle;
514     RGN_ATTR_S stAttr;
515     RGN_CHN_ATTR_S stChnAttr;
516 
517     memset(&stAttr, 0, sizeof(RGN_ATTR_S));
518     memset(&stChnAttr, 0, sizeof(RGN_CHN_ATTR_S));
519 
520     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
521         Handle = i;
522         stAttr.enType = LINE_RGN;
523         s32Ret = RK_MPI_RGN_Create(Handle, &stAttr);
524         if (RK_SUCCESS != s32Ret) {
525             RK_LOGE("failed with %#x!", s32Ret);
526             return RK_FAILURE;
527         }
528 
529         stChnAttr.bShow = RK_TRUE;
530         stChnAttr.enType = LINE_RGN;
531         stChnAttr.unChnAttr.stLineChn.stStartPoint.s32X = 0;
532         stChnAttr.unChnAttr.stLineChn.stStartPoint.s32Y = 0;
533         stChnAttr.unChnAttr.stLineChn.stEndPoint.s32X = 512;
534         stChnAttr.unChnAttr.stLineChn.stEndPoint.s32Y = 512;
535         stChnAttr.unChnAttr.stLineChn.u32Color = 0x00f800;
536         stChnAttr.unChnAttr.stLineChn.u32Thick = 10;
537         s32Ret = RK_MPI_RGN_AttachToChn(Handle, pstMppChn, &stChnAttr);
538         if (RK_SUCCESS != s32Ret) {
539             RK_LOGE("failed with %#x!", s32Ret);
540             goto AttachCover_failed;
541         }
542     }
543 
544     RK_LOGI("create an cover region and attach it to chn0");
545     usleep(1000000);
546 
547     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
548         Handle = i;
549         s32Ret = TEST_RGN_ShowOrHide(Handle, pstMppChn, RK_FALSE);
550         if (RK_SUCCESS != s32Ret) {
551             RK_LOGE("failed with %#x!", s32Ret);
552             goto exit;
553         }
554     }
555     RK_LOGI("hide the cover and the overlay success");
556     usleep(500000);
557 
558     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
559         Handle = i;
560         s32Ret = TEST_RGN_ShowOrHide(Handle, pstMppChn, RK_TRUE);
561         if (RK_SUCCESS != s32Ret) {
562             RK_LOGE("failed with %#x!", s32Ret);
563             goto exit;
564         }
565     }
566 
567     RK_LOGI("show the cover and the overlay success");
568     usleep(500000);
569 
570 exit:
571     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
572         Handle = i;
573         RK_MPI_RGN_DetachFromChn(Handle, pstMppChn);
574     }
575 
576 AttachCover_failed:
577     for (RK_S32 i = 0; i < pstRgnCtx->s32RgnCount; i++) {
578         Handle = i;
579         RK_MPI_RGN_Destroy(Handle);
580     }
581     return s32Ret;
582 }
583 
584 
unit_test_mpi_rgn_venc(TEST_RGN_CTX_S * pstRgnCtx)585 RK_S32 unit_test_mpi_rgn_venc(TEST_RGN_CTX_S *pstRgnCtx) {
586     RK_S32 s32Ret = RK_SUCCESS;
587     VENC_CHN VencChn = 0;
588     MPP_CHN_S stMppChn;
589     COMMON_TEST_VENC_CTX_S stVencCtx;
590 
591     stMppChn.enModId = RK_ID_VENC;
592     stMppChn.s32DevId = 0;
593     stMppChn.s32ChnId = VencChn;
594 
595     memset(&stVencCtx, 0, sizeof(COMMON_TEST_VENC_CTX_S));
596 
597     stVencCtx.u32Width = pstRgnCtx->u32RawWidth;
598     stVencCtx.u32Height = pstRgnCtx->u32RawHeight;
599     stVencCtx.enPixFmt = RK_FMT_YUV420SP;
600     stVencCtx.enType = RK_VIDEO_ID_AVC;
601     stVencCtx.VencChn = VencChn;
602     stVencCtx.u32StreamBufCnt = 4;
603     stVencCtx.pSrcFramePath = pstRgnCtx->srcFileRawName;
604     stVencCtx.pSaveStreamPath = pstRgnCtx->dstSaveFileName;
605 
606     s32Ret = TEST_VENC_Start(&stVencCtx);
607     if (s32Ret != RK_SUCCESS) {
608         return s32Ret;
609     }
610 
611     switch (pstRgnCtx->s32Operation) {
612       case OVERLAY_RGN: {
613         s32Ret = test_rgn_overlay_process(pstRgnCtx, &stMppChn);
614       } break;
615       case COVER_RGN: {
616         s32Ret = test_rgn_cover_process(pstRgnCtx, &stMppChn);
617       } break;
618       default:
619         RK_LOGE("unsupport operation %d.", pstRgnCtx->s32Operation);
620         s32Ret = RK_FAILURE;
621     }
622     if (s32Ret != RK_SUCCESS) {
623         return s32Ret;
624     }
625 
626     s32Ret = TEST_VENC_Stop(VencChn);
627     if (s32Ret != RK_SUCCESS) {
628         return s32Ret;
629     }
630 
631     return s32Ret;
632 }
633 
unit_test_mpi_rgn_vpss(TEST_RGN_CTX_S * pstRgnCtx)634 RK_S32 unit_test_mpi_rgn_vpss(TEST_RGN_CTX_S *pstRgnCtx) {
635     RK_S32 s32Ret = RK_SUCCESS;
636     VPSS_GRP VpssGrp = 0;
637     MPP_CHN_S stMppChn;
638     VPSS_GRP_ATTR_S stGrpAttr;
639     VPSS_CHN_ATTR_S stChnAttr;
640     TEST_VPSS_PROC_CTX_S stProcCtx;
641 
642     stMppChn.enModId = RK_ID_VPSS;
643     stMppChn.s32DevId = VpssGrp;
644     stMppChn.s32ChnId = 0;
645 
646     memset(&stGrpAttr, 0, sizeof(VPSS_GRP_ATTR_S));
647     memset(&stChnAttr, 0, sizeof(VPSS_CHN_ATTR_S));
648     memset(&stProcCtx, 0, sizeof(TEST_VPSS_PROC_CTX_S));
649 
650     stGrpAttr.u32MaxW = 4096;
651     stGrpAttr.u32MaxH = 4096;
652     stGrpAttr.enPixelFormat = (PIXEL_FORMAT_E)pstRgnCtx->u32RawFormat;
653     stGrpAttr.enCompressMode = COMPRESS_MODE_NONE;
654     stGrpAttr.stFrameRate.s32SrcFrameRate = -1;
655     stGrpAttr.stFrameRate.s32DstFrameRate = -1;
656     stChnAttr.enChnMode = VPSS_CHN_MODE_USER;
657     stChnAttr.enCompressMode = COMPRESS_MODE_NONE;
658     stChnAttr.enDynamicRange = DYNAMIC_RANGE_SDR8;
659     stChnAttr.enPixelFormat = (PIXEL_FORMAT_E)pstRgnCtx->u32RawFormat;
660     stChnAttr.stFrameRate.s32SrcFrameRate = -1;
661     stChnAttr.stFrameRate.s32DstFrameRate = -1;
662     stChnAttr.u32Width = pstRgnCtx->u32RawWidth;
663     stChnAttr.u32Height = pstRgnCtx->u32RawHeight;
664     stChnAttr.u32Depth = 8;
665     s32Ret = TEST_VPSS_Start(VpssGrp, 1, &stGrpAttr, &stChnAttr);
666     if (s32Ret != RK_SUCCESS) {
667         return s32Ret;
668     }
669 
670     stProcCtx.srcFileName = pstRgnCtx->srcFileRawName;
671     stProcCtx.dstSaveFileName = pstRgnCtx->dstSaveFileName;
672     stProcCtx.u32RawWidth = pstRgnCtx->u32RawWidth;
673     stProcCtx.u32RawHeight = pstRgnCtx->u32RawHeight;
674     stProcCtx.u32RawPixelFmt = pstRgnCtx->u32RawFormat;
675     stProcCtx.u32SendFrameRate = 30;
676     s32Ret = TEST_VPSS_StartProc(VpssGrp, 1, &stProcCtx);
677     if (s32Ret != RK_SUCCESS) {
678         return s32Ret;
679     }
680 
681     switch (pstRgnCtx->s32Operation) {
682       case OVERLAY_RGN: {
683         s32Ret = test_rgn_overlay_process(pstRgnCtx, &stMppChn);
684       } break;
685       case COVER_RGN: {
686         s32Ret = test_rgn_cover_process(pstRgnCtx, &stMppChn);
687       } break;
688       case MOSAIC_RGN: {
689         s32Ret = test_rgn_mosaic_process(pstRgnCtx, &stMppChn);
690       } break;
691       case LINE_RGN: {
692         s32Ret = test_rgn_draw_line_process(pstRgnCtx, &stMppChn);
693       } break;
694       default:
695         RK_LOGE("unsupport operation %d.", pstRgnCtx->s32Operation);
696         s32Ret = RK_FAILURE;
697     }
698     if (s32Ret != RK_SUCCESS) {
699         return s32Ret;
700     }
701 
702     s32Ret = TEST_VPSS_StopProc(VpssGrp);
703     if (s32Ret != RK_SUCCESS) {
704         return s32Ret;
705     }
706     s32Ret = TEST_VPSS_Stop(VpssGrp, 1);
707     if (s32Ret != RK_SUCCESS) {
708         return s32Ret;
709     }
710 
711     return s32Ret;
712 }
713 
714 
mpi_rgn_test_show_options(const TEST_RGN_CTX_S * ctx)715 static void mpi_rgn_test_show_options(const TEST_RGN_CTX_S *ctx) {
716     RK_PRINT("cmd parse result:\n");
717     RK_PRINT("rgn input raw file name   : %s\n", ctx->srcFileRawName);
718     RK_PRINT("rgn input bmp file name   : %s\n", ctx->srcFileBmpName);
719     RK_PRINT("rgn output file name      : %s\n", ctx->dstSaveFileName);
720     RK_PRINT("rgn count                 : %d\n", ctx->s32RgnCount);
721     RK_PRINT("rgn operation             : %d\n", ctx->s32Operation);
722     RK_PRINT("rgn region pos x          : %d\n", ctx->stRegion.s32X);
723     RK_PRINT("rgn region pos y          : %d\n", ctx->stRegion.s32Y);
724     RK_PRINT("rgn canvas width          : %d\n", ctx->stRegion.u32Width);
725     RK_PRINT("rgn canvas height         : %d\n", ctx->stRegion.u32Height);
726     RK_PRINT("rgn raw width             : %d\n", ctx->u32RawWidth);
727     RK_PRINT("rgn raw height            : %d\n", ctx->u32RawHeight);
728     RK_PRINT("clut num                  : %d\n", ctx->u32ClutNum);
729 }
730 
731 static const char *const usages[] = {
732     "./rk_mpi_rgn_test [-w RECT_W] [-h RECT_H]...",
733     NULL,
734 };
735 
main(int argc,const char ** argv)736 int main(int argc, const char **argv) {
737     RK_S32 s32Ret = RK_SUCCESS;
738     TEST_RGN_CTX_S stRgnCtx;
739 
740     memset(&stRgnCtx, 0, sizeof(TEST_RGN_CTX_S));
741     stRgnCtx.s32Operation   = OVERLAY_RGN;
742     stRgnCtx.s32LoopCount   = 1;
743     stRgnCtx.s32RgnCount    = 1;
744     stRgnCtx.u32BmpFormat   = RK_FMT_BGRA5551;
745     stRgnCtx.bRgnQp         = RK_FALSE;
746     stRgnCtx.u32RawFormat   = RK_FMT_YUV420SP;
747     stRgnCtx.u32AttachMod   = RK_ID_VENC;
748     stRgnCtx.u32CoverType   = AREA_RECT;
749 
750     struct argparse_option options[] = {
751         OPT_HELP(),
752         OPT_GROUP("basic options:"),
753         OPT_STRING('i', "input_raw_name", &(stRgnCtx.srcFileRawName),
754                     "input raw data file name. default(RK_NULL)", NULL, 0, 0),
755         OPT_STRING('\0', "input_bmp_name", &(stRgnCtx.srcFileBmpName),
756                     "input bmp data file name. <required>", NULL, 0, 0),
757         OPT_STRING('o', "output_name", &(stRgnCtx.dstSaveFileName),
758                     "output stream file name. default(RK_NULL).", NULL, 0, 0),
759         OPT_INTEGER('r', "rgn_count", &(stRgnCtx.s32RgnCount),
760                     "the number of rgn handle. default(1).", NULL, 0, 0),
761         OPT_INTEGER('p', "operation", &(stRgnCtx.s32Operation),
762                     "RGN operation. default(0). 0: overlay. 1: cover. 2: mosaic. 3: line", NULL, 0, 0),
763         OPT_INTEGER('x', "rect_x", &(stRgnCtx.stRegion.s32X),
764                     "RGN region pos x. default(0).", NULL, 0, 0),
765         OPT_INTEGER('y', "rect_y", &(stRgnCtx.stRegion.s32Y),
766                     "RGN region pos x. default(0).", NULL, 0, 0),
767         OPT_INTEGER('w', "bmp_w", &(stRgnCtx.stRegion.u32Width),
768                     "bmp width. default(0). <required>", NULL, 0, 0),
769         OPT_INTEGER('h', "bmp_h", &(stRgnCtx.stRegion.u32Height),
770                     "bmp height. default(0). <required>", NULL, 0, 0),
771         OPT_INTEGER('q', "rgn_qp", &(stRgnCtx.bRgnQp),
772                     "rgn roi qp. default(0). ", NULL, 0, 0),
773         OPT_INTEGER('W', "raw_w", &(stRgnCtx.u32RawWidth),
774                     "raw width. default(0). <required>", NULL, 0, 0),
775         OPT_INTEGER('H', "raw_h", &(stRgnCtx.u32RawHeight),
776                     "raw height. default(0). <required>", NULL, 0, 0),
777         OPT_INTEGER('F', "raw_fmt", &(stRgnCtx.u32RawFormat),
778                     "raw pixel format. default(0). 0: NV12", NULL, 0, 0),
779         OPT_INTEGER('f', "format", &(stRgnCtx.u32BmpFormat),
780                     "bmp pixel format. default(65557). 65546: ARGB1555, 65557: BGRA5551", NULL, 0, 0),
781         OPT_INTEGER('\0', "clut_num", &(stRgnCtx.u32ClutNum),
782                     "set color loop up table num. default(0). range[0, 255].", NULL, 0, 0),
783         OPT_INTEGER('\0', "mod", &(stRgnCtx.u32AttachMod),
784                     "attach module. default(4), 4: VENC, 6: VPSS"),
785         OPT_INTEGER('\0', "cover_type", &(stRgnCtx.u32CoverType),
786                     "cover type. default(0), 0: rect, 1: quad"),
787         OPT_END(),
788     };
789 
790     struct argparse argparse;
791     argparse_init(&argparse, options, usages, 0);
792     argparse_describe(&argparse, "\nselect a test case to run.",
793                                  "\nuse --help for details.");
794 
795     argc = argparse_parse(&argparse, argc, argv);
796     mpi_rgn_test_show_options(&stRgnCtx);
797 
798     if (stRgnCtx.stRegion.u32Width <= 0 ||
799           stRgnCtx.stRegion.u32Height <= 0 ||
800           stRgnCtx.u32RawWidth <= 0 ||
801           stRgnCtx.u32RawHeight <= 0 ||
802           stRgnCtx.srcFileBmpName == RK_NULL) {
803         argparse_usage(&argparse);
804         return RK_FAILURE;
805     }
806 
807     s32Ret = RK_MPI_SYS_Init();
808     if (s32Ret != RK_SUCCESS) {
809         return s32Ret;
810     }
811 
812     switch (stRgnCtx.u32AttachMod) {
813       case RK_ID_VENC: {
814         s32Ret = unit_test_mpi_rgn_venc(&stRgnCtx);
815       } break;
816       case RK_ID_VPSS: {
817         s32Ret = unit_test_mpi_rgn_vpss(&stRgnCtx);
818       } break;
819       default:
820       break;
821     }
822 
823     if (s32Ret != RK_SUCCESS) {
824         goto __FAILED;
825     }
826 
827     s32Ret = RK_MPI_SYS_Exit();
828     if (s32Ret != RK_SUCCESS) {
829         return s32Ret;
830     }
831     RK_LOGI("test running ok.");
832     return RK_SUCCESS;
833 
834 __FAILED:
835     RK_MPI_SYS_Exit();
836     RK_LOGE("test running failed!");
837     return s32Ret;
838 }
839