linux下s5pv210 fimc实现yuv转rgb

来源:互联网 发布:linux查看tcp连接状态 编辑:程序博客网 时间:2024/04/29 03:57

首先移植安卓源码内的:v4l2_utils.c 和 v4l2_utils.h 文件。

测试程序如下:

int fd;    int w, h;    s5p_fimc_t g_s5p_fimc;    int phyAddr;    int ret, num, i, first;    void *frame_virt_base[4];    int frame_virt_len[4];    int frame_phy_base[4];    char *yuv_buffer;    int yuv_size;    w = 320;    h = 240;    num = 1;    fd = v4l2_overlay_open("/dev/video1");//打开fimc    v4l2_overlay_init_fimc(fd, &g_s5p_fimc);    g_s5p_fimc.params.src.full_width = w;    g_s5p_fimc.params.src.full_height = h;    g_s5p_fimc.params.src.width = w;    g_s5p_fimc.params.src.height = h;    g_s5p_fimc.params.src.color_space = V4L2_PIX_FMT_YUYV;//设置输入格式    ret = check_fimc_src_constraints(&g_s5p_fimc);    if(ret != 0) {        if(ret < 0) {            DBG("Not supported source image size");        } else {            DBG("src width, height are changed [w= %d, h= %d]->[w=%d, h= %d]\n"                    , w, h, g_s5p_fimc.params.src.width                    , g_s5p_fimc.params.src.height);            w = g_s5p_fimc.params.src.width;            h = g_s5p_fimc.params.src.height;        }    }    if (v4l2_overlay_init(fd, w, h, g_s5p_fimc.params.src.color_space, phyAddr)) {        DBG("Failed initializing overlays\n");    }    if (v4l2_overlay_set_crop(fd, 0, 0, w, h)) {        DBG("Failed defaulting crop window\n");    }    if (v4l2_overlay_set_flip(fd, 0)) {        DBG("Failed defaulting flip\n");    }    if (v4l2_overlay_set_rotation(fd, 0, 0)) {        DBG("Failed defaulting rotation\n");    }    //v4l2_overlay_set_global_alpha(fd, 1, 0xff);    if (v4l2_overlay_req_buf(fd, &num, 0, 0)) { //V4L2_MEMORY_MMAP  设置内存初始化,分配内存        DBG("Failed requesting buffers\n");    }    for(i = 0; i < num; i++){        ret = v4l2_overlay_map_buf(fd, i, &frame_virt_base[i], &frame_virt_len[i]);//获得内存接口        if(ret < 0){            DBG("mmap buffer %d error\n", i);        }        memset(frame_virt_base[i], 0x0, frame_virt_len[i]);    }    if(0){        struct v4l2_control control;        memset(&control, 0, sizeof(struct v4l2_control));;        control.id = V4L2_CID_OVERLAY_AUTO;        control.value = 1;        if(ioctl(fd, VIDIOC_S_CTRL, &control) < 0){            perror("VIDIOC_S_CTRL");        }    }    v4l2_overlay_set_position(fd, 0, 0, w, h, 0);        i = 0;    phyAddr = 0;    first = 0;    yuv_buffer = malloc(320*240*2);    {        int fp;        fp = open("test.yuv", O_RDWR, 0655);//打开YUV图片        if(fp > 0){            yuv_size = read(fp, yuv_buffer, 320*240*2);            printf("------------------>yuv_size = %d\n", yuv_size);            close(fp);        }    }           int index = 0;                struct timeval t, d;        int rgb_phy_addr = 0x40000000;        void * rgb_vir_addr;        int len;       printf("hello!\n");int fd_men = open("/dev/mem", O_RDWR|O_SYNC);  if (fd_men == -1)  {  return (-1);  }  //物理地址转虚拟地址  rgb_vir_addr = mmap(NULL, (320*240*4), PROT_READ|PROT_WRITE, MAP_SHARED, fd_men, rgb_phy_addr);  memset(rgb_vir_addr, 0, (320*240*4));                                gettimeofday(&d, NULL);        memcpy(frame_virt_base[index], yuv_buffer, 320*240*2);        v4l2_overlay_stream_off(fd);        v4l2_overlay_s_fbuf(fd, 0, rgb_phy_addr);//设置输出格式与输出地址        v4l2_overlay_stream_on(fd);        //DBG("Q buffer\n");    v4l2_overlay_q_buf(fd, index, 0);        sleep(1);        if(v4l2_overlay_dq_buf(fd, &index, 0) == 0){            gettimeofday(&t, NULL);            DBG("DQ buffer OK %d, %dms\n", phyAddr++, (t.tv_sec - d.tv_sec) * 1000 + (t.tv_usec - d.tv_usec) / 1000);        }else{            DBG("DQ buffer error\n");        } int fd_rgb = open("test.rgb32",O_RDWR | O_CREAT | O_TRUNC );//保存一张图ret = write(fd_rgb,rgb_vir_addr,320*240*4);close(fd);close(fd_men);close(fd_rgb);    return 0;}
实现了将一张yuv图片转换为rgb图片。

0 0
原创粉丝点击