1.aarch64平台移植是需要根据不同指令集调整编译,dotprod指令支持需要armv8.2以上指令集,CortexA53架构的SOC编译失败。
2.MakeLists.txt里面有多个功能模块需要用的armv9指令集,如果SOC不支持需要编译前注释掉这些模块生产。
3.项目中用到的接口封装如下:
static int DispYV12Scale(char *src_img, int src_w, int src_h, char *dst_img, int dst_w, int dst_h)
{
char *src_y_addr = src_img;
char *src_v_addr = src_img + (src_w * src_h);
char *src_u_addr = src_img + (src_w * src_h * 5 / 4);
char *dst_y_addr = dst_img;
char *dst_v_addr = dst_img + (dst_w * dst_h);
char *dst_u_addr = dst_img + (dst_w * dst_h * 5 / 4);
return I420Scale(src_y_addr, src_w, src_u_addr, src_w>>1, src_v_addr, src_w>>1, src_w, src_h,
dst_y_addr, dst_w, dst_u_addr, dst_w>>1, dst_v_addr, dst_w>>1, dst_w, dst_h, kFilterLinear);//kFilterNone
}
static int DispYV12ToARGB(char *yuv_img, char *rgb_img, int img_w, int img_h)
{
char *src_y_addr = yuv_img;
char *src_v_addr = yuv_img + (img_w * img_h);
char *src_u_addr = yuv_img + (img_w * img_h * 5 / 4);
return I420ToARGB(src_y_addr, img_w, src_u_addr, img_w>>1, src_v_addr, img_w>>1,
rgb_img, img_w*4, img_w, img_h);
}
static int DispNV21Scale(char *src_img, int src_w, int src_h, char *dst_img, int dst_w, int dst_h)
{
int ret = 0;
char *src_y_addr = src_img;
char *src_vu_addr = src_img + (src_w * src_h);
char *dst_y_addr = dst_img;
char *dst_vu_addr = dst_img + (dst_w * dst_h);
return NV12Scale(src_y_addr, src_w, src_vu_addr, src_w, src_w, src_h,
dst_y_addr, dst_w, dst_vu_addr, dst_w, dst_w, dst_h, kFilterLinear);//kFilterNone
}
static int DispNV21ToARGB(char *yuv_img, char *rgb_img, int img_w, int img_h)
{
char *src_y_addr = yuv_img;
char *src_vu_addr = yuv_img + (img_w * img_h);
return NV21ToARGB(src_y_addr, img_w, src_vu_addr, img_w, rgb_img, img_w*4, img_w, img_h);
}
static void DispYV12ToNV21(char *src_img, char *dst_img, int img_w, int img_h)
{
char *dst_y_addr = dst_img;
char *dst_vu_addr = dst_img + (img_w * img_h);
char *src_y_addr = src_img;
char *src_v_addr = src_img + (img_w * img_h);
char *src_u_addr = src_img + (img_w * img_h * 5 / 4);
CopyPlane(src_y_addr, img_w, dst_y_addr, img_w, img_w, img_h);
MergeUVPlane(src_v_addr, img_w/2, src_u_addr, img_w/2, dst_vu_addr, img_w, img_w/2, img_h/2);
SINK_LOG_DEBUG("YV12 to NV21 img_w=%d, img_h=%d", img_w, img_h);
}
static int DispDrawNV21(void *hdl, char *img)
{
dispOutPort *vout_hd = (dispOutPort *)hdl;
disp_layer_t* layer = vout_hd->layer;
char * dst_addr;
char * src_addr;
int dst_width = layer->config.info.fb.size[0].width;
int dst_height = layer->config.info.fb.size[0].height;
int src_width = ALIGN_32B(vout_hd->window.width);
int src_height = vout_hd->window.height;
int dst_y_offset = vout_hd->window.x + vout_hd->window.y * dst_width;
int dst_vu_offset = vout_hd->window.x + vout_hd->window.y * dst_width/2;
char *dst_y_addr = (char *)layer->disp_buff.vir_addr + dst_y_offset;
char *dst_vu_addr = (char *)layer->disp_buff.vir_addr + dst_width * dst_height + dst_vu_offset;
char *src_y_addr = img;
char *src_vu_addr = img + src_width * src_height;
pthread_mutex_lock(g_layer_mutex);
for (int i=0; i<src_height; i++) {
dst_addr = dst_y_addr + i * (dst_width);
src_addr = src_y_addr + i * (src_width);
//SINK_LOG_DEBUG("dst_y_vir=%p, src_y_vir=%p",dst_vir_addr, src_vir_addr,i, mem_width);
memcpy(dst_addr, src_addr, vout_hd->window.width);
}
for (int i=0; i<src_height/2; i++) {
dst_addr = dst_vu_addr + i * (dst_width);
src_addr = src_vu_addr + i * (src_width);
//SINK_LOG_DEBUG("dst_y_vir=%p, src_y_vir=%p",dst_vir_addr, src_vir_addr,i, mem_width);
memcpy(dst_addr, src_addr, vout_hd->window.width);
}
pthread_mutex_unlock(g_layer_mutex);
return 0;
}
static int DispDrawYV12(void *hdl)
{
dispOutPort *vout_hd = (dispOutPort *)hdl;
disp_layer_t* layer = vout_hd->layer;
char * dst_addr;
char * src_addr;
int dst_width = layer->config.info.fb.size[0].width;
int dst_height = layer->config.info.fb.size[0].height;
int src_width = ALIGN_32B(vout_hd->window.width);
int src_height = vout_hd->window.height;
int dst_y_offset = vout_hd->window.x + vout_hd->window.y * dst_width;
int dst_uv_offset = (vout_hd->window.x*2 + vout_hd->window.y * dst_width)/4;
char *dst_y_addr = (char *)layer->disp_buff.vir_addr + dst_y_offset;
char *dst_u_addr = (char *)layer->disp_buff.vir_addr + dst_width * dst_height + dst_uv_offset;
char *dst_v_addr = (char *)layer->disp_buff.vir_addr + dst_width * dst_height * 5/4 + dst_uv_offset;
char *src_y_addr = vout_hd->yuv_img;
char *src_u_addr = vout_hd->yuv_img + src_width * src_height;
char *src_v_addr = vout_hd->yuv_img + src_width * src_height * 5 /4;
pthread_mutex_lock(g_layer_mutex);
for (int i=0; i<src_height; i++) {
dst_addr = dst_y_addr + i * (dst_width);
src_addr = src_y_addr + i * (src_width);
//SINK_LOG_DEBUG("dst_y_vir=%p, src_y_vir=%p",dst_vir_addr, src_vir_addr,i, mem_width);
memcpy(dst_addr, src_addr, vout_hd->window.width);
}
for (int i=0; i<src_height/2; i++) {
dst_addr = dst_u_addr + i * (dst_width/2);
src_addr = src_u_addr + i * (src_width/2);
memcpy(dst_addr, src_addr, vout_hd->window.width/2);
dst_addr = dst_v_addr + i * (dst_width/2);
src_addr = src_v_addr + i * (src_width/2);
memcpy(dst_addr, src_addr, vout_hd->window.width/2);
}
pthread_mutex_unlock(g_layer_mutex);
return 0;
}