diff --git a/middleware/v2/include/cvi_gdc.h b/middleware/v2/include/cvi_gdc.h index fc4fd1fbd..6012e2210 100644 --- a/middleware/v2/include/cvi_gdc.h +++ b/middleware/v2/include/cvi_gdc.h @@ -154,9 +154,10 @@ CVI_S32 CVI_GDC_DumpMesh(MESH_DUMP_ATTR_S *pMeshDumpAttr); * @brief load mesh for GDC, mesh data is load from user * * @param pMeshDumpAttr(In), mesh dump attribute + * @param pstLDCAttr(In), LDC_ATTR_S * @return CVI_S32 Return CVI_SUCCESS if succeed */ -CVI_S32 CVI_GDC_LoadMesh(MESH_DUMP_ATTR_S *pMeshDumpAttr); +CVI_S32 CVI_GDC_LoadMesh(MESH_DUMP_ATTR_S *pMeshDumpAttr, const LDC_ATTR_S *pstLDCAttr); #ifdef __cplusplus #if __cplusplus } diff --git a/middleware/v2/include/cvi_sns_ctrl.h b/middleware/v2/include/cvi_sns_ctrl.h index 35ed8083b..26707420a 100644 --- a/middleware/v2/include/cvi_sns_ctrl.h +++ b/middleware/v2/include/cvi_sns_ctrl.h @@ -181,6 +181,7 @@ extern ISP_SNS_OBJ_S stSnsSC3332_Obj; extern ISP_SNS_OBJ_S stSnsSC3335_Obj; extern ISP_SNS_OBJ_S stSnsSC3335_Slave_Obj; extern ISP_SNS_OBJ_S stSnsSC3336_Obj; +extern ISP_SNS_OBJ_S stSnsSC3336_1L_Obj; extern ISP_SNS_OBJ_S stSnsSC3336P_Obj; extern ISP_SNS_OBJ_S stSnsSC2331_1L_Obj; extern ISP_SNS_OBJ_S stSnsSC2331_1L_Slave_Obj; diff --git a/middleware/v2/include/cvi_sys.h b/middleware/v2/include/cvi_sys.h index 59ac45990..5a920fadc 100644 --- a/middleware/v2/include/cvi_sys.h +++ b/middleware/v2/include/cvi_sys.h @@ -34,6 +34,13 @@ extern "C" { */ CVI_S32 CVI_SYS_Init(void); +/** + * @brief To check is SYS initialized. + * + * @return CVI_S32 Return CVI_TRUE if initialized. + */ +CVI_S32 CVI_SYS_IsInited(void); + /** * @brief system exit. * diff --git a/middleware/v2/include/cvi_vb.h b/middleware/v2/include/cvi_vb.h index e1c72d4f3..e34c81161 100644 --- a/middleware/v2/include/cvi_vb.h +++ b/middleware/v2/include/cvi_vb.h @@ -32,6 +32,13 @@ extern "C"{ */ CVI_S32 CVI_VB_Init(void); +/** + * @brief To check is VB initialized. + * + * @return CVI_S32 Return CVI_TRUE if initialized. + */ +CVI_S32 CVI_VB_IsInited(void); + /** * @brief VB exit. * diff --git a/middleware/v2/modules/sys/include/vb_ioctl.h b/middleware/v2/modules/sys/include/vb_ioctl.h index e2f3f9df8..bbd3f1627 100644 --- a/middleware/v2/modules/sys/include/vb_ioctl.h +++ b/middleware/v2/modules/sys/include/vb_ioctl.h @@ -21,5 +21,6 @@ int vb_ioctl_release_block(int fd, VB_BLK blk); int vb_ioctl_get_pool_max_cnt(int fd, CVI_U32 *vb_max_pools); int vb_ioctl_print_pool(int fd, VB_POOL poolId); int vb_ioctl_unit_test(int fd, CVI_U32 op); +int vb_ioctl_get_vb_init(int fd, CVI_U32 *val); #endif // MODULES_VB_IOCTL_H_ diff --git a/middleware/v2/modules/sys/src/cvi_sys.c b/middleware/v2/modules/sys/src/cvi_sys.c index 2d99cf240..963a89916 100644 --- a/middleware/v2/modules/sys/src/cvi_sys.c +++ b/middleware/v2/modules/sys/src/cvi_sys.c @@ -298,6 +298,28 @@ CVI_S32 CVI_SYS_Init(void) return s32ret; } +CVI_S32 CVI_SYS_IsInited(void) +{ + CVI_S32 s32ret = CVI_SUCCESS, _sys_fd = -1; + CVI_U32 sys_init = 0; + + _sys_fd = get_sys_fd(); + if (_sys_fd == -1) { + CVI_TRACE_VB(CVI_DBG_ERR, "get_sys_fd failed.\n"); + return CVI_FALSE; + } + + sys_get_sys_init(_sys_fd, &sys_init); + if (s32ret != CVI_SUCCESS) { + CVI_TRACE_VB(CVI_DBG_ERR, "sys_get_sys_init failed.\n"); + return CVI_FALSE; + } + + if (sys_init == 0) + return CVI_FALSE; + else return CVI_TRUE; +} + CVI_S32 CVI_SYS_Exit(void) { CVI_S32 s32ret = CVI_SUCCESS, _sys_fd = -1; diff --git a/middleware/v2/modules/sys/src/cvi_vb.c b/middleware/v2/modules/sys/src/cvi_vb.c index 7ae2e5bcc..b20f6a7eb 100644 --- a/middleware/v2/modules/sys/src/cvi_vb.c +++ b/middleware/v2/modules/sys/src/cvi_vb.c @@ -216,6 +216,28 @@ CVI_S32 CVI_VB_Init(void) return CVI_SUCCESS; } +CVI_S32 CVI_VB_IsInited(void) +{ + CVI_S32 s32ret = CVI_SUCCESS, _vb_fd = -1; + CVI_U32 vb_init = 0; + + _vb_fd = get_base_fd(); + if (_vb_fd == -1) { + CVI_TRACE_VB(CVI_DBG_ERR, "get_base_fd failed.\n"); + return CVI_FALSE; + } + + s32ret = vb_ioctl_get_vb_init(_vb_fd, &vb_init); + if (s32ret != CVI_SUCCESS) { + CVI_TRACE_VB(CVI_DBG_ERR, "vb_ioctl_get_vb_init failed.\n"); + return CVI_FALSE; + } + + if (vb_init == 0) + return CVI_FALSE; + else return CVI_TRUE; +} + CVI_S32 CVI_VB_Exit(void) { CVI_S32 s32Ret, fd; @@ -325,8 +347,7 @@ CVI_S32 CVI_VB_SetConfig(const VB_CONFIG_S *pstVbConfig) CVI_U32 i; MOD_CHECK_NULL_PTR(CVI_ID_VB, pstVbConfig); - if (pstVbConfig->u32MaxPoolCnt > VB_COMM_POOL_MAX_CNT - || pstVbConfig->u32MaxPoolCnt == 0) { + if (pstVbConfig->u32MaxPoolCnt > VB_COMM_POOL_MAX_CNT) { CVI_TRACE_VB(CVI_DBG_ERR, "Invalid vb u32MaxPoolCnt(%d)\n", pstVbConfig->u32MaxPoolCnt); return CVI_ERR_VB_ILLEGAL_PARAM; diff --git a/middleware/v2/modules/sys/src/vb_ioctl.c b/middleware/v2/modules/sys/src/vb_ioctl.c index 4af30675a..d845f18f0 100644 --- a/middleware/v2/modules/sys/src/vb_ioctl.c +++ b/middleware/v2/modules/sys/src/vb_ioctl.c @@ -139,3 +139,8 @@ int vb_ioctl_unit_test(int fd, CVI_U32 op) { VB_CTRL_S_VALUE(fd, op, VB_IOCTL_UNIT_TEST); } + +int vb_ioctl_get_vb_init(int fd, CVI_U32 *val) +{ + VB_CTRL_G_VALUE(fd, val, VB_IOCTL_GET_VB_INIT); +} \ No newline at end of file diff --git a/middleware/v2/modules/vpu/include/grid_info.h b/middleware/v2/modules/vpu/include/grid_info.h new file mode 100644 index 000000000..ad1828de2 --- /dev/null +++ b/middleware/v2/modules/vpu/include/grid_info.h @@ -0,0 +1,55 @@ +#ifndef __GRID_INFO_H__ +#define __GRID_INFO_H__ + +#include +#include + +#ifdef __cplusplus +#if __cplusplus + extern "C"{ +#endif +#endif /* End of #ifdef __cplusplus */ + +typedef struct _MESH_DATA_ALL_S { + char grid_name[64]; + bool balloc; + int num_pairs, imgw, imgh, node_index; + int *pgrid_src, *pgrid_dst; + int *pmesh_src, *pmesh_dst; + int *pnode_src, *pnode_dst; + int mesh_w; // unit: pixel + int mesh_h; // unit: pixel + int mesh_horcnt; // unit: mesh_w + int mesh_vercnt; // unit: mesh_h + int unit_rx; // unit: mesh_w + int unit_ry; // unit: mesh_h + //int unit_ex; // = rx + mesh_horcnt - 1 + //int unit_ey; // = ry + mesh_vercnt - 1 + int _nbr_mesh_x, _nbr_mesh_y; + bool _bhomo; + float _homography[10]; + int corners[10]; + float *_pmapx, *_pmapy; +} MESH_DATA_ALL_S; + +#define SAFE_FREE_POINTER(ptr) \ + do { \ + if (ptr != NULL) { \ + free(ptr); \ + ptr = NULL; \ + } \ + } while (0) + +typedef MESH_DATA_ALL_S meshdata_all; + +int load_meshdata(const char *path, MESH_DATA_ALL_S *pmeshdata, const char *bindName); + +int free_cur_meshdata(MESH_DATA_ALL_S *pmeshdata); + +#ifdef __cplusplus +#if __cplusplus + } +#endif +#endif /* End of #ifdef __cplusplus */ + +#endif /* __GRID_INFO_H__ */ diff --git a/middleware/v2/modules/vpu/src/cvi_gdc_1822.c b/middleware/v2/modules/vpu/src/cvi_gdc_1822.c index 419cd1a28..f44820161 100644 --- a/middleware/v2/modules/vpu/src/cvi_gdc_1822.c +++ b/middleware/v2/modules/vpu/src/cvi_gdc_1822.c @@ -339,6 +339,7 @@ CVI_S32 CVI_GDC_GenLDCMesh(CVI_U32 u32Width, CVI_U32 u32Height, const LDC_ATTR_S CVI_TRACE_GDC(CVI_DBG_ERR, " Can't acquire memory for LDC mesh.\n"); return CVI_ERR_GDC_NOMEM; } + memset(vaddr, 0 , mesh_size); if (mesh_gen_ldc(in_size, out_size, pstLDCAttr, paddr, vaddr, enRotation) != CVI_SUCCESS) { CVI_SYS_IonFree(paddr, vaddr); @@ -387,6 +388,7 @@ CVI_S32 CVI_GDC_LoadLDCMesh(CVI_U32 u32Width, CVI_U32 u32Height, const char *fil CVI_TRACE_GDC(CVI_DBG_ERR, "Can't acquire memory for mesh.\n"); return CVI_ERR_GDC_NOMEM; } + memset(vaddr, 0 , mesh_size); FILE *fp = fopen(fileNname, "rb"); if (!fp) { @@ -553,7 +555,7 @@ CVI_S32 CVI_GDC_DumpMesh(MESH_DUMP_ATTR_S *pMeshDumpAttr) return CVI_SUCCESS; } -CVI_S32 CVI_GDC_LoadMesh(MESH_DUMP_ATTR_S *pMeshDumpAttr) +CVI_S32 CVI_GDC_LoadMesh(MESH_DUMP_ATTR_S *pMeshDumpAttr, const LDC_ATTR_S *pstLDCAttr) { MOD_CHECK_NULL_PTR(CVI_ID_GDC, pMeshDumpAttr); @@ -628,6 +630,7 @@ CVI_S32 CVI_GDC_LoadMesh(MESH_DUMP_ATTR_S *pMeshDumpAttr) fclose(fp); return CVI_ERR_VPSS_NOMEM; } + memset(virMesh, 0 , mesh_size); CVI_TRACE_GDC(CVI_DBG_DEBUG, "load mesh size:%d, mesh phy addr:%#"PRIx64", vir addr:%p.\n", mesh_size, phyMesh, virMesh); @@ -647,7 +650,7 @@ CVI_S32 CVI_GDC_LoadMesh(MESH_DUMP_ATTR_S *pMeshDumpAttr) vi_cfg.ViChn = viChn; vi_cfg.enRotation = ROTATION_0; - //vi_cfg.stLDCAttr = *pstLDCAttr; + vi_cfg.stLDCAttr.stAttr = *pstLDCAttr; vi_cfg.stLDCAttr.bEnable = CVI_TRUE; vi_cfg.meshHandle = pmesh->paddr; if (vi_sdk_set_chn_ldc(fd, &vi_cfg) != CVI_SUCCESS) { @@ -665,7 +668,7 @@ CVI_S32 CVI_GDC_LoadMesh(MESH_DUMP_ATTR_S *pMeshDumpAttr) vpss_cfg.VpssGrp = vpssGrp; vpss_cfg.VpssChn = vpssChn; vpss_cfg.enRotation = ROTATION_0; - //vpss_cfg.stLDCAttr = *pstLDCAttr; + vpss_cfg.stLDCAttr.stAttr = *pstLDCAttr; vpss_cfg.stLDCAttr.bEnable = CVI_TRUE; vpss_cfg.meshHandle = pmesh->paddr; if (vpss_set_chn_ldc(fd, &vpss_cfg) != CVI_SUCCESS) { diff --git a/middleware/v2/modules/vpu/src/gdc_mesh_1822.c b/middleware/v2/modules/vpu/src/gdc_mesh_1822.c index cbd5baab0..34f320ff4 100644 --- a/middleware/v2/modules/vpu/src/gdc_mesh_1822.c +++ b/middleware/v2/modules/vpu/src/gdc_mesh_1822.c @@ -8,9 +8,9 @@ #include #if !(defined(__CV181X__) || defined(__CV180X__)) -#include "cvi_common.h" +#include "linux/cvi_common.h" #include "cvi_math.h" -#include "cvi_comm_video.h" +#include "linux/cvi_comm_video.h" #endif #include "cvi_base.h" @@ -18,6 +18,7 @@ #include "cvi_sys.h" #include "cvi_gdc.h" #include "gdc_mesh.h" +#include "grid_info.h" #define TILESIZE 64 // HW: data Tile Size #define HW_MESH_SIZE 8 @@ -41,7 +42,9 @@ #define minmax(a, b, c) (((a) < (b)) ? (b):((a) > (c)) ? (c) : (a)) -// #define SAVE_MESH_TBL_FILE +meshdata_all gdc_meshdata; + +//#define SAVE_MESH_TBL_FILE // #define ENABLE_PROFILE typedef struct { @@ -92,34 +95,34 @@ typedef struct LDC_ATTR { int InRadius; // input fisheye radius in pixels. // frame-based dst mesh info. maximum num=128*28 = 16384 meshes. - MESH_STRUCT DstRgnMeshInfo[MAX_FRAME_MESH_NUM]; + MESH_STRUCT *DstRgnMeshInfo; // frame-based src mesh info. - MESH_STRUCT SrcRgnMeshInfo[MAX_FRAME_MESH_NUM]; + MESH_STRUCT *SrcRgnMeshInfo; // frame-based dst mesh info. maximum num=128*28 = 16384 meshes. - MESH_STRUCT DstRgnMeshInfoExt[9 * MAX_FRAME_MESH_NUM]; + MESH_STRUCT *DstRgnMeshInfoExt; // frame-based src mesh info. - MESH_STRUCT SrcRgnMeshInfoExt[9 * MAX_FRAME_MESH_NUM]; + MESH_STRUCT *SrcRgnMeshInfoExt; // frame-based dst mesh info. maximum num=128*28 = 16384 meshes. - MESH_STRUCT DstRgnMeshInfoExt2ND[9 * MAX_FRAME_MESH_NUM]; + MESH_STRUCT *DstRgnMeshInfoExt2ND; // frame-based src mesh info. - MESH_STRUCT SrcRgnMeshInfoExt2ND[9 * MAX_FRAME_MESH_NUM]; + MESH_STRUCT *SrcRgnMeshInfoExt2ND; // frame-based dst mesh info. maximum num=128*28 = 16384 meshes. - MESH_STRUCT DstRgnMeshInfo_1st[MAX_FRAME_MESH_NUM]; + MESH_STRUCT *DstRgnMeshInfo_1st; // frame-based src mesh info. - MESH_STRUCT SrcRgnMeshInfo_1st[MAX_FRAME_MESH_NUM]; + MESH_STRUCT *SrcRgnMeshInfo_1st; // frame-based dst mesh info. maximum num=128*28 = 16384 meshes. - MESH_STRUCT DstRgnMeshInfo_2nd[MAX_FRAME_MESH_NUM]; + MESH_STRUCT *DstRgnMeshInfo_2nd; // frame-based src mesh info. - MESH_STRUCT SrcRgnMeshInfo_2nd[MAX_FRAME_MESH_NUM]; + MESH_STRUCT *SrcRgnMeshInfo_2nd; // How many tile is sliced in a frame horizontally. int SliceX_Num; @@ -154,16 +157,16 @@ typedef struct LDC_RGN_ATTR { int RegionValid; // label valid/ invalid for each region // initial buffer to store destination mesh info. max: 32*32 - MESH_STRUCT DstRgnMeshInfo[MAX_FRAME_MESH_NUM]; + MESH_STRUCT *DstRgnMeshInfo; // extend to 3x3 range. - MESH_STRUCT DstRgnMeshInfoExt[9 * MAX_FRAME_MESH_NUM]; + MESH_STRUCT *DstRgnMeshInfoExt; // initial buffer to store source mesh info - MESH_STRUCT SrcRgnMeshInfo[MAX_FRAME_MESH_NUM]; + MESH_STRUCT *SrcRgnMeshInfo; // extend to 3x3 range. - MESH_STRUCT SrcRgnMeshInfoExt[9 * MAX_FRAME_MESH_NUM]; + MESH_STRUCT *SrcRgnMeshInfoExt; } LDC_RGN_ATTR; typedef struct Vector2D { @@ -372,10 +375,12 @@ static void save_2nd_src_mesh_table(int num_tiley_s2, int num_tilex_s2, if (fp2x_bin) { size_t wr_size = fwrite(src_2nd_list, mesh_2nd_size, 1, fp2x_bin); - if (wr_size != mesh_2nd_size) + if (wr_size != mesh_2nd_size) { CVI_TRACE_GDC(CVI_DBG_ERR, "2nd src mesh, fwrite %d, only %d succeed\n", mesh_2nd_size, wr_size); + } + fclose(fp2x_bin); } @@ -390,12 +395,12 @@ static void save_2nd_src_mesh_table(int num_tiley_s2, int num_tilex_s2, } } -static void save_mesh_info(LDC_ATTR *cfg) +static void save_mesh_info(LDC_ATTR *cfg, int max_frame_mesh_num) { FILE *fpsrc = fopen("mesh_frm_src.txt", "w"); FILE *fpdst = fopen("mesh_frm_dst.txt", "w"); - for (int meshidx = 0; meshidx < 9 * MAX_FRAME_MESH_NUM; meshidx++) { + for (int meshidx = 0; meshidx < 9 * max_frame_mesh_num; meshidx++) { fprintf(fpsrc, "meshidx = %d\n", meshidx); fprintf(fpdst, "meshidx = %d\n", meshidx); @@ -512,10 +517,12 @@ static CVI_S32 convert_1st_src_mesh_table(int num_tiley_s1, int num_tilex_s1, if (fp1x_bin) { size_t wr_size = fwrite(src_1st_list_1d, mesh_1st_size, 1, fp1x_bin); - if (wr_size != mesh_1st_size) + if (wr_size != mesh_1st_size) { CVI_TRACE_GDC(CVI_DBG_DEBUG, "1st src mesh, fwrite %d, only %d succeed\n", mesh_1st_size, wr_size); + } + fclose(fp1x_bin); } #endif @@ -523,10 +530,141 @@ static CVI_S32 convert_1st_src_mesh_table(int num_tiley_s1, int num_tilex_s1, return CVI_SUCCESS; } -static CVI_S32 _get_1st_src_midxy(int num_tilex_s1, - LDC_ATTR *cfg, COORD2D_INT_HW *src_1st_list, int tidx, int tidy) +static CVI_S32 _get_src_1st_list(int num_tilex_s1, const LDC_ATTR_S *pstLDCAttr, + LDC_ATTR *cfg, COORD2D_INT *cur_dst_mesh, int tidx, int tidy, int midx, int midy, + CVI_U32 max_mesh_num, COORD2D_INT_HW *src_1st_list) { - CVI_U32 max_mesh_num = 9 * (MAX_HEIGHT_MESH_NUM * MAX_WIDTH_MESH_NUM); + uint32_t swmesh_hit_index[4]; + + for (int i = 0; i < 4; i++) + swmesh_hit_index[i] = 0xFFFFFFFF; + + if (pstLDCAttr->stGridInfoAttr.Enable) { + // go through al hwmesh knots + int use_count = 0; + + for (int knotidx = 0; knotidx < 4; knotidx++) { + for (uint32_t meshidx = 0; meshidx < max_mesh_num; meshidx++) { + MESH_STRUCT cur_sw_mesh; + MESH_STRUCT *dst = &cfg->DstRgnMeshInfoExt[meshidx]; + MESH_STRUCT *src = &cfg->SrcRgnMeshInfoExt[meshidx]; + + // load cur_sw_mesh to check if hwmesh's knot is in it? + for (int swknotidx = 0; swknotidx < 4; swknotidx++) { + cur_sw_mesh.knot[swknotidx].xcor = dst->knot[swknotidx].xcor; + cur_sw_mesh.knot[swknotidx].ycor = src->knot[swknotidx].ycor; + } + + // check if cur-pixel in this mesh + int sw_mesh_hit = _chk_in_mesh(cur_dst_mesh[knotidx].xcor, + cur_dst_mesh[knotidx].ycor, cur_sw_mesh); + + if (sw_mesh_hit) { + swmesh_hit_index[knotidx] = meshidx; + break; + } + } + + // each knot has been + // assigned a swmesh index + // to estimate approximation. + // do estimation here: + COORD2D map_src_knot; + + memset(&map_src_knot, 0, sizeof(map_src_knot)); + + if (swmesh_hit_index[knotidx] != 0xFFFFFFFF) + use_count++; + } + + for (int knotidx = 0; knotidx < 4; knotidx++) { + COORD2D map_src_knot; + int xidx = tidx * MESH_NUM_ATILE + midx; + int yidx = tidy * MESH_NUM_ATILE + midy; + uint32_t xcor; + uint32_t offset; + + if (use_count == 4) { + map_src_knot = _find_knot_map2src(cur_dst_mesh[knotidx], cfg, + swmesh_hit_index[knotidx], 0); //0 = 1st stage + xcor = (uint32_t)_double2Int_s13_10(map_src_knot.xcor); + } else { + xcor = 0; + } + offset = (yidx * (num_tilex_s1 * MESH_NUM_ATILE) + xidx) * 4 + knotidx; + + src_1st_list[offset].xcor[0] = xcor & 0xff; + src_1st_list[offset].xcor[1] = (xcor >> 8) & 0xff; + src_1st_list[offset].xcor[2] = (xcor >> 16) & 0xff; + } + } else { + // go through al hwmesh knots + for (int knotidx = 0; knotidx < 4; knotidx++) { + for (uint32_t meshidx = 0; meshidx < max_mesh_num; meshidx++) { + MESH_STRUCT cur_sw_mesh; + MESH_STRUCT *dst = &cfg->DstRgnMeshInfoExt[meshidx]; + MESH_STRUCT *src = &cfg->SrcRgnMeshInfoExt[meshidx]; + + // load cur_sw_mesh to check if hwmesh's knot is in it? + for (int swknotidx = 0; swknotidx < 4; swknotidx++) { + cur_sw_mesh.knot[swknotidx].xcor = dst->knot[swknotidx].xcor; + cur_sw_mesh.knot[swknotidx].ycor = src->knot[swknotidx].ycor; + } + + // check if cur-pixel in this mesh + int sw_mesh_hit = _chk_in_mesh(cur_dst_mesh[knotidx].xcor, + cur_dst_mesh[knotidx].ycor, cur_sw_mesh); + + if (sw_mesh_hit) { + swmesh_hit_index[knotidx] = meshidx; + break; + } + } + + // each knot has been + // assigned a swmesh index + // to estimate approximation. + // do estimation here: + COORD2D map_src_knot; + + memset(&map_src_knot, 0, sizeof(map_src_knot)); + + if (swmesh_hit_index[knotidx] == 0xFFFFFFFF) { + CVI_TRACE_GDC(CVI_DBG_ERR, + " knotidx = %d tidx = %d tidy = %d,\n", + knotidx, tidx, tidy); + CVI_TRACE_GDC(CVI_DBG_ERR, " midx = %d, midy = %d,\n", midx, + midy); + CVI_TRACE_GDC(CVI_DBG_ERR, + " cur_dst_mesh[%d] = (%d, %d)\n", knotidx, + cur_dst_mesh[knotidx].xcor, + cur_dst_mesh[knotidx].ycor); + CVI_TRACE_GDC(CVI_DBG_ERR, " DEBUG STASRT!!\n"); + return CVI_ERR_GDC_ILLEGAL_PARAM; + } + + map_src_knot = _find_knot_map2src(cur_dst_mesh[knotidx], cfg, + swmesh_hit_index[knotidx], 0); //0 = 1st stage + + int xidx = tidx * MESH_NUM_ATILE + midx; + int yidx = tidy * MESH_NUM_ATILE + midy; + uint32_t xcor = (uint32_t)_double2Int_s13_10(map_src_knot.xcor); + uint32_t offset = + (yidx * (num_tilex_s1 * MESH_NUM_ATILE) + xidx) * 4 + + knotidx; + + src_1st_list[offset].xcor[0] = xcor & 0xff; + src_1st_list[offset].xcor[1] = (xcor >> 8) & 0xff; + src_1st_list[offset].xcor[2] = (xcor >> 16) & 0xff; + } + } + return CVI_SUCCESS; +} + +static CVI_S32 _get_1st_src_midxy(int num_tilex_s1, LDC_ATTR *cfg, COORD2D_INT_HW *src_1st_list, + int tidx, int tidy, int mesh_horcnt, int mesh_vercnt, const LDC_ATTR_S *pstLDCAttr) +{ + CVI_U32 max_mesh_num = 9 * (mesh_vercnt * mesh_horcnt); // go check all meshes inside. for (int midy = 0; midy < MESH_NUM_ATILE; midy++) { @@ -546,78 +684,8 @@ static CVI_S32 _get_1st_src_midxy(int num_tilex_s1, cur_dst_mesh[1].ycor = (tidy * TILESIZE) + (midy + 0) * HW_MESH_SIZE; cur_dst_mesh[2].ycor = (tidy * TILESIZE) + (midy + 1) * HW_MESH_SIZE; cur_dst_mesh[3].ycor = (tidy * TILESIZE) + (midy + 1) * HW_MESH_SIZE; - - // for each knot of grid cur_dst_mesh, check all sw mesh - // "on source" to estimate approximation. - // swmesh_hit_index[N] is to record which sw-mesh index - // cur knot-N hit. - uint32_t swmesh_hit_index[4]; - - for (int i = 0; i < 4; i++) - swmesh_hit_index[i] = 0xFFFFFFFF; - - // go through al hwmesh knots - for (int knotidx = 0; knotidx < 4; knotidx++) { - for (uint32_t meshidx = 0; meshidx < max_mesh_num; meshidx++) { - MESH_STRUCT cur_sw_mesh; - MESH_STRUCT *dst = &cfg->DstRgnMeshInfoExt[meshidx]; - MESH_STRUCT *src = &cfg->SrcRgnMeshInfoExt[meshidx]; - - // load cur_sw_mesh to check if hwmesh's knot is in it? - for (int swknotidx = 0; swknotidx < 4; swknotidx++) { - // 1st stage, SW destination( x, y ) = ( int ,float ) - // 1st stage, SW source( x,y ) = ( float, float ) - cur_sw_mesh.knot[swknotidx].xcor = - dst->knot[swknotidx].xcor; - cur_sw_mesh.knot[swknotidx].ycor = - src->knot[swknotidx].ycor; - } - - // check if cur-pixel in this mesh - int sw_mesh_hit = _chk_in_mesh(cur_dst_mesh[knotidx].xcor, - cur_dst_mesh[knotidx].ycor, cur_sw_mesh); - if (sw_mesh_hit) { - swmesh_hit_index[knotidx] = meshidx; - break; - } - } - - // each knot has been - // assigned a swmesh index - // to estimate approximation. - // do estimation here: - COORD2D map_src_knot; - - memset(&map_src_knot, 0, sizeof(map_src_knot)); - - if (swmesh_hit_index[knotidx] == 0xFFFFFFFF) { - CVI_TRACE_GDC(CVI_DBG_ERR, - " knotidx = %d tidx = %d tidy = %d,\n", - knotidx, tidx, tidy); - CVI_TRACE_GDC(CVI_DBG_ERR, " midx = %d, midy = %d,\n", midx, - midy); - CVI_TRACE_GDC(CVI_DBG_ERR, - " cur_dst_mesh[%d] = (%d, %d)\n", knotidx, - cur_dst_mesh[knotidx].xcor, - cur_dst_mesh[knotidx].ycor); - CVI_TRACE_GDC(CVI_DBG_ERR, " DEBUG STASRT!!\n"); - return CVI_ERR_GDC_ILLEGAL_PARAM; - } - - map_src_knot = _find_knot_map2src(cur_dst_mesh[knotidx], cfg, - swmesh_hit_index[knotidx], 0); //0 = 1st stage - - int xidx = tidx * MESH_NUM_ATILE + midx; - int yidx = tidy * MESH_NUM_ATILE + midy; - uint32_t xcor = (uint32_t)_double2Int_s13_10(map_src_knot.xcor); - uint32_t offset = - (yidx * (num_tilex_s1 * MESH_NUM_ATILE) + xidx) * 4 + - knotidx; - - src_1st_list[offset].xcor[0] = xcor & 0xff; - src_1st_list[offset].xcor[1] = (xcor >> 8) & 0xff; - src_1st_list[offset].xcor[2] = (xcor >> 16) & 0xff; - } + _get_src_1st_list(num_tilex_s1, pstLDCAttr, cfg, cur_dst_mesh, + tidx, tidy, midx, midy, max_mesh_num, src_1st_list); } } @@ -625,9 +693,8 @@ static CVI_S32 _get_1st_src_midxy(int num_tilex_s1, } static CVI_S32 _offline_get_1st_src_mesh_table(int num_tiley_s1, - int num_tilex_s1, - LDC_ATTR *cfg, - COORD2D_INT_HW *src_1st_list) + int num_tilex_s1, LDC_ATTR *cfg, COORD2D_INT_HW *src_1st_list, + int mesh_horcnt, int mesh_vercnt, const LDC_ATTR_S *pstLDCAttr) { CVI_S32 ret; @@ -635,7 +702,7 @@ static CVI_S32 _offline_get_1st_src_mesh_table(int num_tiley_s1, for (int tidy = 0; tidy < num_tiley_s1; tidy++) { for (int tidx = 0; tidx < num_tilex_s1; tidx++) { ret = _get_1st_src_midxy(num_tilex_s1, cfg, - src_1st_list, tidx, tidy); + src_1st_list, tidx, tidy, mesh_horcnt, mesh_vercnt, pstLDCAttr); if (ret != CVI_SUCCESS) return ret; } @@ -730,10 +797,12 @@ static void convert_2nd_src_mesh_table(int num_tiley_s2, int num_tilex_s2, FILE *fp2x_bin = fopen("srcx_2nd_mesh.bin", "wb"); size_t wr_size = fwrite(src_2nd_list_1d, mesh_2nd_size, 1, fp2x_bin); - if (wr_size != mesh_2nd_size) + if (wr_size != mesh_2nd_size) { CVI_TRACE_GDC(CVI_DBG_DEBUG, "2nd src mesh, fwrite %d, only %d succeed\n", mesh_2nd_size, wr_size); + } + fclose(fp2x_bin); #endif } @@ -741,9 +810,9 @@ static void convert_2nd_src_mesh_table(int num_tiley_s2, int num_tilex_s2, static CVI_S32 _fill_src_2nd_list(int num_tilex_s2, LDC_ATTR *cfg, COORD2D_INT_HW *src_2nd_list, int tidx, int tidy, int midx, int midy, MESH_STRUCT *dstMesh, COORD2D_INT *cur_dst_mesh, - uint32_t *swmesh_hit_index) + uint32_t *swmesh_hit_index, int mesh_horcnt, int mesh_vercnt) { - CVI_U32 max_mesh_num = 9 * (MAX_HEIGHT_MESH_NUM * MAX_WIDTH_MESH_NUM); + CVI_U32 max_mesh_num = 9 * (mesh_vercnt * mesh_horcnt); // go through all hwmesh knots for (int knotidx = 0; knotidx < 4; knotidx++) { @@ -804,12 +873,12 @@ static CVI_S32 _fill_src_2nd_list(int num_tilex_s2, LDC_ATTR *cfg, static CVI_S32 _offline_get_2nd_src_mesh_table(int stage2_rotate_type, int num_tiley_s2, int num_tilex_s2, LDC_ATTR *cfg, COORD2D_INT_HW *src_2nd_list, int src_width_s1, int src_height_s1, - CVI_U32 mesh_2nd_size) + CVI_U32 mesh_2nd_size, int mesh_horcnt, int mesh_vercnt) { // stage2_rotate_type = 0: +90 degrees // stage2_rotate_type = 1: -90 degrees - CVI_U32 max_mesh_num = 9 * (MAX_HEIGHT_MESH_NUM * MAX_WIDTH_MESH_NUM); + CVI_U32 max_mesh_num = 9 * (mesh_vercnt * mesh_horcnt); int RMATRIX[2][2]; MESH_STRUCT *dstMesh = cfg->DstRgnMeshInfoExt2ND; @@ -899,7 +968,8 @@ static CVI_S32 _offline_get_2nd_src_mesh_table(int stage2_rotate_type, ret = _fill_src_2nd_list(num_tilex_s2, cfg, src_2nd_list, tidx, tidy, midx, midy, - dstMesh, cur_dst_mesh, swmesh_hit_index); + dstMesh, cur_dst_mesh, swmesh_hit_index, + mesh_horcnt, mesh_vercnt); if (ret != CVI_SUCCESS) return ret; } @@ -919,7 +989,7 @@ static CVI_S32 _offline_get_2nd_src_mesh_table(int stage2_rotate_type, static void _ldc_attr_map_cv182x(const LDC_ATTR_S *pstLDCAttr, LDC_ATTR *cfg, LDC_RGN_ATTR *rgn_attr, double x0, - double y0, double r) + double y0, double r, int mesh_horcnt, int mesh_vercnt) { // Global Initialization cfg->Enable = 1; @@ -943,8 +1013,13 @@ static void _ldc_attr_map_cv182x(const LDC_ATTR_S *pstLDCAttr, LDC_ATTR *cfg, rgn_attr[0].OutY = 0; rgn_attr[0].InRadius = pstLDCAttr->s32CenterXOffset; rgn_attr[0].OutRadius = pstLDCAttr->s32CenterYOffset; - rgn_attr[0].MeshVer = 16; - rgn_attr[0].MeshHor = 16; + if (pstLDCAttr->stGridInfoAttr.Enable) { + rgn_attr[0].MeshVer = mesh_vercnt; + rgn_attr[0].MeshHor = mesh_horcnt; + } else { + rgn_attr[0].MeshVer = MAX_WIDTH_MESH_NUM; + rgn_attr[0].MeshHor = MAX_HEIGHT_MESH_NUM; + } rgn_attr[0].ThetaX = pstLDCAttr->s32XRatio; rgn_attr[0].ThetaZ = pstLDCAttr->s32YRatio; } @@ -979,12 +1054,6 @@ static CVI_S32 _get_region_dst_mesh_list(LDC_RGN_ATTR *rgn_attr, int view_w, for (int i = 0; i < mesh_horcnt; i++) { int meshidx = j * mesh_horcnt + i; - if (meshidx >= MAX_FRAME_MESH_NUM) { - CVI_TRACE_GDC(CVI_DBG_WARN, " [%d][%d] meshidx = %d >= MAX_FRAME_MESH_NUM(%d)\n", - j, i, meshidx, MAX_FRAME_MESH_NUM); - return CVI_ERR_GDC_ILLEGAL_PARAM; - } - int xcor = (mesh_xstep * (i + 0)) >> PHASEBIT; int xcor_r = (mesh_xstep * (i + 1)) >> PHASEBIT; int ycor = (mesh_ystep * (j + 0)) >> PHASEBIT; @@ -1134,7 +1203,7 @@ static void _get_frame_mesh_list(LDC_ATTR *cfg, LDC_RGN_ATTR *rgn_attr) { // pack all regions' mesh info, including src & dst. int rgnNum = cfg->RgnNum; - int meshNumRgn[MAX_REGION_NUM]; + int meshNumRgn[MAX_REGION_NUM] = {0}; int frameMeshIdx = 0; for (int i = 0; i < rgnNum; i++) { @@ -1164,12 +1233,12 @@ static void _get_frame_mesh_list(LDC_ATTR *cfg, LDC_RGN_ATTR *rgn_attr) cfg->TotalMeshNum = frameMeshIdx; #ifdef SAVE_MESH_TBL_FILE - save_mesh_info(cfg); + save_mesh_info(cfg, meshNumRgn[0]); #endif } static void _get_region_src_mesh_list(LDC_RGN_ATTR *rgn_attr, int rgn_idx, - double x0, double y0) + double x0, double y0, meshdata_all *meshdata, const LDC_ATTR_S *pstLDCAttr) { int view_w = rgn_attr[rgn_idx].OutW; int view_h = rgn_attr[rgn_idx].OutH; @@ -1196,36 +1265,71 @@ static void _get_region_src_mesh_list(LDC_RGN_ATTR *rgn_attr, int rgn_idx, double Aspect_gainY = MAX(ud_gain, lr_gain); Vector2D dist2d; - for (int i = 0; i < 9*(mesh_horcnt * mesh_vercnt); i++) { - // Do LDC mapping in Center Mesh Grid only - for (int knotidx = 0; knotidx < 4; knotidx++) { - double x = rgn_attr[rgn_idx].DstRgnMeshInfoExt[i].knot[knotidx].xcor - - rgn_attr[rgn_idx].OutX - rgn_attr[rgn_idx].OutW / 2; - double y = rgn_attr[rgn_idx].DstRgnMeshInfoExt[i].knot[knotidx].ycor - - rgn_attr[rgn_idx].OutY - rgn_attr[rgn_idx].OutH / 2; + if (pstLDCAttr->stGridInfoAttr.Enable) { + int str_idx = *(meshdata->pmesh_dst) / meshdata->mesh_w; + int str_idy = *(meshdata->pmesh_dst + 1) / meshdata->mesh_h; + int end_idx = str_idx + meshdata->mesh_horcnt - 1; + int end_idy = str_idy + meshdata->mesh_vercnt - 1; - x = x - CenterXOffset; // -view_w / 2 + 1, view_w / 2 - 1); - y = y - CenterYOffset; // -view_h / 2 + 1, view_h / 2 - 1); + int ext_str_idx = str_idx + mesh_horcnt; + int ext_end_idx = end_idx + mesh_horcnt; + int ext_str_idy = str_idy + mesh_vercnt; + int ext_end_idy = end_idy + mesh_vercnt; - x = x / Aspect_gainX; - y = y / Aspect_gainY; + for (int i = 0; i < 9 * (mesh_horcnt * mesh_vercnt); i++) { + int idy = i / (mesh_horcnt * 3); + int idx = i % (mesh_horcnt * 3); - if (bAspect == true) { - x = x * (1 - 0.333 * (100 - XYRatio) / 100); - y = y * (1 - 0.333 * (100 - XYRatio) / 100); - } else { - x = x * (1 - 0.333 * (100 - XRatio) / 100); - y = y * (1 - 0.333 * (100 - YRatio) / 100); + for (int j = 0; j < 4; j++) { + if (ext_str_idx <= idx && idx <= ext_end_idx && ext_str_idy <= idy && + idy <= ext_end_idy) { + int roi_idx = idx - ext_str_idx; + int roi_idy = idy - ext_str_idy; + + rgn_attr[rgn_idx].SrcRgnMeshInfoExt[i].knot[j].xcor = *(meshdata->pmesh_src + + 8 * roi_idx + meshdata->mesh_horcnt * 8 * roi_idy + 2 * j); + rgn_attr[rgn_idx].SrcRgnMeshInfoExt[i].knot[j].ycor = *(meshdata->pmesh_src + + 8 * roi_idx + meshdata->mesh_horcnt * 8 * roi_idy + 2 * j + 1); + } else { + rgn_attr[rgn_idx].SrcRgnMeshInfoExt[i].knot[j].xcor = 0; + rgn_attr[rgn_idx].SrcRgnMeshInfoExt[i].knot[j].ycor = 0; + } } + } + } else { + for (int i = 0; i < 9*(mesh_horcnt * mesh_vercnt); i++) { + // Do LDC mapping in Center Mesh Grid only + for (int knotidx = 0; knotidx < 4; knotidx++) { + double x = rgn_attr[rgn_idx].DstRgnMeshInfoExt[i].knot[knotidx].xcor - + rgn_attr[rgn_idx].OutX - rgn_attr[rgn_idx].OutW / 2; + double y = rgn_attr[rgn_idx].DstRgnMeshInfoExt[i].knot[knotidx].ycor - + rgn_attr[rgn_idx].OutY - rgn_attr[rgn_idx].OutH / 2; - double rd = MIN(norm, sqrt(x * x + y * y)); + x = x - CenterXOffset; // -view_w / 2 + 1, view_w / 2 - 1); + y = y - CenterYOffset; // -view_h / 2 + 1, view_h / 2 - 1); - dist2d.x = x * (1 + k * ((rd / norm) * (rd / norm))); - dist2d.y = y * (1 + k * ((rd / norm) * (rd / norm))); + x = x / Aspect_gainX; + y = y / Aspect_gainY; - // update source mesh-info here - rgn_attr[rgn_idx].SrcRgnMeshInfoExt[i].knot[knotidx].xcor = dist2d.x + x0 + CenterXOffset; - rgn_attr[rgn_idx].SrcRgnMeshInfoExt[i].knot[knotidx].ycor = dist2d.y + y0 + CenterYOffset; + if (bAspect == true) { + x = x * (1 - 0.333 * (100 - XYRatio) / 100); + y = y * (1 - 0.333 * (100 - XYRatio) / 100); + } else { + x = x * (1 - 0.333 * (100 - XRatio) / 100); + y = y * (1 - 0.333 * (100 - YRatio) / 100); + } + + double rd = MIN(norm, sqrt(x * x + y * y)); + + dist2d.x = x * (1 + k * ((rd / norm) * (rd / norm))); + dist2d.y = y * (1 + k * ((rd / norm) * (rd / norm))); + + // update source mesh-info here + rgn_attr[rgn_idx].SrcRgnMeshInfoExt[i].knot[knotidx].xcor = + dist2d.x + x0 + CenterXOffset; + rgn_attr[rgn_idx].SrcRgnMeshInfoExt[i].knot[knotidx].ycor = + dist2d.y + y0 + CenterYOffset; + } } } } @@ -1354,15 +1458,60 @@ CVI_S32 mesh_gen_ldc(SIZE_S in_size, SIZE_S out_size, CVI_TRACE_GDC(CVI_DBG_DEBUG, " 1st src_1st_list=%p(%d), src_2nd_list=%p(%d)\n", src_1st_list_1d, mesh_1st_size, src_2nd_list_1d, mesh_2nd_size); + // load gridinfo + int mesh_horcnt = MAX_WIDTH_MESH_NUM, mesh_vercnt = MAX_HEIGHT_MESH_NUM; + + if (pstLDCAttr->stGridInfoAttr.Enable) { + load_meshdata(pstLDCAttr->stGridInfoAttr.gridFileName, &gdc_meshdata, + pstLDCAttr->stGridInfoAttr.gridBindName); + mesh_horcnt = gdc_meshdata.imgw / gdc_meshdata.mesh_w; + mesh_vercnt = gdc_meshdata.imgh / gdc_meshdata.mesh_h; + } + CVI_TRACE_GDC(CVI_DBG_DEBUG, "mesh_horcnt, mesh_vercnt (%d, %d\n)", mesh_horcnt, mesh_vercnt); + int max_frame_mesh_num = mesh_horcnt * mesh_vercnt; + src_1st_list = (COORD2D_INT_HW *)malloc(mesh_1st_size); src_2nd_list = (COORD2D_INT_HW *)malloc(mesh_2nd_size); cfg = (LDC_ATTR *)calloc(1, sizeof(*cfg)); rgn_attr = (LDC_RGN_ATTR *)calloc(1, sizeof(*rgn_attr) * MAX_REGION_NUM); - if (!src_1st_list || !src_2nd_list || !cfg || !rgn_attr) { + cfg->DstRgnMeshInfo = (MESH_STRUCT *)calloc(max_frame_mesh_num, sizeof(MESH_STRUCT)); + cfg->SrcRgnMeshInfo = (MESH_STRUCT *)calloc(max_frame_mesh_num, sizeof(MESH_STRUCT)); + cfg->DstRgnMeshInfoExt = (MESH_STRUCT *)calloc(9 * max_frame_mesh_num, sizeof(MESH_STRUCT)); + cfg->SrcRgnMeshInfoExt = (MESH_STRUCT *)calloc(9 * max_frame_mesh_num, sizeof(MESH_STRUCT)); + cfg->DstRgnMeshInfoExt2ND = (MESH_STRUCT *)calloc(9 * max_frame_mesh_num, sizeof(MESH_STRUCT)); + cfg->SrcRgnMeshInfoExt2ND = (MESH_STRUCT *)calloc(9 * max_frame_mesh_num, sizeof(MESH_STRUCT)); + cfg->DstRgnMeshInfo_1st = (MESH_STRUCT *)calloc(max_frame_mesh_num, sizeof(MESH_STRUCT)); + cfg->SrcRgnMeshInfo_1st = (MESH_STRUCT *)calloc(max_frame_mesh_num, sizeof(MESH_STRUCT)); + cfg->DstRgnMeshInfo_2nd = (MESH_STRUCT *)calloc(max_frame_mesh_num, sizeof(MESH_STRUCT)); + cfg->SrcRgnMeshInfo_2nd = (MESH_STRUCT *)calloc(max_frame_mesh_num, sizeof(MESH_STRUCT)); + rgn_attr->DstRgnMeshInfo = (MESH_STRUCT *)calloc(max_frame_mesh_num, sizeof(MESH_STRUCT)); + rgn_attr->DstRgnMeshInfoExt = (MESH_STRUCT *)calloc(9 * max_frame_mesh_num, sizeof(MESH_STRUCT)); + rgn_attr->SrcRgnMeshInfo = (MESH_STRUCT *)calloc(max_frame_mesh_num, sizeof(MESH_STRUCT)); + rgn_attr->SrcRgnMeshInfoExt = (MESH_STRUCT *)calloc(9 * max_frame_mesh_num, sizeof(MESH_STRUCT)); + if (!src_1st_list || !src_2nd_list || !cfg || !rgn_attr || !cfg->DstRgnMeshInfo || + !cfg->SrcRgnMeshInfo || !cfg->DstRgnMeshInfoExt || !cfg->SrcRgnMeshInfoExt || + !cfg->DstRgnMeshInfoExt2ND || !cfg->SrcRgnMeshInfoExt2ND || !cfg->DstRgnMeshInfo_1st || + !cfg->SrcRgnMeshInfo_1st || !cfg->DstRgnMeshInfo_2nd || !cfg->SrcRgnMeshInfo_2nd || + !rgn_attr->DstRgnMeshInfo || !rgn_attr->DstRgnMeshInfoExt || !rgn_attr->SrcRgnMeshInfo || + !rgn_attr->SrcRgnMeshInfoExt) { free(src_1st_list); free(src_2nd_list); free(cfg); free(rgn_attr); + free(cfg->DstRgnMeshInfo); + free(cfg->SrcRgnMeshInfo); + free(cfg->DstRgnMeshInfoExt); + free(cfg->SrcRgnMeshInfoExt); + free(cfg->DstRgnMeshInfoExt2ND); + free(cfg->SrcRgnMeshInfoExt2ND); + free(cfg->DstRgnMeshInfo_1st); + free(cfg->SrcRgnMeshInfo_1st); + free(cfg->DstRgnMeshInfo_2nd); + free(cfg->SrcRgnMeshInfo_2nd); + free(rgn_attr->DstRgnMeshInfo); + free(rgn_attr->DstRgnMeshInfoExt); + free(rgn_attr->SrcRgnMeshInfo); + free(rgn_attr->SrcRgnMeshInfoExt); CVI_TRACE_GDC(CVI_DBG_ERR, " fail to alloc mesh\n"); return CVI_ERR_GDC_NOMEM; @@ -1377,9 +1526,16 @@ CVI_S32 mesh_gen_ldc(SIZE_S in_size, SIZE_S out_size, reg.bg_color_y_r = (bgc_pack & 0xFF0000) >> 16; reg.bg_color_u_g = (bgc_pack & 0x00FF00) >> 8; reg.bg_color_v_b = (bgc_pack & 0x0000FF) >> 0; + int ori_src_width; + int ori_src_height; - int ori_src_width = in_size.u32Width; - int ori_src_height = in_size.u32Height; + if (pstLDCAttr->stGridInfoAttr.Enable) { + ori_src_width = gdc_meshdata.imgw; + ori_src_height = gdc_meshdata.imgh; + } else { + ori_src_width = in_size.u32Width; + ori_src_height = in_size.u32Height; + } CVI_TRACE_GDC(CVI_DBG_DEBUG, " ori_src_width = %d,\n", ori_src_width); CVI_TRACE_GDC(CVI_DBG_DEBUG, " ori_src_height = %d,\n", ori_src_height); @@ -1415,8 +1571,7 @@ CVI_S32 mesh_gen_ldc(SIZE_S in_size, SIZE_S out_size, CVI_TRACE_GDC(CVI_DBG_DEBUG, "cfg size %d\n", (int)sizeof(LDC_ATTR)); // update parameters - _ldc_attr_map_cv182x(pstLDCAttr, cfg, rgn_attr, x0, y0, r); - + _ldc_attr_map_cv182x(pstLDCAttr, cfg, rgn_attr, x0, y0, r, mesh_horcnt, mesh_vercnt); // In Each Mode, for Every Region: for (int rgn_idx = 0; rgn_idx < cfg->RgnNum; rgn_idx++) { // check region valid first @@ -1426,8 +1581,8 @@ CVI_S32 mesh_gen_ldc(SIZE_S in_size, SIZE_S out_size, // Destination Mesh-Info Allocation int view_w = rgn_attr[rgn_idx].OutW; int view_h = rgn_attr[rgn_idx].OutH; - int mesh_horcnt = rgn_attr[rgn_idx].MeshHor; - int mesh_vercnt = rgn_attr[rgn_idx].MeshVer; + // int mesh_horcnt = rgn_attr[rgn_idx].MeshHor; + // int mesh_vercnt = rgn_attr[rgn_idx].MeshVer; // get & store region mesh info. #ifdef ENABLE_PROFILE @@ -1444,7 +1599,7 @@ CVI_S32 mesh_gen_ldc(SIZE_S in_size, SIZE_S out_size, #ifdef ENABLE_PROFILE clock_gettime(CLOCK_MONOTONIC, &start); #endif - _get_region_src_mesh_list(rgn_attr, rgn_idx, x0, y0); //, mat0); + _get_region_src_mesh_list(rgn_attr, rgn_idx, x0, y0, &gdc_meshdata, pstLDCAttr); //, mat0); #ifdef ENABLE_PROFILE clock_gettime(CLOCK_MONOTONIC, &end); CVI_TRACE_GDC(CVI_DBG_ERR, " _get_region_src_mesh_list: %ldms\n", @@ -1455,6 +1610,8 @@ CVI_S32 mesh_gen_ldc(SIZE_S in_size, SIZE_S out_size, CVI_TRACE_GDC(CVI_DBG_DEBUG, " REGION %d done.\n", rgn_idx); } + free_cur_meshdata(&gdc_meshdata); + //combine all region meshs - mesh projection done. #ifdef ENABLE_PROFILE clock_gettime(CLOCK_MONOTONIC, &start); @@ -1503,7 +1660,8 @@ CVI_S32 mesh_gen_ldc(SIZE_S in_size, SIZE_S out_size, #ifdef ENABLE_PROFILE clock_gettime(CLOCK_MONOTONIC, &start); #endif - ret |= _offline_get_1st_src_mesh_table(num_tiley_s1, num_tilex_s1, cfg, src_1st_list); + ret |= _offline_get_1st_src_mesh_table(num_tiley_s1, num_tilex_s1, cfg, src_1st_list, + mesh_horcnt, mesh_vercnt, pstLDCAttr); #ifdef ENABLE_PROFILE clock_gettime(CLOCK_MONOTONIC, &end); CVI_TRACE_GDC(CVI_DBG_ERR, " _offline_get_1st_src_mesh_table: %ldms\n", @@ -1514,7 +1672,7 @@ CVI_S32 mesh_gen_ldc(SIZE_S in_size, SIZE_S out_size, clock_gettime(CLOCK_MONOTONIC, &start); #endif ret |= _offline_get_2nd_src_mesh_table(reg.stage2_rotate_type, num_tiley_s2, num_tilex_s2, cfg, - src_2nd_list, src_width_s1, src_height_s1, mesh_2nd_size); + src_2nd_list, src_width_s1, src_height_s1, mesh_2nd_size, mesh_horcnt, mesh_vercnt); #ifdef ENABLE_PROFILE clock_gettime(CLOCK_MONOTONIC, &end); CVI_TRACE_GDC(CVI_DBG_ERR, " _offline_get_2nd_src_mesh_table: %ldms\n", @@ -1545,7 +1703,20 @@ CVI_S32 mesh_gen_ldc(SIZE_S in_size, SIZE_S out_size, free(src_2nd_list); free(cfg); free(rgn_attr); - + free(cfg->DstRgnMeshInfo); + free(cfg->SrcRgnMeshInfo); + free(cfg->DstRgnMeshInfoExt); + free(cfg->SrcRgnMeshInfoExt); + free(cfg->DstRgnMeshInfoExt2ND); + free(cfg->SrcRgnMeshInfoExt2ND); + free(cfg->DstRgnMeshInfo_1st); + free(cfg->SrcRgnMeshInfo_1st); + free(cfg->DstRgnMeshInfo_2nd); + free(cfg->SrcRgnMeshInfo_2nd); + free(rgn_attr->DstRgnMeshInfo); + free(rgn_attr->DstRgnMeshInfoExt); + free(rgn_attr->SrcRgnMeshInfo); + free(rgn_attr->SrcRgnMeshInfoExt); return ret; } diff --git a/middleware/v2/modules/vpu/src/grid_info.c b/middleware/v2/modules/vpu/src/grid_info.c new file mode 100644 index 000000000..f8e9b7db4 --- /dev/null +++ b/middleware/v2/modules/vpu/src/grid_info.c @@ -0,0 +1,130 @@ +#include +#include +#include +#include +#include "cvi_debug.h" +#include "grid_info.h" + +int load_meshdata(const char *path, MESH_DATA_ALL_S *pmeshdata, const char *bindName) +{ + int info[100] = {0}; + FILE *fpGrid; + + if (path == NULL) { + CVI_TRACE_GDC(CVI_DBG_ERR, "file is null\n"); + return -1; + } + + fpGrid = fopen(path, "rb"); + if (fpGrid == NULL) { + CVI_TRACE_GDC(CVI_DBG_ERR, "open file fail, %s\n", path); + return -1; + } + + //fread(&pmeshdata->mesh_horcnt, sizeof(int), 1, fpGrid); + //fread(&pmeshdata->mesh_vercnt, sizeof(int), 1, fpGrid); + //fread(&pmeshdata->num_pairs, sizeof(int), 1, fpGrid); + //fread(&pmeshdata->imgw, sizeof(int), 1, fpGrid); + //fread(&pmeshdata->imgh, sizeof(int), 1, fpGrid); +#if USE_OLD + if (fread(info, sizeof(int), 20, fpGrid) != 20) { + CVI_TRACE_GDC(CVI_DBG_ERR, "read file fail, %s\n", path); + return -1; + } +#else + if (fread(info, sizeof(int), 100, fpGrid) != 100) { + CVI_TRACE_GDC(CVI_DBG_ERR, "read file fail, %s\n", path); + return -1; + } +#endif + + CVI_TRACE_GDC(CVI_DBG_DEBUG, "head %d %d %d %d %d\n", info[0], info[1], info[2], info[3], info[4]); + pmeshdata->mesh_horcnt = info[0]; // num of mesh in roi + pmeshdata->mesh_vercnt = info[1]; // num of mesh in roi + pmeshdata->num_pairs = info[2]; + pmeshdata->imgw = info[3]; + pmeshdata->imgh = info[4]; + // + pmeshdata->mesh_w = info[5]; // unit: pixel + pmeshdata->mesh_h = info[6]; // unit: pixel + pmeshdata->unit_rx = info[7]; // unit: mesh_w + pmeshdata->unit_ry = info[8]; // unit: mesh_h + pmeshdata->_nbr_mesh_x = info[9]; // total meshes in horizontal + pmeshdata->_nbr_mesh_y = info[10]; // total meshes in vertical + memcpy(pmeshdata->corners, info + 11, sizeof(int) * 8); + + int _nbr_mesh_y = pmeshdata->mesh_vercnt; // for roi, not for whole image + int _nbr_mesh_x = pmeshdata->mesh_horcnt; + int count_grid = pmeshdata->num_pairs; + + pmeshdata->node_index = (_nbr_mesh_x + 1)*(_nbr_mesh_y + 1); + + strcpy(pmeshdata->grid_name, bindName); + + pmeshdata->pgrid_src = (int *)calloc(count_grid * 2, sizeof(int)); + pmeshdata->pgrid_dst = (int *)calloc(count_grid * 2, sizeof(int)); + pmeshdata->pmesh_src = (int *)calloc(count_grid * 8, sizeof(int)); + pmeshdata->pmesh_dst = (int *)calloc(count_grid * 8, sizeof(int)); + pmeshdata->pnode_src = (int *)calloc(pmeshdata->node_index*2, sizeof(int)); + pmeshdata->pnode_dst = (int *)calloc(pmeshdata->node_index*2, sizeof(int)); + + CVI_TRACE_GDC(CVI_DBG_DEBUG, + "mesh_horcnt,mesh_vercnt,_nbr_mesh_x, _nbr_mesh_y, count_grid, num_nodes: %d %d %d %d %d %d\n", + pmeshdata->mesh_horcnt, pmeshdata->mesh_vercnt, _nbr_mesh_x, _nbr_mesh_y, count_grid, + pmeshdata->node_index); + CVI_TRACE_GDC(CVI_DBG_DEBUG, "imgw, imgh, mesh_w, mesh_h ,unit_rx, unit_ry: %d %d %d %d %d %d", + pmeshdata->imgw, pmeshdata->imgh, pmeshdata->mesh_w, pmeshdata->mesh_h, pmeshdata->unit_rx, + pmeshdata->unit_ry); + + if (fread(pmeshdata->pgrid_src, sizeof(int), (count_grid * 2), fpGrid) != (size_t)(count_grid * 2)) { + CVI_TRACE_GDC(CVI_DBG_ERR, "read file fail, %s\n", path); + return -1; + } + + if (fread(pmeshdata->pgrid_dst, sizeof(int), (count_grid * 2), fpGrid) != (size_t)(count_grid * 2)) { + CVI_TRACE_GDC(CVI_DBG_ERR, "read file fail, %s\n", path); + return -1; + } + // hw mesh + if (fread(pmeshdata->pmesh_src, sizeof(int), (count_grid * 2 * 4), fpGrid) != (size_t)(count_grid * 2 * 4)) { + CVI_TRACE_GDC(CVI_DBG_ERR, "read file fail, %s\n", path); + return -1; + } + if (fread(pmeshdata->pmesh_dst, sizeof(int), (count_grid * 2 * 4), fpGrid) != (size_t)(count_grid * 2 * 4)) { + CVI_TRACE_GDC(CVI_DBG_ERR, "read file fail, %s\n", path); + return -1; + } + // hw node + if (fread(pmeshdata->pnode_src, sizeof(int), (pmeshdata->node_index * 2), + fpGrid) != (size_t)(pmeshdata->node_index * 2)) { + CVI_TRACE_GDC(CVI_DBG_ERR, "read file fail, %s\n", path); + return -1; + } + if (fread(pmeshdata->pnode_dst, sizeof(int), (pmeshdata->node_index * 2), + fpGrid) != (size_t)(pmeshdata->node_index * 2)) { + CVI_TRACE_GDC(CVI_DBG_ERR, "read file fail, %s\n", path); + return -1; + } + + fclose(fpGrid); + + pmeshdata->balloc = true; + CVI_TRACE_GDC(CVI_DBG_DEBUG, "read succ\n"); + + return 0; +} + +int free_cur_meshdata(MESH_DATA_ALL_S *pmeshdata) +{ + SAFE_FREE_POINTER(pmeshdata->pgrid_src); + SAFE_FREE_POINTER(pmeshdata->pgrid_dst); + SAFE_FREE_POINTER(pmeshdata->pmesh_src); + SAFE_FREE_POINTER(pmeshdata->pmesh_dst); + SAFE_FREE_POINTER(pmeshdata->pnode_src); + SAFE_FREE_POINTER(pmeshdata->pnode_dst); + + pmeshdata->balloc = false; + pmeshdata->_bhomo = false; + + return 0; +} \ No newline at end of file diff --git a/middleware/v2/sample/common/Kbuild b/middleware/v2/sample/common/Kbuild index aa4550ac6..a753c3522 100644 --- a/middleware/v2/sample/common/Kbuild +++ b/middleware/v2/sample/common/Kbuild @@ -261,6 +261,10 @@ ifeq ($(CONFIG_SENSOR_SMS_SC3336), y) KBUILD_DEFINES += -DSENSOR_SMS_SC3336 endif +ifeq ($(CONFIG_SENSOR_SMS_SC3336_1L), y) + KBUILD_DEFINES += -DSENSOR_SMS_SC3336_1L +endif + ifeq ($(CONFIG_SENSOR_SMS_SC3336P), y) KBUILD_DEFINES += -DSENSOR_SMS_SC3336P endif diff --git a/middleware/v2/sample/common/sample_comm.h b/middleware/v2/sample/common/sample_comm.h index e956bd408..2225891b7 100644 --- a/middleware/v2/sample/common/sample_comm.h +++ b/middleware/v2/sample/common/sample_comm.h @@ -263,6 +263,7 @@ typedef enum _SAMPLE_SNS_TYPE_E { SMS_SC3335_MIPI_3M_30FPS_10BIT, SMS_SC3335_SLAVE_MIPI_3M_30FPS_10BIT, SMS_SC3336_MIPI_3M_30FPS_10BIT, + SMS_SC3336_1L_MIPI_3M_20FPS_10BIT, SMS_SC3336P_MIPI_3M_30FPS_10BIT, SMS_SC2331_1L_MIPI_2M_30FPS_10BIT, SMS_SC2331_1L_SLAVE_MIPI_2M_30FPS_10BIT, @@ -768,6 +769,7 @@ typedef struct _chnInputCfg_ { CVI_U32 complex_min_percent; CVI_BOOL smart_ai_en; + CVI_U32 u32ResetGop; } chnInputCfg; typedef enum _CHN_STATE_ { diff --git a/middleware/v2/sample/common/sample_common_sensor.c b/middleware/v2/sample/common/sample_common_sensor.c index 9b6f3c9a4..9c302d8c6 100644 --- a/middleware/v2/sample/common/sample_common_sensor.c +++ b/middleware/v2/sample/common/sample_common_sensor.c @@ -168,6 +168,7 @@ static const char *snsr_type_name[SAMPLE_SNS_TYPE_BUTT] = { "SMS_SC3335_MIPI_3M_30FPS_10BIT", "SMS_SC3335_SLAVE_MIPI_3M_30FPS_10BIT", "SMS_SC3336_MIPI_3M_30FPS_10BIT", + "SMS_SC3336_1L_MIPI_3M_20FPS_10BIT", "SMS_SC3336P_MIPI_3M_30FPS_10BIT", "SMS_SC2331_1L_MIPI_2M_30FPS_10BIT", "SMS_SC2331_1L_SLAVE_MIPI_2M_30FPS_10BIT", @@ -478,6 +479,7 @@ CVI_S32 SAMPLE_COMM_SNS_GetSize(SAMPLE_SNS_TYPE_E enMode, PIC_SIZE_E *penSize) case SMS_SC3335_MIPI_3M_30FPS_10BIT: case SMS_SC3335_SLAVE_MIPI_3M_30FPS_10BIT: case SMS_SC3336_MIPI_3M_30FPS_10BIT: + case SMS_SC3336_1L_MIPI_3M_20FPS_10BIT: case SMS_SC3336P_MIPI_3M_30FPS_10BIT: case SOI_Q03_MIPI_3M_30FPS_10BIT: case SOI_Q03P_MIPI_3M_30FPS_10BIT: @@ -1096,6 +1098,7 @@ CVI_S32 SAMPLE_COMM_SNS_GetIspAttrBySns(SAMPLE_SNS_TYPE_E enSnsType, ISP_PUB_ATT pstPubAttr->f32FrameRate = 12; break; case GCORE_GC0312_MIPI_480P_20FPS_8BIT: + case SMS_SC3336_1L_MIPI_3M_20FPS_10BIT: pstPubAttr->f32FrameRate = 20; break; case GCORE_GC0329_MIPI_480P_10FPS_8BIT: @@ -1571,6 +1574,11 @@ CVI_VOID *SAMPLE_COMM_SNS_GetSnsObj(SAMPLE_SNS_TYPE_E enSnsType) pSnsObj = &stSnsSC3336_Obj; break; #endif +#if defined(SENSOR_SMS_SC3336_1L) + case SMS_SC3336_1L_MIPI_3M_20FPS_10BIT: + pSnsObj = &stSnsSC3336_1L_Obj; + break; +#endif #if defined(SENSOR_SMS_SC3336P) case SMS_SC3336P_MIPI_3M_30FPS_10BIT: pSnsObj = &stSnsSC3336P_Obj; diff --git a/middleware/v2/sample/common/sample_common_venc.c b/middleware/v2/sample/common/sample_common_venc.c index ce9b14c14..f0f135241 100644 --- a/middleware/v2/sample/common/sample_common_venc.c +++ b/middleware/v2/sample/common/sample_common_venc.c @@ -201,6 +201,7 @@ CVI_VOID SAMPLE_COMM_VENC_InitChnInputCfg(chnInputCfg *pIc) pIc->single_LumaBuf = 0; pIc->single_core = 0; pIc->forceIdr = -1; + pIc->u32ResetGop = 0; pIc->chgNum = -1; pIc->tempLayer = 0; pIc->bgInterval = CVI_H26X_SMARTP_BG_INTERVAL_DEFAULT; diff --git a/middleware/v2/sample/venc/src/sample_venc_lib.c b/middleware/v2/sample/venc/src/sample_venc_lib.c index f955f1b4e..e207b9327 100644 --- a/middleware/v2/sample/venc/src/sample_venc_lib.c +++ b/middleware/v2/sample/venc/src/sample_venc_lib.c @@ -167,6 +167,8 @@ static optionExt venc_long_option_ext[] = { "0: disable, 1: use single core(h264 or h265 only)"}, {{"forceIdr", optional_argument, NULL, 0}, ARG_INT, 0, 1000000000, "0: disable, > 0: set force idr at number of frame"}, + {{"resetGop", optional_argument, NULL, 0}, ARG_UINT, 0, 1, + "0: not reset, 1: reset gop, reset when forceIdr > 0"}, {{"chgNum", optional_argument, NULL, 0}, ARG_INT, 0, 1000000, "frame num to change attr"}, {{"chgBitrate", optional_argument, NULL, 0}, ARG_INT, 1, 1000000, @@ -927,6 +929,8 @@ CVI_S32 parseEncArgv(sampleVenc *psv, chnInputCfg *pIc, CVI_S32 argc, char **arg pIc->single_LumaBuf = arg.ival; } else if (!strcmp(long_options[idx].name, "forceIdr")) { pIc->forceIdr = arg.ival; + } else if (!strcmp(long_options[idx].name, "resetGop")) { + pIc->u32ResetGop = arg.uval; } else if (!strcmp(long_options[idx].name, "chgNum")) { pIc->chgNum = arg.ival; } else if (!strcmp(long_options[idx].name, "chgBitrate")) { @@ -3106,10 +3110,10 @@ static CVI_S32 _SAMPLE_VENC_SendFrame(vencChnCtx *pvecc, CVI_U32 i) CVI_VENC_TRACE("[Chn%d] frame %d (%d)\n", VencChn, i, pvecc->num_frames); if (pIc->forceIdr > 0 && pIc->forceIdr == (CVI_S32)i) { - CVI_BOOL bInstant = CVI_TRUE; + CVI_BOOL bInstant = pIc->u32ResetGop; CVI_VENC_RequestIDR(VencChn, bInstant); - CVI_VENC_TRACE("CVI_VENC_RequestIDR\n"); + CVI_VENC_TRACE("CVI_VENC_RequestIDR, resetGop:%d\n", bInstant); } if (enableBinRoi) { ctbHeight = ((pvecc->stSize.u32Width + 63) & ~63) >> 6;