Browse Source

Linux_SDK_V1.1.2

thead_admin 1 year ago
parent
commit
7f90ed1091

+ 43 - 59
examples/camera/cam_demo_dual_ir.c

@@ -17,7 +17,7 @@
 #define LOG_PREFIX "cam_demo_dual_ir"
 #include <syslog.h>
 
-#include <csi_frame.h>
+#include <csi_frame_ex.h>
 #include <csi_camera.h>
 #include <csi_camera_dev_api.h>
 #include "list.h"
@@ -72,7 +72,7 @@ typedef struct{
 typedef struct camera_sync_msg{
     cam_sync_message_type_e  type;
     union{
-        csi_frame_s  frame;
+        csi_frame_ex_s  frame;
         cam_ai_info_t ai_info;
         cam_dsp_info_t  dsp_info;
     };
@@ -193,7 +193,7 @@ typedef struct dual_dsp_handle{
 int file_id = 0;
 extern void *vi_plink_create(csi_camera_channel_cfg_s *chn_cfg);
 extern void vi_plink_release(void * plink);
-extern void display_camera_frame(void * plink, csi_frame_s *frame);
+extern void display_camera_frame(void * plink, csi_frame_ex_s *frame);
 
 static void *cam_frame_sync_process(void *ctx);
 static void* dsp_dual_ir_porcess(void *arg);
@@ -920,7 +920,7 @@ static void cam_sync_destroy(void *arg)
     free(ctx);
     LOG_O("cam sync destroy\n");
 }
-static int push_new_frame(struct list_head *frame_list, csi_frame_s * new_frame)
+static int push_new_frame(struct list_head *frame_list, csi_frame_ex_s * new_frame)
 {
     int entry_num =0;
     frame_item_t *frame_item = NULL;
@@ -936,8 +936,8 @@ static int push_new_frame(struct list_head *frame_list, csi_frame_s * new_frame)
     if((entry_num+1)>MAX_FIFO_FRAME_NUM)
     {
         frame_item = list_first_entry(frame_list,frame_item_t,head);
-        LOG_D("release frame fd:%d\n",((csi_frame_s *)frame_item->item)->img.fds[0]);
-        csi_camera_put_frame((csi_frame_s *)frame_item->item);
+        LOG_D("release frame fd:%d\n",((csi_frame_ex_s *)frame_item->item)->frame_data.fd[0]);
+        csi_camera_put_frame((csi_frame_ex_s *)frame_item->item);
         free(frame_item->item);
         list_del(&frame_item->head);
         free(frame_item);
@@ -948,9 +948,9 @@ static int push_new_frame(struct list_head *frame_list, csi_frame_s * new_frame)
     return 0;
 }
 
-static csi_frame_s * pop_matched_frame_with_fd(struct list_head *frame_list,int fd)
+static csi_frame_ex_s * pop_matched_frame_with_fd(struct list_head *frame_list,int fd)
 {
-    csi_frame_s *  frame = NULL;
+    csi_frame_ex_s *  frame = NULL;
     frame_item_t *frame_item = NULL;
     frame_item_t * temp;
     if(frame_list==NULL)
@@ -958,12 +958,12 @@ static csi_frame_s * pop_matched_frame_with_fd(struct list_head *frame_list,int
         return NULL;
     }
     list_for_each_entry_safe(frame_item,temp,frame_list,head){
-        frame = (csi_frame_s *)frame_item->item;
-        if(frame->img.fds[0]==fd)
+        frame = (csi_frame_ex_s *)frame_item->item;
+        if(frame->frame_data.fd[0]==fd)
         {
             list_del(&frame_item->head);
             free(frame_item);
-            LOG_D("get frame fd:%d\n",frame->img.fds[0]);
+            LOG_D("get frame fd:%d\n",frame->frame_data.fd[0]);
             return frame;
         }
     }
@@ -971,11 +971,11 @@ static csi_frame_s * pop_matched_frame_with_fd(struct list_head *frame_list,int
 }
 
 
-static csi_frame_s * pop_matched_frame_with_ts(struct list_head *frame_list, csi_frame_s * target_frame,uint32_t rang_us,bool clear_early)
+static csi_frame_ex_s * pop_matched_frame_with_ts(struct list_head *frame_list, csi_frame_ex_s * target_frame,uint32_t rang_us,bool clear_early)
 {
-    csi_camera_meta_s *meta_data = (csi_camera_meta_s *)target_frame->meta.data;
-	csi_camrea_meta_unit_s target_ts,loop_ts;
-     csi_frame_s *  frame;
+    csi_camera_meta_s *meta_data = (csi_camera_meta_s *)target_frame->frame_meta.data;
+	csi_camera_meta_unit_s target_ts,loop_ts;
+     csi_frame_ex_s *  frame;
     frame_item_t *frame_item = NULL;
     frame_item_t * tmp;
     struct timeval  time_value;
@@ -994,8 +994,8 @@ static csi_frame_s * pop_matched_frame_with_ts(struct list_head *frame_list, csi
     target_us = target_ts.time_value.tv_sec*1000000 + target_ts.time_value.tv_usec;
 
     list_for_each_entry_safe(frame_item,tmp,frame_list,head){
-            frame = ( csi_frame_s *)frame_item->item;
-            meta_data = (csi_camera_meta_s *)frame->meta.data;
+            frame = ( csi_frame_ex_s *)frame_item->item;
+            meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
             csi_camera_frame_get_meta_unit(
 	    	&loop_ts, meta_data, CSI_CAMERA_META_ID_TIMESTAMP);
             loop_us =  loop_ts.time_value.tv_sec*1000000 + loop_ts.time_value.tv_usec;
@@ -1018,20 +1018,20 @@ static csi_frame_s * pop_matched_frame_with_ts(struct list_head *frame_list, csi
 
 }
 
-static int send_paired_frame_to_dsp(msg_queue_ctx_t *queue,csi_frame_s *master_frame,csi_frame_s *slave_frame,struct list_head *send_frames)
+static int send_paired_frame_to_dsp(msg_queue_ctx_t *queue,csi_frame_ex_s *master_frame,csi_frame_ex_s *slave_frame,struct list_head *send_frames)
 {
     dsp_dual_ir_frame_msg_t *dsp_msg_payload;
     msg_queue_item_t *dsp_msg;
     frame_item_t *main_item,*slave_item;
     csi_camera_meta_s *meta_data;
-	csi_camrea_meta_unit_s timestap;
+	csi_camera_meta_unit_s timestap;
     if(queue==NULL || master_frame==NULL || slave_frame==NULL)
     {
         return -1;
     }
     
-    if(master_frame->img.width!=slave_frame->img.width||
-        master_frame->img.height!=slave_frame->img.height)       
+    if(master_frame->frame_info.width!=slave_frame->frame_info.width||
+        master_frame->frame_info.height!=slave_frame->frame_info.height)       
         {
             LOG_E("paird frame not the same picture param\n");
             return -1;
@@ -1046,20 +1046,20 @@ static int send_paired_frame_to_dsp(msg_queue_ctx_t *queue,csi_frame_s *master_f
         free(dsp_msg);
         return -1;
     }
-    meta_data = (csi_camera_meta_s *)master_frame->meta.data;
+    meta_data = (csi_camera_meta_s *)master_frame->frame_meta.data;
     csi_camera_frame_get_meta_unit(
 		&timestap, meta_data, CSI_CAMERA_META_ID_TIMESTAMP);
 
     dsp_msg->payload = dsp_msg_payload;
 
-    dsp_msg_payload->size = master_frame->img.height*master_frame->img.strides[0];
-    dsp_msg_payload->width = master_frame->img.width;
-    dsp_msg_payload->height = master_frame->img.height;
-    dsp_msg_payload->pix_format = master_frame->img.pix_format;
-    dsp_msg_payload->master_stride = master_frame->img.strides[0];
-    dsp_msg_payload->master_fd =  master_frame->img.fds[0];
-    dsp_msg_payload->slave_fd =  slave_frame->img.fds[0];
-    dsp_msg_payload->slave_stride = slave_frame->img.strides[0];
+    dsp_msg_payload->size = master_frame->frame_info.height*master_frame->frame_data.stride[0];
+    dsp_msg_payload->width = master_frame->frame_info.width;
+    dsp_msg_payload->height = master_frame->frame_info.height;
+    dsp_msg_payload->pix_format = master_frame->frame_info.pixel_format;
+    dsp_msg_payload->master_stride = master_frame->frame_data.stride[0];
+    dsp_msg_payload->master_fd =  master_frame->frame_data.fd[0];
+    dsp_msg_payload->slave_fd =  slave_frame->frame_data.fd[0];
+    dsp_msg_payload->slave_stride = slave_frame->frame_data.stride[0];
     dsp_msg_payload->timestap = timestap.time_value.tv_sec*1000000+timestap.time_value.tv_usec;
     enqueue_msg(queue,dsp_msg);
     main_item = malloc(sizeof(frame_item_t));
@@ -1072,12 +1072,12 @@ static int send_paired_frame_to_dsp(msg_queue_ctx_t *queue,csi_frame_s *master_f
     return 0;
 }
 
-static int cam_dual_frame_process(struct list_head * pair_frame_list,struct list_head * free_frame_list, struct list_head *busy_frame_list,csi_frame_s *frame, msg_queue_ctx_t *dsp_prcoess_queue,cam_sync_message_type_e type)
+static int cam_dual_frame_process(struct list_head * pair_frame_list,struct list_head * free_frame_list, struct list_head *busy_frame_list,csi_frame_ex_s *frame, msg_queue_ctx_t *dsp_prcoess_queue,cam_sync_message_type_e type)
 {
-    csi_frame_s *new_frame = NULL;
-    csi_frame_s *pair_frame = NULL;
-    csi_frame_s *master_frame = NULL;
-    csi_frame_s *slave_frame = NULL;
+    csi_frame_ex_s *new_frame = NULL;
+    csi_frame_ex_s *pair_frame = NULL;
+    csi_frame_ex_s *master_frame = NULL;
+    csi_frame_ex_s *slave_frame = NULL;
 
     if(pair_frame_list == NULL ||free_frame_list==NULL ||busy_frame_list ==NULL || 
         frame == NULL || dsp_prcoess_queue == NULL || type >CAM_SYNC_MSG_SLAVE_FRAME)
@@ -1086,14 +1086,14 @@ static int cam_dual_frame_process(struct list_head * pair_frame_list,struct list
             return -1;
         }
 
-    new_frame = malloc(sizeof(csi_frame_s));
+    new_frame = malloc(sizeof(csi_frame_ex_s));
     if(new_frame==NULL)
     {
         LOG_E("malloc fail\n");
         csi_camera_put_frame(frame);
         return -1;
     }
-    memcpy(new_frame,frame,sizeof(csi_frame_s));
+    memcpy(new_frame,frame,sizeof(csi_frame_ex_s));
     pair_frame = pop_matched_frame_with_ts(pair_frame_list,frame,0,true);
     if(pair_frame == NULL)
     {
@@ -1117,7 +1117,7 @@ static int cam_dual_frame_process(struct list_head * pair_frame_list,struct list
         }
         if(send_paired_frame_to_dsp(dsp_prcoess_queue,master_frame,slave_frame,busy_frame_list))
         {
-            LOG_E("fail to send paired frame fd (%d,%d) to dsp\n",new_frame->img.fds[0],pair_frame->img.fds[0]);
+            LOG_E("fail to send paired frame fd (%d,%d) to dsp\n",new_frame->frame_data.fd[0],pair_frame->frame_data.fd[0]);
             csi_camera_put_frame(master_frame);
             free(master_frame);
             csi_camera_put_frame(slave_frame);
@@ -1131,8 +1131,8 @@ static int cam_dual_frame_process(struct list_head * pair_frame_list,struct list
 static void *cam_frame_sync_process(void *arg)
 {
     camera_sync_msg_t  *msg;
-    csi_frame_s * master_frame=NULL;
-    csi_frame_s * slave_frame=NULL;
+    csi_frame_ex_s * master_frame=NULL;
+    csi_frame_ex_s * slave_frame=NULL;
     struct list_head *matched_list=NULL;
     msg_queue_item_t * item;
     cam_sync_process_ctx_t *ctx =(cam_sync_process_ctx_t *)arg;
@@ -1214,7 +1214,7 @@ static int camera_get_chl_id(int env_type, int *chl_id)
 	}
 	return 0;
 }
-static int cam_send_frame_to_sync_process(msg_queue_ctx_t *queue,csi_frame_s *frame, cam_sync_message_type_e  type)
+static int cam_send_frame_to_sync_process(msg_queue_ctx_t *queue,csi_frame_ex_s *frame, cam_sync_message_type_e  type)
 {
     camera_sync_msg_t *msg_palyload = malloc(sizeof(camera_sync_msg_t));
     msg_queue_item_t * item=NULL;
@@ -1229,7 +1229,7 @@ static int cam_send_frame_to_sync_process(msg_queue_ctx_t *queue,csi_frame_s *fr
         return -1;
     }
     msg_palyload->type= type;
-    memcpy(&msg_palyload->frame,frame,sizeof(csi_frame_s));
+    memcpy(&msg_palyload->frame,frame,sizeof(csi_frame_ex_s));
     item->payload = msg_palyload;
     return enqueue_msg(queue,item);
 
@@ -1248,7 +1248,7 @@ static int camera_event_process(void *arg)
     type = ctx->cam_id==0?CAM_SYNC_MSG_MAIN_FRAME:CAM_SYNC_MSG_SLAVE_FRAME;
 	struct timeval cur_time;
 	struct csi_camera_event event;
-	csi_frame_s frame;
+	csi_frame_ex_s frame;
 
 	if (ev_handle == NULL) {
 		LOG_E("fail to get ev_handle ev_handle\n");
@@ -1579,22 +1579,6 @@ ONR_ERR:
     exit(0);
 }
 
-static void dump_camera_meta(csi_frame_s *frame)
-{
-	int i;
-	//printf("%s\n", __func__);
-	if (frame->meta.type != CSI_META_TYPE_CAMERA)
-		return;
-
-	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->meta.data;
-	int meta_count = meta_data->count;
-	csi_camrea_meta_unit_s meta_unit;
 
 
-	csi_camera_frame_get_meta_unit(
-		&meta_unit, meta_data, CSI_CAMERA_META_ID_FRAME_ID);
-	LOG_I("meta_id=%d, meta_type=%d, meta_value=%d\n",
-			meta_unit.id, meta_unit.type, meta_unit.int_value);
-}
-
 

+ 56 - 99
examples/camera/cam_demo_ir.c

@@ -28,8 +28,8 @@ typedef struct frame_fps {
 	struct timeval initTick;
 	float fps;
 } frame_fps_t;
-static void dump_camera_meta(csi_frame_s *frame);
-static void dump_camera_frame(csi_frame_s *frame, int ch_id);
+static void dump_camera_meta(csi_frame_ex_s *frame);
+static void dump_camera_frame(csi_frame_ex_s *frame, int ch_id);
 
 
 typedef struct event_queue_item{
@@ -92,7 +92,7 @@ static void* camera_channle_process(void* arg)
 
 	struct timeval init_time, cur_time;
     frame_fps_t demo_fps;
-    csi_frame_s frame;
+    csi_frame_ex_s frame;
 	memset(&init_time, 0, sizeof(init_time));
 	memset(&cur_time, 0, sizeof(cur_time));
     channel_handle_ctx_t * ctx = (channel_handle_ctx_t *)arg;
@@ -126,7 +126,6 @@ static void* camera_channle_process(void* arg)
 
                     // csi_camera_frame_unlock(cam_handle, &frame);
                     csi_camera_put_frame(&frame);
-					csi_frame_release(&frame);
 				}
                 unsigned  long diff;
 				if (init_time.tv_usec == 0)
@@ -550,14 +549,14 @@ int main(int argc, char *argv[])
 	csi_camera_close(cam_handle);
 }
 
-static void dump_camera_meta(csi_frame_s *frame)
+static void dump_camera_meta(csi_frame_ex_s *frame)
 {
 	int i;
-	if (frame->meta.type != CSI_META_TYPE_CAMERA)
+	if (frame->frame_meta.type != CSI_META_TYPE_CAMERA)
 		return;
 
-	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->meta.data;
-	csi_camrea_meta_unit_s meta_frame_id,meta_frame_ts;
+	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
+	csi_camera_meta_unit_s meta_frame_id,meta_frame_ts;
 
 
 	csi_camera_frame_get_meta_unit(
@@ -567,138 +566,96 @@ static void dump_camera_meta(csi_frame_s *frame)
 	LOG_O("meta frame id=%d,time stap:(%ld,%ld)\n",
 			 meta_frame_id.int_value,meta_frame_ts.time_value.tv_sec,meta_frame_ts.time_value.tv_usec);
 }
-
-static void dump_camera_frame(csi_frame_s *frame,  int ch_id)
+int file_id = 0;
+static void dump_camera_frame(csi_frame_ex_s *frame, int ch_id)
 {
 	char file[128];
 	static int file_indx=0;
-	int size,buf_size;
+	int size;
 	uint32_t indexd, j;
-    void *buf[3];
+	void *buf[3]={NULL,NULL,NULL};
+    int buf_size;
+	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
+	csi_camera_meta_unit_s meta_unit;
 
-	sprintf(file,"demo_save_img_ch_%d_%d", ch_id,file_indx++%6);
+	csi_camera_frame_get_meta_unit(&meta_unit, meta_data, CSI_CAMERA_META_ID_CAMERA_NAME);
+
+	sprintf(file, "demo_save_img_%s_ch%d_%d_%d", meta_unit.str_value, ch_id,file_id, file_indx++%10);
 	int fd = open(file, O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR | S_IROTH);
 	if(fd == -1) {
 		LOG_E("%s, %d, open file error!!!!!!!!!!!!!!!\n", __func__, __LINE__);
-		return ;
+		return;
 	}
-    if (frame->img.type == CSI_IMG_TYPE_DMA_BUF) {
-
-        buf_size = frame->img.strides[0]*frame->img.height;
-        switch(frame->img.pix_format) {
-                case CSI_PIX_FMT_NV12:
-		        case CSI_PIX_FMT_YUV_SEMIPLANAR_420:
-                        if(frame->img.num_planes ==2)
-                        { 
-                            buf_size+=frame->img.strides[1]*frame->img.height/2;
-                        }
-                        else{
-                            LOG_E("img fomrat is not match with frame planes:%d\n",frame->img.num_planes);
-                            return;
-                        }
-                        break;
-                case CSI_PIX_FMT_YUV_SEMIPLANAR_422:
-                        if(frame->img.num_planes ==2)
-                        { 
-                            buf_size+=frame->img.strides[1]*frame->img.height;
-                        }
-                        else{
-                            LOG_E("img fomrat is not match with frame planes:%d\n",frame->img.num_planes);
-                            return;
-                        }
-                        break;
-                default:
-                        break;
-                
-        }
 
-        buf[0]= mmap(0, buf_size, PROT_READ | PROT_WRITE,
-                    MAP_SHARED, frame->img.dmabuf[0].fds, frame->img.dmabuf[0].offset);
-        // plane_size[1] = frame->img.strides[1]*frame->img.height;
-        // printf("frame plane 1 stride:%d,offset:%d\n", frame->img.strides[1],(uint32_t)frame->img.dmabuf[1].offset);
-        if(frame->img.num_planes ==2)
-        {
-            // buf[1] = mmap(0, plane_size[1]/2, PROT_READ | PROT_WRITE,
-            //             MAP_SHARED, frame->img.dmabuf[1].fds, frame->img.dmabuf[1].offset);
-            buf[1] = buf[0]+frame->img.dmabuf[1].offset;
-        }
-
-    }
-    else{
-            buf[0] = frame->img.usr_addr[0];
-            buf[1] = frame->img.usr_addr[1];
+    for(j =0;j<frame->frame_data.num_plane;j++)
+    {
+        buf[j] = frame->frame_data.vir_addr[j];
     }
 
-	LOG_O("save img from :%d, to %s, fmt:%d width:%d stride:%d height:%d\n",frame->img.dmabuf[0].fds, file, frame->img.pix_format , frame->img.width, frame->img.strides[0], frame->img.height);
-    frame->img.pix_format = CSI_PIX_FMT_RAW_12BIT;
-	switch(frame->img.pix_format) {
+	LOG_I("save img from: addr:%p,to %s, fd:%d,fmt:%d width:%d stride:%d height:%d\n", buf[0], file, frame->frame_data.fd[0], 
+            frame->frame_info.pixel_format, frame->frame_info.width, frame->frame_data.stride[0], frame->frame_info.height);
+
+	switch(frame->frame_info.pixel_format) {
 		case CSI_PIX_FMT_NV12:
 		case CSI_PIX_FMT_YUV_SEMIPLANAR_420:
-            if (frame->img.strides[0] == 0) {
-				frame->img.strides[0] = frame->img.width;
-			}
-			for (j = 0; j < frame->img.height; j++) { //Y
-				indexd = j*frame->img.strides[0];
-				write(fd, buf[0] + indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height; j++) { //Y
+				indexd = j*frame->frame_data.stride[0];
+				write(fd, buf[0] + indexd, frame->frame_info.width);
 			}
-			for (j = 0; j < frame->img.height / 2; j++) { //UV
-				indexd = j*frame->img.strides[0];
-				write(fd, buf[1] + indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height / 2; j++) { //UV
+				indexd = j*frame->frame_data.stride[0];
+				write(fd, buf[1] + indexd, frame->frame_info.width);
 			}
 			break;
 		case CSI_PIX_FMT_RGB_INTEVLEAVED_888:
 		case CSI_PIX_FMT_YUV_TEVLEAVED_444:
-            size = frame->img.width*3;
-            for (j = 0; j < frame->img.height; j++) {
-				indexd = j*frame->img.strides[0];
+			size = frame->frame_info.width*3;
+			for (j = 0; j < frame->frame_info.height; j++) {
+				indexd = j*frame->frame_data.stride[0];
 				write(fd, buf[0] + indexd, size);
 			}
 			break;
 		case CSI_PIX_FMT_BGR:
 		case CSI_PIX_FMT_RGB_PLANAR_888:
 		case CSI_PIX_FMT_YUV_PLANAR_444:
-			size = frame->img.width * frame->img.height * 3;
+			size = frame->frame_info.width * frame->frame_info.height * 3;
 			write(fd, buf[0], size);
 			break;
-        case CSI_PIX_FMT_RAW_8BIT:
-            size = frame->img.width;
-            for (j = 0; j < frame->img.height; j++) {
-				indexd = j*frame->img.strides[0];
+		case CSI_PIX_FMT_RAW_8BIT:
+			size = frame->frame_info.width;
+			for (j = 0; j < frame->frame_info.height; j++) {
+				indexd = j*frame->frame_data.stride[0];
 				write(fd, buf[0] + indexd, size);
 			}
 			break;
 		case CSI_PIX_FMT_YUV_TEVLEAVED_422:
-        case CSI_PIX_FMT_RAW_10BIT:
-	    case CSI_PIX_FMT_RAW_12BIT:
-	    case CSI_PIX_FMT_RAW_14BIT:
-	    case CSI_PIX_FMT_RAW_16BIT:
-            size = frame->img.width*2;
-            for (j = 0; j < frame->img.height; j++) {
-				indexd = j*frame->img.strides[0];
+		case CSI_PIX_FMT_RAW_10BIT:
+		case CSI_PIX_FMT_RAW_12BIT:
+		case CSI_PIX_FMT_RAW_14BIT:
+		case CSI_PIX_FMT_RAW_16BIT:
+			size = frame->frame_info.width*2;
+			for (j = 0; j < frame->frame_info.height; j++) {
+				indexd = j*frame->frame_data.stride[0];
 				write(fd, buf[0] + indexd, size);
 			}
 			break;
 		case CSI_PIX_FMT_YUV_SEMIPLANAR_422:
-			if (frame->img.strides[0] == 0) {
-				frame->img.strides[0] = frame->img.width;
+			if (frame->frame_data.stride[0] == 0) {
+				frame->frame_data.stride[0] = frame->frame_info.width;
 			}
-			for (j = 0; j < frame->img.height; j++) { //Y
-				indexd = j*frame->img.strides[0];
-				write(fd,buf[0] + indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height; j++) { //Y
+				indexd = j*frame->frame_data.stride[0];
+				write(fd,buf[0] + indexd, frame->frame_info.width);
 			}
-			for (j = 0; j < frame->img.height; j++) { //UV
-				indexd = j*frame->img.strides[0];
-				write(fd, buf[1]+ indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height; j++) { //UV
+				indexd = j*frame->frame_data.stride[0];
+				write(fd, buf[1]+ indexd, frame->frame_info.width);
 			}
 			break;
 		default:
-			LOG_E("%s unsupported format to save\n", __func__);
-			exit(-1);
+			LOG_E("%s unsupported format to save\n", __func__);			
 			break;
 	}
 
 	close(fd);
-    munmap(buf[0],buf_size);
-    // munmap(buf[1],plane_size[1]);
-	LOG_O("%s exit\n", __func__);
-}
+}

+ 53 - 103
examples/camera/cam_demo_multi.c

@@ -26,8 +26,8 @@
 #endif
 #define  MAX_CAM_NUM    3
 #define  MAX_CHANNEL_NUM 3 
-static void dump_camera_meta(csi_frame_s *frame);
-static void dump_camera_frame(csi_frame_s *frame, csi_pixel_fmt_e fmt, int camera_id);
+static void dump_camera_meta(csi_frame_ex_s *frame);
+static void dump_camera_frame(csi_frame_ex_s *frame, int ch_id);
 
 // extern int csi_camera_frame_unlock(csi_cam_handle_t cam_handle, csi_frame_s *frame);
 
@@ -94,7 +94,7 @@ typedef struct _camera_ctx{
 int file_id = 0;
 extern void *vi_plink_create(csi_camera_channel_cfg_s *chn_cfg);
 extern void vi_plink_release(void * plink);
-extern void display_camera_frame(void * plink, csi_frame_s *frame);
+extern void display_camera_frame(void * plink, csi_frame_ex_s *frame);
 
 static void usage(void)
 {
@@ -255,7 +255,7 @@ static void *camera_event_thread(void *arg)
 
 	frame_fps_t demo_fps;
 	memset(&demo_fps, 0, sizeof(demo_fps));
-	csi_frame_s frame;
+	csi_frame_ex_s frame;
 
 	if (ev_handle == NULL) {
 		LOG_E("fail to get ev_handle ev_handle\n");
@@ -314,10 +314,10 @@ static void *camera_event_thread(void *arg)
 					csi_camera_get_frame(ctx->cam_handle, chn_id, &frame, timeout);
 					dump_camera_meta(&frame);
 					if (ctx->frame_mode[chn_id] == FRAME_SAVE_IMG) {
-						dump_camera_frame(&frame, ch_cfg->img_fmt.pix_fmt, chn_id);
+						dump_camera_frame(&frame, chn_id);
 					}
 					if (ctx->disaply_plink && ctx->frame_mode[chn_id]==FRAME_SAVE_DISPLAY) {
-						frame.img.pix_format = ch_cfg->img_fmt.pix_fmt;
+						
 						display_camera_frame(ctx->disaply_plink, &frame);
                     }
                     csi_camera_put_frame(&frame);
@@ -645,16 +645,16 @@ ONR_ERR:
     exit(0);
 }
 
-static void dump_camera_meta(csi_frame_s *frame)
+static void dump_camera_meta(csi_frame_ex_s *frame)
 {
 	int i;
 	//printf("%s\n", __func__);
-	if (frame->meta.type != CSI_META_TYPE_CAMERA)
+	if (frame->frame_meta.type != CSI_META_TYPE_CAMERA)
 		return;
 
-	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->meta.data;
+	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
 	int meta_count = meta_data->count;
-	csi_camrea_meta_unit_s meta_unit;
+	csi_camera_meta_unit_s meta_unit;
 
 
 	csi_camera_frame_get_meta_unit(
@@ -663,145 +663,95 @@ static void dump_camera_meta(csi_frame_s *frame)
 			meta_unit.id, meta_unit.type, meta_unit.int_value);
 }
 
-static void dump_camera_frame(csi_frame_s *frame, csi_pixel_fmt_e fmt, int chan_id)
+static void dump_camera_frame(csi_frame_ex_s *frame, int ch_id)
 {
 	char file[128];
 	static int file_indx=0;
 	int size;
 	uint32_t indexd, j;
-    void *buf[3];
+	void *buf[3]={NULL,NULL,NULL};
     int buf_size;
-    csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->meta.data;
-	csi_camrea_meta_unit_s meta_unit;
+	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
+	csi_camera_meta_unit_s meta_unit;
 
+	csi_camera_frame_get_meta_unit(&meta_unit, meta_data, CSI_CAMERA_META_ID_CAMERA_NAME);
 
-	csi_camera_frame_get_meta_unit(
-		&meta_unit, meta_data, CSI_CAMERA_META_ID_CAMERA_NAME);
-
-              
-	sprintf(file,"demo_save_img%s_%d_%d",meta_unit.str_value,chan_id, file_indx++%10);
+	sprintf(file, "demo_save_img_%s_ch%d_%d_%d", meta_unit.str_value, ch_id,file_id, file_indx++%10);
 	int fd = open(file, O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR | S_IROTH);
 	if(fd == -1) {
 		LOG_E("%s, %d, open file error!!!!!!!!!!!!!!!\n", __func__, __LINE__);
-		return ;
+		return;
 	}
-    if (frame->img.type == CSI_IMG_TYPE_DMA_BUF) {
-
-        buf_size = frame->img.strides[0]*frame->img.height;
-         switch(fmt) {
-                case CSI_PIX_FMT_NV12:
-		        case CSI_PIX_FMT_YUV_SEMIPLANAR_420:
-                        if(frame->img.num_planes ==2)
-                        { 
-                            buf_size+=frame->img.strides[1]*frame->img.height/2;
-                        }
-                        else{
-                            LOG_O("img fomrat is not match with frame planes:%d\n",frame->img.num_planes);
-                            return;
-                        }
-                        break;
-                case CSI_PIX_FMT_YUV_SEMIPLANAR_422:
-                        if(frame->img.num_planes ==2)
-                        { 
-                            buf_size+=frame->img.strides[1]*frame->img.height;
-                        }
-                        else{
-                            LOG_O("img fomrat is not match with frame planes:%d\n",frame->img.num_planes);
-                            return;
-                        }
-                        break;
-                default:
-                        break;
-                
-        }
-
-        buf[0]= mmap(0, buf_size, PROT_READ | PROT_WRITE,
-                    MAP_SHARED, frame->img.dmabuf[0].fds, frame->img.dmabuf[0].offset);
-        // plane_size[1] = frame->img.strides[1]*frame->img.height;
-        // printf("frame plane 1 stride:%d,offset:%d\n", frame->img.strides[1],(uint32_t)frame->img.dmabuf[1].offset);
-        if(frame->img.num_planes ==2)
-        {
-            // buf[1] = mmap(0, plane_size[1]/2, PROT_READ | PROT_WRITE,
-            //             MAP_SHARED, frame->img.dmabuf[1].fds, frame->img.dmabuf[1].offset);
-            buf[1] = buf[0]+frame->img.dmabuf[1].offset;
-        }
 
-    }
-    else{
-            buf[0] = frame->img.usr_addr[0];
-            buf[1] = frame->img.usr_addr[1];
+    for(j =0;j<frame->frame_data.num_plane;j++)
+    {
+        buf[j] = frame->frame_data.vir_addr[j];
     }
 
-	LOG_O("%s,save img from : (%lx,%lx)size:%d to %s, fmt:%d width:%d stride:%d height:%d\n",__FUNCTION__, (uint64_t)buf[0],(uint64_t)buf[1],size, file, fmt, frame->img.width, frame->img.strides[0], frame->img.height);
+	LOG_I("save img from: addr:%p,to %s, fd:%d,fmt:%d width:%d stride:%d height:%d\n", buf[0], file, frame->frame_data.fd[0], 
+            frame->frame_info.pixel_format, frame->frame_info.width, frame->frame_data.stride[0], frame->frame_info.height);
 
-	if (frame->img.strides[0] == 0) {
-		frame->img.strides[0] = frame->img.width;
-	}
-	switch(fmt) {
+	switch(frame->frame_info.pixel_format) {
 		case CSI_PIX_FMT_NV12:
 		case CSI_PIX_FMT_YUV_SEMIPLANAR_420:
-			for (j = 0; j < frame->img.height; j++) { //Y
-				indexd = j*frame->img.strides[0];
-				write(fd, buf[0] + indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height; j++) { //Y
+				indexd = j*frame->frame_data.stride[0];
+				write(fd, buf[0] + indexd, frame->frame_info.width);
 			}
-			for (j = 0; j < frame->img.height / 2; j++) { //UV
-				indexd = j*frame->img.strides[0];
-				write(fd, buf[1] + indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height / 2; j++) { //UV
+				indexd = j*frame->frame_data.stride[0];
+				write(fd, buf[1] + indexd, frame->frame_info.width);
 			}
 			break;
 		case CSI_PIX_FMT_RGB_INTEVLEAVED_888:
 		case CSI_PIX_FMT_YUV_TEVLEAVED_444:
-            size = frame->img.width*3;
-            for (j = 0; j < frame->img.height; j++) {
-				indexd = j*frame->img.strides[0];
+			size = frame->frame_info.width*3;
+			for (j = 0; j < frame->frame_info.height; j++) {
+				indexd = j*frame->frame_data.stride[0];
 				write(fd, buf[0] + indexd, size);
 			}
 			break;
 		case CSI_PIX_FMT_BGR:
 		case CSI_PIX_FMT_RGB_PLANAR_888:
 		case CSI_PIX_FMT_YUV_PLANAR_444:
-			size = frame->img.width * frame->img.height * 3;
+			size = frame->frame_info.width * frame->frame_info.height * 3;
 			write(fd, buf[0], size);
 			break;
-        case CSI_PIX_FMT_RAW_8BIT:
-            size = frame->img.width;
-            for (j = 0; j < frame->img.height; j++) {
-				indexd = j*frame->img.strides[0];
+		case CSI_PIX_FMT_RAW_8BIT:
+			size = frame->frame_info.width;
+			for (j = 0; j < frame->frame_info.height; j++) {
+				indexd = j*frame->frame_data.stride[0];
 				write(fd, buf[0] + indexd, size);
 			}
 			break;
 		case CSI_PIX_FMT_YUV_TEVLEAVED_422:
-        case CSI_PIX_FMT_RAW_10BIT:
-	    case CSI_PIX_FMT_RAW_12BIT:
-	    case CSI_PIX_FMT_RAW_14BIT:
-	    case CSI_PIX_FMT_RAW_16BIT:
-            size = frame->img.width*2;
-            for (j = 0; j < frame->img.height; j++) {
-				indexd = j*frame->img.strides[0];
+		case CSI_PIX_FMT_RAW_10BIT:
+		case CSI_PIX_FMT_RAW_12BIT:
+		case CSI_PIX_FMT_RAW_14BIT:
+		case CSI_PIX_FMT_RAW_16BIT:
+			size = frame->frame_info.width*2;
+			for (j = 0; j < frame->frame_info.height; j++) {
+				indexd = j*frame->frame_data.stride[0];
 				write(fd, buf[0] + indexd, size);
 			}
 			break;
 		case CSI_PIX_FMT_YUV_SEMIPLANAR_422:
-			if (frame->img.strides[0] == 0) {
-				frame->img.strides[0] = frame->img.width;
+			if (frame->frame_data.stride[0] == 0) {
+				frame->frame_data.stride[0] = frame->frame_info.width;
 			}
-			for (j = 0; j < frame->img.height; j++) { //Y
-				indexd = j*frame->img.strides[0];
-				write(fd,buf[0] + indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height; j++) { //Y
+				indexd = j*frame->frame_data.stride[0];
+				write(fd,buf[0] + indexd, frame->frame_info.width);
 			}
-			for (j = 0; j < frame->img.height; j++) { //UV
-				indexd = j*frame->img.strides[0];
-				write(fd, buf[1]+ indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height; j++) { //UV
+				indexd = j*frame->frame_data.stride[0];
+				write(fd, buf[1]+ indexd, frame->frame_info.width);
 			}
 			break;
 		default:
-			LOG_E("%s unsupported format to save\n", __func__);
-			exit(-1);
+			LOG_E("%s unsupported format to save\n", __func__);			
 			break;
 	}
 
 	close(fd);
-    munmap(buf[0],buf_size);
-    // munmap(buf[1],plane_size[1]);
-	LOG_O("%s exit\n", __func__);
 }

+ 54 - 106
examples/camera/cam_demo_simple.c

@@ -17,7 +17,7 @@
 #define LOG_PREFIX "cam_demo_simple"
 #include <syslog.h>
 
-#include <csi_frame.h>
+#include <csi_frame_ex.h>
 #include <csi_camera.h>
 #include "csi_camera_dev_api.h"
 // #include "vi_mem.h"
@@ -25,8 +25,8 @@
 #include "apputilities.h"
 #endif
 
-static void dump_camera_meta(csi_frame_s *frame);
-static void dump_camera_frame(csi_frame_s *frame, csi_pixel_fmt_e fmt);
+static void dump_camera_meta(csi_frame_ex_s *frame);
+static void dump_camera_frame(csi_frame_ex_s *frame, int ch_id);
 
 
 #define TEST_DEVICE_NAME "/dev/video0"
@@ -102,7 +102,7 @@ static void get_system_time(const char *func, int line_num)
 int file_id = 0;
 extern void *vi_plink_create(csi_camera_channel_cfg_s *chn_cfg);
 extern void vi_plink_release(void * plink);
-extern void display_camera_frame(void * plink, csi_frame_s *frame);
+extern void display_camera_frame(void * plink, csi_frame_ex_s *frame);
 int main(int argc, char *argv[])
 {
 	bool running = true;
@@ -452,7 +452,7 @@ int main(int argc, char *argv[])
 	}
     get_system_time(__func__, __LINE__);
 	// 处理订阅的Event
-	csi_frame_s frame;
+	csi_frame_ex_s frame;
 	struct csi_camera_event event;
 
 	while (running) {
@@ -524,17 +524,15 @@ int main(int argc, char *argv[])
 					dump_camera_meta(&frame);
 					chn_cfg.chn_id = chn_id;
 					csi_camera_channel_query(cam_handle, &chn_cfg);
-					frame.img.pix_format = chn_cfg.img_fmt.pix_fmt;
 
 					if (dump_enable) {
-						dump_camera_frame(&frame, chn_cfg.img_fmt.pix_fmt);
+						dump_camera_frame(&frame, chn_id);
 					}
 					if (display_enable == 1) {
                         display_camera_frame(display_plink, &frame);
                         continue;
                     }
                     csi_camera_put_frame(&frame);
-					csi_frame_release(&frame);
 				}
 				break;
 			}
@@ -563,16 +561,16 @@ int main(int argc, char *argv[])
     }
 }
 
-static void dump_camera_meta(csi_frame_s *frame)
+static void dump_camera_meta(csi_frame_ex_s *frame)
 {
 	int i;
 
-	if (frame->meta.type != CSI_META_TYPE_CAMERA)
+	if (frame->frame_meta.type != CSI_META_TYPE_CAMERA)
 		return;
 
-	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->meta.data;
+	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
 	int meta_count = meta_data->count;
-	csi_camrea_meta_unit_s meta_unit;
+	csi_camera_meta_unit_s meta_unit;
 
 
 	csi_camera_frame_get_meta_unit(
@@ -581,145 +579,95 @@ static void dump_camera_meta(csi_frame_s *frame)
 			meta_unit.id, meta_unit.type, meta_unit.int_value);
 }
 
-static void dump_camera_frame(csi_frame_s *frame, csi_pixel_fmt_e fmt)
+static void dump_camera_frame(csi_frame_ex_s *frame, int ch_id)
 {
 	char file[128];
 	static int file_indx=0;
 	int size;
 	uint32_t indexd, j;
-    void *buf[3];
+	void *buf[3]={NULL,NULL,NULL};
     int buf_size;
-    csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->meta.data;
-	csi_camrea_meta_unit_s meta_unit;
+	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
+	csi_camera_meta_unit_s meta_unit;
 
+	csi_camera_frame_get_meta_unit(&meta_unit, meta_data, CSI_CAMERA_META_ID_CAMERA_NAME);
 
-	csi_camera_frame_get_meta_unit(
-		&meta_unit, meta_data, CSI_CAMERA_META_ID_CAMERA_NAME);
-
-              
-	sprintf(file,"demo_save_img%s_%d_%d",meta_unit.str_value,file_id, file_indx++%10);
+	sprintf(file, "demo_save_img_%s_ch%d_%d_%d", meta_unit.str_value, ch_id,file_id, file_indx++%10);
 	int fd = open(file, O_RDWR | O_CREAT | O_TRUNC, S_IRUSR | S_IWUSR | S_IROTH);
 	if(fd == -1) {
 		LOG_E("%s, %d, open file error!!!!!!!!!!!!!!!\n", __func__, __LINE__);
-		return ;
+		return;
 	}
-    if (frame->img.type == CSI_IMG_TYPE_DMA_BUF) {
-
-        buf_size = frame->img.strides[0]*frame->img.height;
-        switch(fmt) {
-                case CSI_PIX_FMT_NV12:
-		        case CSI_PIX_FMT_YUV_SEMIPLANAR_420:
-                        if(frame->img.num_planes ==2)
-                        { 
-                            buf_size+=frame->img.strides[1]*frame->img.height/2;
-                        }
-                        else{
-                            LOG_E("img fomrat is not match with frame planes:%d\n",frame->img.num_planes);
-                            return;
-                        }
-                        break;
-                case CSI_PIX_FMT_YUV_SEMIPLANAR_422:
-                        if(frame->img.num_planes ==2)
-                        { 
-                            buf_size+=frame->img.strides[1]*frame->img.height;
-                        }
-                        else{
-                            LOG_E("img fomrat is not match with frame planes:%d\n",frame->img.num_planes);
-                            return;
-                        }
-                        break;
-                default:
-                        break;
-                
-        }
-
-        buf[0]= mmap(0, buf_size, PROT_READ | PROT_WRITE,
-                    MAP_SHARED, frame->img.dmabuf[0].fds, frame->img.dmabuf[0].offset);
-        // plane_size[1] = frame->img.strides[1]*frame->img.height;
-        // printf("frame plane 1 stride:%d,offset:%d\n", frame->img.strides[1],(uint32_t)frame->img.dmabuf[1].offset);
-        if(frame->img.num_planes ==2)
-        {
-            // buf[1] = mmap(0, plane_size[1]/2, PROT_READ | PROT_WRITE,
-            //             MAP_SHARED, frame->img.dmabuf[1].fds, frame->img.dmabuf[1].offset);
-            buf[1] = buf[0]+frame->img.dmabuf[1].offset;
-        }
 
-    }
-    else{
-            buf[0] = frame->img.usr_addr[0];
-            buf[1] = frame->img.usr_addr[1];
+    for(j =0;j<frame->frame_data.num_plane;j++)
+    {
+        buf[j] = frame->frame_data.vir_addr[j];
     }
 
-	LOG_O("%s,save img from : (%lx,%lx)size:%d to %s, fmt:%d width:%d stride:%d height:%d\n",__FUNCTION__, (uint64_t)buf[0],(uint64_t)buf[1],size, file, fmt, frame->img.width, frame->img.strides[0], frame->img.height);
+	LOG_I("save img from: addr:%p,to %s, fd:%d,fmt:%d width:%d stride:%d height:%d\n", buf[0], file, frame->frame_data.fd[0], 
+            frame->frame_info.pixel_format, frame->frame_info.width, frame->frame_data.stride[0], frame->frame_info.height);
 
-	if (frame->img.strides[0] == 0) {
-		frame->img.strides[0] = frame->img.width;
-	}
-	switch(fmt) {
+	switch(frame->frame_info.pixel_format) {
 		case CSI_PIX_FMT_NV12:
 		case CSI_PIX_FMT_YUV_SEMIPLANAR_420:
-			for (j = 0; j < frame->img.height; j++) { //Y
-				indexd = j*frame->img.strides[0];
-				write(fd, buf[0] + indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height; j++) { //Y
+				indexd = j*frame->frame_data.stride[0];
+				write(fd, buf[0] + indexd, frame->frame_info.width);
 			}
-			for (j = 0; j < frame->img.height / 2; j++) { //UV
-				indexd = j*frame->img.strides[0];
-				write(fd, buf[1] + indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height / 2; j++) { //UV
+				indexd = j*frame->frame_data.stride[0];
+				write(fd, buf[1] + indexd, frame->frame_info.width);
 			}
 			break;
 		case CSI_PIX_FMT_RGB_INTEVLEAVED_888:
 		case CSI_PIX_FMT_YUV_TEVLEAVED_444:
-            size = frame->img.width*3;
-            for (j = 0; j < frame->img.height; j++) {
-				indexd = j*frame->img.strides[0];
+			size = frame->frame_info.width*3;
+			for (j = 0; j < frame->frame_info.height; j++) {
+				indexd = j*frame->frame_data.stride[0];
 				write(fd, buf[0] + indexd, size);
 			}
 			break;
 		case CSI_PIX_FMT_BGR:
 		case CSI_PIX_FMT_RGB_PLANAR_888:
 		case CSI_PIX_FMT_YUV_PLANAR_444:
-			size = frame->img.width * frame->img.height * 3;
+			size = frame->frame_info.width * frame->frame_info.height * 3;
 			write(fd, buf[0], size);
 			break;
-        case CSI_PIX_FMT_RAW_8BIT:
-            size = frame->img.width;
-            for (j = 0; j < frame->img.height; j++) {
-				indexd = j*frame->img.strides[0];
+		case CSI_PIX_FMT_RAW_8BIT:
+			size = frame->frame_info.width;
+			for (j = 0; j < frame->frame_info.height; j++) {
+				indexd = j*frame->frame_data.stride[0];
 				write(fd, buf[0] + indexd, size);
 			}
 			break;
 		case CSI_PIX_FMT_YUV_TEVLEAVED_422:
-        case CSI_PIX_FMT_RAW_10BIT:
-	    case CSI_PIX_FMT_RAW_12BIT:
-	    case CSI_PIX_FMT_RAW_14BIT:
-	    case CSI_PIX_FMT_RAW_16BIT:
-            size = frame->img.width*2;
-            for (j = 0; j < frame->img.height; j++) {
-				indexd = j*frame->img.strides[0];
+		case CSI_PIX_FMT_RAW_10BIT:
+		case CSI_PIX_FMT_RAW_12BIT:
+		case CSI_PIX_FMT_RAW_14BIT:
+		case CSI_PIX_FMT_RAW_16BIT:
+			size = frame->frame_info.width*2;
+			for (j = 0; j < frame->frame_info.height; j++) {
+				indexd = j*frame->frame_data.stride[0];
 				write(fd, buf[0] + indexd, size);
 			}
 			break;
 		case CSI_PIX_FMT_YUV_SEMIPLANAR_422:
-			if (frame->img.strides[0] == 0) {
-				frame->img.strides[0] = frame->img.width;
+			if (frame->frame_data.stride[0] == 0) {
+				frame->frame_data.stride[0] = frame->frame_info.width;
 			}
-			for (j = 0; j < frame->img.height; j++) { //Y
-				indexd = j*frame->img.strides[0];
-				write(fd,buf[0] + indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height; j++) { //Y
+				indexd = j*frame->frame_data.stride[0];
+				write(fd,buf[0] + indexd, frame->frame_info.width);
 			}
-			for (j = 0; j < frame->img.height; j++) { //UV
-				indexd = j*frame->img.strides[0];
-				write(fd, buf[1]+ indexd, frame->img.width);
+			for (j = 0; j < frame->frame_info.height; j++) { //UV
+				indexd = j*frame->frame_data.stride[0];
+				write(fd, buf[1]+ indexd, frame->frame_info.width);
 			}
 			break;
 		default:
-			LOG_E("%s unsupported format to save\n", __func__);
-			exit(-1);
+			LOG_E("%s unsupported format to save\n", __func__);			
 			break;
 	}
 
 	close(fd);
-    munmap(buf[0],buf_size);
-    // munmap(buf[1],plane_size[1]);
-	LOG_O("%s exit\n", __func__);
-}
+}

+ 6 - 6
examples/camera/camera_demo1.c

@@ -23,7 +23,7 @@
 #include "platform_action.h"
 #endif
 
-static void dump_camera_meta(csi_frame_s *frame);
+static void dump_camera_meta(csi_frame_ex_s *frame);
 
 //#define TEST_DEVICE_NAME "/dev/fake"
 #define TEST_DEVICE_NAME "/dev/video0"
@@ -222,7 +222,7 @@ int main(int argc, char *argv[])
 	csi_camera_channel_start(cam_handle, CSI_CAMERA_CHANNEL_0);
 
 	// 处理订阅的Event
-	csi_frame_s frame;
+	csi_frame_ex_s frame;
 	struct csi_camera_event event;
 
 	while (running) {
@@ -283,15 +283,15 @@ int main(int argc, char *argv[])
 	csi_camera_close(cam_handle);
 }
 
-static void dump_camera_meta(csi_frame_s *frame)
+static void dump_camera_meta(csi_frame_ex_s *frame)
 {
 	int i;
-	if (frame->meta.type != CSI_META_TYPE_CAMERA)
+	if (frame->frame_meta.type != CSI_META_TYPE_CAMERA)
 		return;
 
-	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->meta.data;
+	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
 	int meta_count = meta_data->count;
-	csi_camrea_meta_unit_s meta_unit;
+	csi_camera_meta_unit_s meta_unit;
 
 	for (i = 0; i < meta_count; i++) {
 		csi_camera_frame_get_meta_unit(

+ 8 - 8
examples/camera/camera_demo2.c

@@ -24,7 +24,7 @@
 #include "platform_action.h"
 #endif
 
-static void dump_camera_meta(csi_frame_s *frame);
+static void dump_camera_meta(csi_frame_ex_s *frame);
 
 #define TEST_DEVICE_NAME "/dev/video0"
 int main(int argc, char *argv[])
@@ -240,7 +240,7 @@ int main(int argc, char *argv[])
 	LOG_O("Channel start OK\n");
 
 	// 处理订阅的Event
-	csi_frame_s frame;
+	csi_frame_ex_s frame;
 	struct csi_camera_event event;
 
 	LOG_O("Starting get frame...\n");
@@ -272,7 +272,7 @@ int main(int argc, char *argv[])
 #endif
 				dump_camera_meta(&frame);
 
-				csi_frame_release(&frame);
+				csi_camera_put_frame(&frame);
 				break;
 			}
 			default:
@@ -299,7 +299,7 @@ int main(int argc, char *argv[])
 #endif
 					dump_camera_meta(&frame);
 
-					csi_frame_release(&frame);
+					csi_camera_put_frame(&frame);
 				}
 				break;
 			}
@@ -332,15 +332,15 @@ int main(int argc, char *argv[])
 	csi_camera_close(cam_handle);
 }
 
-static void dump_camera_meta(csi_frame_s *frame)
+static void dump_camera_meta(csi_frame_ex_s *frame)
 {
 	int i;
-	if (frame->meta.type != CSI_META_TYPE_CAMERA)
+	if (frame->frame_meta.type != CSI_META_TYPE_CAMERA)
 		return;
 
-	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->meta.data;
+	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
 	int meta_count = meta_data->count;
-	csi_camrea_meta_unit_s meta_unit;
+	csi_camera_meta_unit_s meta_unit;
 
 	for (i = 0; i < meta_count; i++) {
 		csi_camera_frame_get_meta_unit(

+ 4 - 4
examples/camera/camera_demo3_srcs/dialog_channel_run.c

@@ -102,7 +102,7 @@ static int do_camera_event_action(cams_t *session, csi_camera_event_s *event)
 static int do_channel_event_action(cams_t *session, csi_camera_event_s *event)
 {
 	_CHECK_SESSION_RETURN();
-	csi_frame_s frame;
+	csi_frame_ex_s frame;
 	int ret = 0;
 
 	camera_event_action_union_t *event_action_u =
@@ -160,7 +160,7 @@ static int do_channel_event_action(cams_t *session, csi_camera_event_s *event)
 					LOG_D("read_frame_count = %d\n",read_frame_count);
 					for (int i = 0; i < read_frame_count; i++) {
 						csi_camera_get_frame(NULL,event->type - CSI_CAMERA_EVENT_TYPE_CHANNEL0, &frame, timeout);
-						if(frame.img.usr_addr[0] != NULL) {
+						if(frame.frame_data.vir_addr[0] != NULL) {
 							camera_action_image_save(&frame);
 							csi_camera_put_frame(&frame);
 						}
@@ -182,9 +182,9 @@ static int do_channel_event_action(cams_t *session, csi_camera_event_s *event)
 					LOG_D("read_frame_count = %d\n",read_frame_count);
 					//for (int i = 0; i < read_frame_count; i++) {
 						csi_camera_get_frame(NULL,event->type - CSI_CAMERA_EVENT_TYPE_CHANNEL0, &frame, timeout);
-						if(frame.img.usr_addr[0] != NULL) {
+						if(frame.frame_data.vir_addr[0] != NULL) {
 							camera_action_image_display(&frame);
-							LOG_D("frame->usr_addr = %p\n",frame.img.usr_addr[0]);
+							LOG_D("frame->usr_addr = %p\n",frame.frame_data.vir_addr[0]);
 							csi_camera_put_frame(&frame);
 						}
 					//}

+ 7 - 7
examples/camera/camera_demo4.c

@@ -17,7 +17,7 @@
 #define LOG_PREFIX "camera_demo4"
 #include <syslog.h>
 
-#include <csi_frame.h>
+#include <csi_frame_ex.h>
 #include <csi_camera.h>
 
 #define TEST_DEVICE_NAME "/dev/video0"
@@ -29,7 +29,7 @@ typedef struct cam_channel_control {
 	csi_camera_channel_cfg_s chn_cfg;
 } cam_channel_control_t;
 
-static void dump_camera_meta(csi_frame_s *frame);
+static void dump_camera_meta(csi_frame_ex_s *frame);
 static void *channel_thread(void *arg);
 
 int main(int argc, char *argv[])
@@ -225,7 +225,7 @@ static void *channel_thread(void *arg)
 
 	// 处理订阅的Event
 	LOG_O("[chn_%d] Starting get events...\n", chn_id);
-	csi_frame_s frame;
+	csi_frame_ex_s frame;
 	struct csi_camera_event event;
 
 	while (chn_ctrl->run) {
@@ -277,15 +277,15 @@ static void *channel_thread(void *arg)
 	pthread_exit(NULL);
 }
 
-static void dump_camera_meta(csi_frame_s *frame)
+static void dump_camera_meta(csi_frame_ex_s *frame)
 {
 	int i;
-	if (frame->meta.type != CSI_META_TYPE_CAMERA)
+	if (frame->frame_meta.type != CSI_META_TYPE_CAMERA)
 		return;
 
-	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->meta.data;
+	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
 	int meta_count = meta_data->count;
-	csi_camrea_meta_unit_s meta_unit;
+	csi_camera_meta_unit_s meta_unit;
 
 	for (i = 0; i < meta_count; i++) {
 		csi_camera_frame_get_meta_unit(

+ 66 - 53
examples/camera/camera_frame_display.c

@@ -38,7 +38,7 @@ typedef struct _CsiPlinkContext
     int useplink;
     int exitplink;
     CsiPictureBuffer sendbuffer[NUM_OF_BUFFERS];
-    csi_frame_s  frame_buf[NUM_OF_BUFFERS];
+    csi_frame_ex_s  frame_buf[NUM_OF_BUFFERS];
     int sendid;
     int available_bufs;
     void *vmem;
@@ -99,11 +99,11 @@ static void* camera_buf_release_process(CsiPlinkContext * plink_ctx)
                             LOG_W("invalid resp_id:%d\n",resp_id);
                             continue;
                         }
-                        if(plink_ctx->frame_buf[resp_id].img.dmabuf[0].fds!= 0)
+                        if(plink_ctx->frame_buf[resp_id].frame_data.fd[0]!= 0)
                         {
                             csi_camera_put_frame(&plink_ctx->frame_buf[resp_id]);
-                            LOG_D("release resp_id:%d, fd:%d\n",resp_id,plink_ctx->frame_buf[resp_id].img.dmabuf[0].fds);
-                            plink_ctx->frame_buf[resp_id].img.dmabuf[0].fds = 0;
+                            LOG_D("release resp_id:%d, fd:%d\n",resp_id,plink_ctx->frame_buf[resp_id].frame_data.fd[0]);
+                            plink_ctx->frame_buf[resp_id].frame_data.fd[0] = 0;
                         }
 
                     }
@@ -125,6 +125,7 @@ static void* camera_buf_release_process(CsiPlinkContext * plink_ctx)
      LOG_O("Process is exit .....\n");
      return NULL;
 }
+
 static int allocate_sendbuffers(CsiPictureBuffer picbuffers[NUM_OF_BUFFERS], unsigned int size, void *vmem)
 {
     unsigned int buffer_size = (size + 0xFFF) & ~0xFFF;
@@ -145,13 +146,15 @@ static int allocate_sendbuffers(CsiPictureBuffer picbuffers[NUM_OF_BUFFERS], uns
         picbuffers[i].size = buffer_size;
         picbuffers[i].fd = params.fd;
     }
+    return 0;
 }
 
 void *vi_plink_create(csi_camera_channel_cfg_s *chn_cfg)
 {
 	int ret = 0;
     CsiPlinkContext *plink_ctx = NULL;
-    char *env=NULL;
+    char *env = NULL;
+
 	if (chn_cfg == NULL) {
 		LOG_E("%s failt to  get chn_cfg\n", __func__);
 		return NULL;
@@ -264,32 +267,33 @@ void vi_plink_release(void * plink)
         VMEM_destroy(plink_ctx->vmem);
     }
 }
-
-
-void display_camera_frame(void *plink, csi_frame_s *frame)
+void display_camera_frame(void *plink, csi_frame_ex_s *frame)
 {
 	
     CsiPlinkContext * plink_ctx = (CsiPlinkContext *)plink;
+
 	if ((plink_ctx == NULL) ||  (frame == NULL)) {
 		LOG_E("%s  check param fail\n", __func__);
         return;
 	}
 
-
-	LOG_O("fmt=%d img.strides[0] = %d\n",frame->img.pix_format, frame->img.strides[0]);
+	LOG_I("fmt=%d,fd=%d,stride:%d\n",frame->frame_info.pixel_format,frame->frame_data.fd[0],frame->frame_data.stride[0]);
 
 	if (!plink_ctx->exitplink) {
 		struct timeval tv_start, tv_end, tv_duration;
 		gettimeofday(&tv_start, 0);
 		PlinkPacket pkt = {0};
 		// send one buffer if there is available slot
-        if (frame->img.type == CSI_IMG_TYPE_DMA_BUF && !plink_ctx->exitplink
-            && plink_ctx->available_bufs > 0 && plink_ctx->plink != NULL && ((frame->img.pix_format == CSI_PIX_FMT_RAW_8BIT)|| (frame->img.pix_format == CSI_PIX_FMT_RAW_12BIT))) {
+        if (!plink_ctx->exitplink&& plink_ctx->available_bufs > 0 &&
+            plink_ctx->plink != NULL && ((frame->frame_info.pixel_format == CSI_PIX_FMT_RAW_8BIT)|| 
+                                            (frame->frame_info.pixel_format == CSI_PIX_FMT_RAW_10BIT)||
+                                            (frame->frame_info.pixel_format== CSI_PIX_FMT_RAW_12BIT))) 
+        {   
             char str[200];
             static int i = 0;
-			uint32_t dstw = frame->img.width;//800;
-			uint32_t dsth = frame->img.height;//1280;
-			uint32_t dsts = frame->img.strides[0];//896;
+			uint32_t dstw = frame->frame_info.width;//800;
+			uint32_t dsth = frame->frame_info.height;//1280;
+			uint32_t dsts = frame->frame_data.stride[0];//896;
 
 			PlinkRawInfo info = {0};
 
@@ -303,33 +307,35 @@ void display_camera_frame(void *plink, csi_frame_s *frame)
 
 			info.img_width = dstw;
 			info.img_height = dsth;
-			info.stride = frame->img.strides[0];
+			info.stride = frame->frame_data.stride[0];
 			info.offset = 0;
 			pkt.list[0] = &info;
 			pkt.num = 1;
-			pkt.fd = frame->img.dmabuf[0].fds;
-            if(plink_ctx->frame_buf[plink_ctx->sendid].img.dmabuf[0].fds!=0)
+			pkt.fd = frame->frame_data.fd[0];
+            if(plink_ctx->frame_buf[plink_ctx->sendid].frame_data.fd[0]!=0)
             {
-                LOG_W("previous sendid :%d,fd %d not release,release it now\n",plink_ctx->sendid,plink_ctx->frame_buf[plink_ctx->sendid].img.dmabuf[0].fds);
+                LOG_W("previous sendid :%d,fd %d not release,release it now\n",plink_ctx->sendid,plink_ctx->frame_buf[plink_ctx->sendid].frame_data.fd[0]);
                 csi_camera_put_frame(&plink_ctx->frame_buf[plink_ctx->sendid]);
             }
-            memcpy(&plink_ctx->frame_buf[plink_ctx->sendid],frame,sizeof(csi_frame_s));
+            memcpy(&plink_ctx->frame_buf[plink_ctx->sendid],frame,sizeof(csi_frame_ex_s));
             plink_ctx->sendid = (plink_ctx->sendid + 1) % NUM_OF_BUFFERS;
 			if (PLINK_send(plink_ctx->plink, plink_ctx->chnid, &pkt) != PLINK_STATUS_OK)
 				plink_ctx->exitplink = 1;
 			gettimeofday(&tv_end, 0);
 			timersub(&tv_end, &tv_start, &tv_duration);
+
+
             pthread_mutex_lock(&plink_ctx->mutex);
 			plink_ctx->available_bufs -= 1;
             pthread_mutex_unlock(&plink_ctx->mutex);
 		}
-        else if (frame->img.type == CSI_IMG_TYPE_DMA_BUF && !plink_ctx->exitplink
-            && plink_ctx->available_bufs > 0 && plink_ctx->plink != NULL && ((frame->img.pix_format == CSI_PIX_FMT_YUV_SEMIPLANAR_420)|| (frame->img.pix_format == CSI_PIX_FMT_NV12))) {
+         else if (!plink_ctx->exitplink && plink_ctx->available_bufs > 0 && 
+                plink_ctx->plink != NULL && ((frame->frame_info.pixel_format == CSI_PIX_FMT_YUV_SEMIPLANAR_420)|| (frame->frame_info.pixel_format == CSI_PIX_FMT_NV12))) {            
             char str[200];
             static int i = 0;
-			uint32_t dstw = frame->img.width;//800;
-			uint32_t dsth = frame->img.height;//1280;
-			uint32_t dsts = frame->img.strides[0];//896;
+			uint32_t dstw = frame->frame_info.width;//800;
+			uint32_t dsth = frame->frame_info.height;//1280;
+			uint32_t dsts = frame->frame_data.stride[0];//896;
 
 
 			PlinkYuvInfo info = {0};
@@ -349,46 +355,42 @@ void display_camera_frame(void *plink, csi_frame_s *frame)
 			info.stride_u = dsts;
 			info.stride_v = dsts;
 			info.offset_y = 0;
-			info.offset_u = frame->img.dmabuf[1].offset;
-			info.offset_v = frame->img.dmabuf[2].offset;
+			info.offset_u = frame->frame_data.offset[1];
+			info.offset_v = frame->frame_data.offset[2];
 			pkt.list[0] = &info;
 			pkt.num = 1;
-			pkt.fd = frame->img.dmabuf[0].fds;
+			pkt.fd = frame->frame_data.fd[0];
             
-            if(plink_ctx->frame_buf[plink_ctx->sendid].img.dmabuf[0].fds!=0)
+            if(plink_ctx->frame_buf[plink_ctx->sendid].frame_data.fd[0]!=0)
             {
-                LOG_W("previous sendid :%d,fd %d not release,release it now\n",plink_ctx->sendid,plink_ctx->frame_buf[plink_ctx->sendid].img.dmabuf[0].fds);
+                LOG_W("previous sendid :%d,fd %d not release,release it now\n",plink_ctx->sendid,plink_ctx->frame_buf[plink_ctx->sendid].frame_data.fd[0]);
                 csi_camera_put_frame(&plink_ctx->frame_buf[plink_ctx->sendid]);
             }
-            memcpy(&plink_ctx->frame_buf[plink_ctx->sendid],frame,sizeof(csi_frame_s));          
+            memcpy(&plink_ctx->frame_buf[plink_ctx->sendid],frame,sizeof(csi_frame_ex_s));          
 			plink_ctx->sendid = (plink_ctx->sendid + 1) % NUM_OF_BUFFERS;
 			if (PLINK_send(plink_ctx->plink, plink_ctx->chnid, &pkt) != PLINK_STATUS_OK)
 				plink_ctx->exitplink = 1;
 			gettimeofday(&tv_end, 0);
 			timersub(&tv_end, &tv_start, &tv_duration);
+            
             pthread_mutex_lock(&plink_ctx->mutex);
 			plink_ctx->available_bufs -= 1;
             pthread_mutex_unlock(&plink_ctx->mutex);
-		} else if (!plink_ctx->exitplink && plink_ctx->available_bufs > 0 && plink_ctx->plink != NULL && (frame->img.pix_format == CSI_PIX_FMT_BGR)) {
+		
+ 		} else if (!plink_ctx->exitplink && plink_ctx->available_bufs > 0 && plink_ctx->plink != NULL && (frame->frame_info.pixel_format == CSI_PIX_FMT_BGR)) {
 			CsiPictureBuffer *buf = &plink_ctx->sendbuffer[plink_ctx->sendid];
 			int y = 0;
-			// if (1) {
-    		// 	void *pbuf[3];
-			// 	void *phyaddr = vi_mem_import(frame->img.dmabuf[0].fds);
-			// 	pbuf[0] = vi_mem_map(phyaddr) + frame->img.dmabuf[0].offset;
-			// 	pbuf[1] = pbuf[0] + frame->img.dmabuf[1].offset;
-			// 	vi_mem_release(phyaddr);
-			// 	frame->img.usr_addr[0] = pbuf[0];
-			// }
-			uint8_t *src = frame->img.usr_addr[0];
+            int buf_size =  frame->frame_info.width*frame->frame_info.height*3;
+
+			uint8_t *src = frame->frame_data.vir_addr[0] ;
 			uint8_t *dst = buf->virtual_address;
-			uint32_t srcw = frame->img.width;
-			uint32_t srch = frame->img.height;
-			uint32_t dstw = frame->img.width;
-			uint32_t dsth = frame->img.height;
-			uint32_t dsts = frame->img.width;
-			switch (frame->img.pix_format ) {
-				case CSI_PIX_FMT_BGR:
+			uint32_t srcw = frame->frame_info.width;
+			uint32_t srch = frame->frame_info.height;
+			uint32_t dstw = frame->frame_info.width;
+			uint32_t dsth = frame->frame_info.height;
+			uint32_t dsts = frame->frame_info.width;
+			switch (frame->frame_info.pixel_format) {				
+                case CSI_PIX_FMT_BGR:
 				{
 					dstw = 300;
 					dsth = 304;
@@ -404,7 +406,7 @@ void display_camera_frame(void *plink, csi_frame_s *frame)
 						src += srcw;
 						dst += dsts;
 					}
-					src = frame->img.usr_addr[0] + srcw*srch;
+					src = frame->frame_data.vir_addr[0] + srcw*srch;
 					dst = buf->virtual_address + dsts*dsth;
 					for (y = 0; y < h; y++)
 					{
@@ -412,7 +414,7 @@ void display_camera_frame(void *plink, csi_frame_s *frame)
 						src += srcw;
 						dst += dsts;
 					}
-					src = frame->img.usr_addr[0] + srcw*srch*2;
+					src = frame->frame_data.vir_addr[0]  + srcw*srch*2;
 					dst = buf->virtual_address + dsts*dsth*2;
 					for (y = 0; y < h; y++)
 					{
@@ -457,7 +459,7 @@ void display_camera_frame(void *plink, csi_frame_s *frame)
 						src += srcw;
 						dst += dsts;
 					}
-					src = frame->img.usr_addr[0] + frame->img.strides[0] * frame->img.height;
+					src = frame->frame_data.vir_addr[0]  +  frame->frame_data.stride[0] * frame->frame_info.height;
 					dst = buf->virtual_address + (dsts * dsth);
 					for (y = 0; y < h/2; y++)
 					{
@@ -490,7 +492,7 @@ void display_camera_frame(void *plink, csi_frame_s *frame)
 					break;
 				}
 			}
-
+            csi_camera_put_frame(frame);
 			gettimeofday(&tv_end, 0);
 			timersub(&tv_end, &tv_start, &tv_duration);
             pthread_mutex_lock(&plink_ctx->mutex);
@@ -498,6 +500,17 @@ void display_camera_frame(void *plink, csi_frame_s *frame)
 			plink_ctx->available_bufs -= 1;
             pthread_mutex_unlock(&plink_ctx->mutex);
 		}
+        else
+        {
+            LOG_W("frame not send by plink,available_bufs:%d,fmt:%d\n",plink_ctx->available_bufs,
+                                                                frame->frame_info.pixel_format);
+            csi_camera_put_frame(frame);
+        }
 	}
-	LOG_O("%s exit \n", __func__);
+    else
+    {
+        LOG_E("plink is exit\n");
+        csi_camera_put_frame(frame);
+    }
+	LOG_I("%s exit \n");
 }

+ 1054 - 169
examples/camera/camera_test1.c

@@ -1,6 +1,6 @@
 /*
- * Copyright (C) 2021 Alibaba Group Holding Limited
- * Author: LuChongzhi <chongzhi.lcz@alibaba-inc.com>
+ * Copyright (C) 2021-2022 Alibaba Group Holding Limited
+ * Author: LuChongzhi <chongzhi.lcz@alibaba-inc.com>; Minxiong Tian <minxiong.tmx@alibaba-inc.com>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2 as
@@ -10,27 +10,139 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+#include <pthread.h>
+#include <unistd.h>
+#include <error.h>
+#include <errno.h>
+
+#include <sys/mman.h>
+#include <sys/ipc.h>
+#include <sys/shm.h>
+#include <sys/sem.h>
+
+#include "csi_camera_dev_api.h"
+
+/* macros for share memory and semaphore */
+#define SHMKEY (key_t)0x39126
+#define SEMKEY (key_t)0x49126
+#define IFLAGS (IPC_CREAT|IPC_EXCL)
 
 #define LOG_LEVEL 2
 #define LOG_PREFIX "camera_demo1"
 #include <syslog.h>
 
-#include <csi_frame.h>
+#include <csi_frame_ex.h>
 #include <csi_camera.h>
 
 #ifdef PLATFORM_SIMULATOR
 #include "apputilities.h"
 #endif
 
-static void dump_camera_meta(csi_frame_s *frame);
-static int save_camera_img(csi_frame_s *frame);
-static int save_camera_stream(csi_frame_s *frame);
+#define PAGE_SIZE 1024
+#define PAGE_ALIGN(addr)   (void *)(((int)(addr)+PAGE_SIZE-1)&~( PAGE_SIZE-1))
+
+/* data store in share-memory */
+struct databuf {
+    int d_buf[2];
+};
+
+static void dump_camera_meta(csi_frame_ex_s *frame, int idx);
+static void* save_camera_img(void *);
+static void* save_camera_stream(void *);
+static int set_properties(csi_cam_handle_t cam_handle, char *pArgs);
+static enum csi_pixel_fmt parse_format(char *fmt);
+// static void handle_dma_buf(csi_frame_s *framei, int cid);
+//extern int csi_camera_frame_unlock(csi_cam_handle_t cam_handle, csi_frame_s *frame);
+extern int csi_camera_put_frame(csi_frame_ex_s *frame);
+static void i_save(csi_frame_ex_s *framei, int cid, FILE *fp, int vmode);
+static void parse_fmt_res(int cindx);
+static void getseg(struct databuf* *pdata);
+static int getsem();
+static void remove_s();
+static void writer(struct databuf *buf, int index, int value);
+static void reader(struct databuf *buf, int index, int * rv);
+static int pr_error(char *mess);
+extern int csi_camera_set_pp_path_param(csi_cam_handle_t cam_handle, uint16_t line_num,uint16_t buf_mode);
+
+extern void *vi_plink_create(csi_camera_channel_cfg_s *chn_cfg);
+extern void vi_plink_release(void * plink);
+extern void display_camera_frame(void * plink, csi_frame_ex_s *frame);
 
 #define TEST_DEVICE_NAME "/dev/video0"
 #define CSI_CAMERA_TRUE  1
 #define CSI_CAMERA_FALSE 0
+#define chnMAX 8
+#define fmtMAX 19
+
+csi_cam_handle_t cam_handle;
+char *prog_name;
+int Soff = 0;
+static char device[CSI_CAMERA_NAME_MAX_LEN];    /* target video device like /dev/video0 */
+static char path[128] = "./";    /* output path */
+static int channelIdx[chnMAX];    /* channel information like 8 */
+enum csi_pixel_fmt fenum[chnMAX];
+int fid[chnMAX] = {0};
+int tframes = 4;
+csi_camera_channel_id_e CAMERA_CHANNEL_ID[chnMAX];
+
+/* File local Global array to store information which will be used when storig images */
+static int PLANE[chnMAX] = {0};
+static int PBIT[chnMAX] = {0};
+static int PLNS[chnMAX][3] = {0};
+static int LNN[chnMAX][3] = {0};
+static int LSZ[chnMAX][3] = {0};
+static int LNNV[chnMAX][3] = {0}; /* for rotation 90/270 */
+static int LSZV[chnMAX][3] = {0}; /* for rotation 90/270 */
+static int NOSTRD[chnMAX] = {0};
+
+/* local global array for meta data verify */
+static int cur_metaint[chnMAX] = {-1, -1, -1, -1};
+static int pre_metaint[chnMAX] = {-1, -1, -1, -1};
+static int cur_metasec[chnMAX] = {-1, -1, -1, -1};
+static int pre_metasec[chnMAX] = {-1, -1, -1, -1};
+static int cur_metausec[chnMAX] = {-1, -1, -1, -1};
+static int pre_metausec[chnMAX] = {-1, -1, -1, -1};
+
+static int shmid, semid;
+struct sembuf p1 = {0, -1, 0}, v1 = {0, 1, 0};
 
-char *prog_name; 
+int meta_mode = -1;
+int flashMode = 0;
+int fNumInc[chnMAX] = {0};
+int fCount = 1;
+int onoffMode = 0;
+int afterOnOff[chnMAX];
+int onoffDrop = 4;
+int onoffFrame = 0;
+int ooNum[chnMAX] = {0};
+int ofTop = 30;
+csi_frame_ex_s frame[chnMAX];
+pthread_t tid[chnMAX]={0};
+int hres[chnMAX], vres[chnMAX];    /* resolution information like 640x480 */
+int idxArray[chnMAX][10]={0};
+static char *dname;
+static int chNum = 0;
+char fmtArray[fmtMAX][50] = {
+    "CSI_PIX_FMT_I420",
+    "CSI_PIX_FMT_NV12",
+    "CSI_PIX_FMT_BGR",
+    "CSI_PIX_FMT_RAW_8BIT",
+    "CSI_PIX_FMT_RAW_10BIT",
+    "CSI_PIX_FMT_RAW_12BIT",
+    "CSI_PIX_FMT_RAW_14BIT",
+    "CSI_PIX_FMT_RAW_16BIT",
+    "CSI_PIX_FMT_RGB_PLANAR_888",
+    "CSI_PIX_FMT_RGB_INTEVLEAVED_888",
+    "CSI_PIX_FMT_YUV_PLANAR_422",
+    "CSI_PIX_FMT_YUV_PLANAR_420",
+    "CSI_PIX_FMT_YUV_PLANAR_444",
+    "CSI_PIX_FMT_YUV_SEMIPLANAR_422",
+    "CSI_PIX_FMT_YUV_SEMIPLANAR_420",
+    "CSI_PIX_FMT_YUV_SEMIPLANAR_444",
+    "CSI_PIX_FMT_YUV_TEVLEAVED_422",
+    "CSI_PIX_FMT_YUV_TEVLEAVED_420",
+    "CSI_PIX_FMT_YUV_TEVLEAVED_444"
+};
 
 void usage()
 {
@@ -38,64 +150,132 @@ void usage()
 			"usage: %s [options]\n"
 			"Options:\n"
 			"\t-D dev		target video device like /dev/video0\n"
-			"\t-R resolution        format is like 640x480\n"
-			"\t-F format		like NV12\n"
-			"\t-C channel_index		channel index defined in dts, index from 0\n"
-			"\t-M output mode		0: save as image; 1: save as stream file\n"
-			"\t-N number for frames		0: record forever; others: the recorded frame numbers"
+			"\t-R resolution        format is like 640x480, use 640x480/1092x1080 for multi channel output\n"
+			"\t-F format		like NV12, use NV12/NV12 to support multi channel output\n"
+			"\t-C channel_index		channel index defined in dts, index from 0, use 0/2 for multi channel output\n"
+			"\t-M test mode		0: save as image; 1: save as stream file; 2: output to plink; 3. performace test\n"
+			"\t-N number for frames		0: record forever; others: the recorded frame numbers, use 30/30 from multi channel output\n"
+			"\t-n number of frames to save 	if not given, 4 is used\n"
+			"\t-P Property		id:type:value, use id:type:value/id:type:value for multi property setting\n"
+			"\t-p output path        store output file in the give path\n"
+			"\t-S turn off stride mode        if given, turn off stride mode\n"
+			"\t-t stream turn on/off test        if will turn off stream after several streams then turn on\n"
+			"\t-s turn off sram mode        if given, turn off sram mode between ISP/DSP and DSP/ISP-RY\n"
+			"\t-m disable DW DMA-BUF         if given, turn off dma-buf mode\n"
+			"\t-f enable LED flash mode         if given, enable LED flash mode for odd and even frame feature in lightA production board\n"
+			"\t-i nubmer of process which needs to do IPC, use for multi-video and mutli-process test scenarios\n"
+			"\t-y meta-data test            0 - meta dump all all elements; 1 - meta verify for CAMERA_NAME;\n"
+            "                                2 - meta verify for CHANNEL_ID; 3 - meta verify for FRAME_ID;\n"
+            "                                4 - meta verify for TIMESTAMP.\n"
+            "                                200 - meta verify for all elements\n"
 			, prog_name
 		);
 }
 
 int main(int argc, char *argv[])
 {
-	bool running = false;
+	bool running = 0;
 	csi_camera_info_s camera_info;
 
 	int opt;
-	char device[CSI_CAMERA_NAME_MAX_LEN];    /* target video device like /dev/video0 */
-	char *resolution;    /* resolution information like 640x480 */
-	int hres, vres;    /* resolution information like 640x480 */
-	char *resDelim = "xX";
-	char *format;    /* format information like NV12 */
-	enum csi_pixel_fmt fenum;
-	int channelIdx;    /* channel information like 8 */
+	char *resDelim = "xX/";
 	int outMode = 0;
-	int fNum = 0;
+	int fNum[chnMAX] = {0};
+	char pArgs[500] = {'\0'};    /* store property args */
+	char *devDelim = "/";
+    char *sCur;
+    int idx = 0;
+    int ret = 0;
+	csi_camera_event_type_e CAMERA_CHANNEL_EVENT_TYPE[chnMAX];
+	struct timeval init_time, cur_time;
+	memset(&init_time, 0, sizeof(init_time));
+	memset(&cur_time, 0, sizeof(cur_time));
+    unsigned long video_open = 0;
+    unsigned long channel_open = 0;
+    unsigned long channel_start = 0;
+    unsigned long first_frame = 0;
+    unsigned long total_frame = 0;
+    float fps = 0.0;
+    int sramMode = 1;
+
+    /* data for share-memory */
+    struct databuf *buf;
+    int mi = 0;
+    int srv1 = 0, srv2 = 0;
 
 	prog_name = argv[0];
 
-	while ((opt = getopt(argc, argv, "D:R:F:C:M:hN:")) != EOF) {
+	while ((opt = getopt(argc, argv, "t:D:R:F:C:M:hN:P:p:Smi:y:fsn:")) != EOF) {
 		switch(opt) {
 			case 'D':
-				//device = optarg;
 				strcpy(device, optarg);
+				strtok(optarg, devDelim);
+				dname=strtok(NULL, devDelim);
+				continue;
+			case 'p':
+				strcpy(path, optarg);
+				continue;
+			case 'S':
+				Soff = 1;
+				continue;
+			case 't':
+				onoffMode = 1;
+				onoffFrame = atoi(optarg);
+				continue;
+			case 's':
+				sramMode = 0;
+			case 'f':
+				flashMode = 1;
+				continue;
+			case 'P':
+				strcpy(pArgs, optarg);
 				continue;
 			case 'R':
-				resolution = optarg;
-				hres = atoi(strtok(resolution, resDelim));
-				vres = atoi(strtok(NULL, resDelim));
+                idx = 0;
+                sCur=strtok(optarg, resDelim);
+                while (sCur != NULL){
+                    if (idx % 2 == 0)
+                        hres[idx/2] =  atoi(sCur);
+                    if (idx % 2 == 1)
+                        vres[idx/2] =  atoi(sCur);
+                    sCur=strtok(NULL, resDelim);
+                    idx++;
+                }
 				continue;
 			case 'M':
 				outMode = atoi(optarg);
 				continue;
+			case 'i':
+				mi = atoi(optarg);
+				continue;
+			case 'y':
+				meta_mode = atoi(optarg);
+				continue;
 			case 'N':
-				fNum = atoi(optarg);
+                for(int j=0; j<chnMAX; j++)
+				    fNum[j] = atoi(optarg);
+				continue;
+			case 'n':
+				tframes = atoi(optarg);
 				continue;
 			case 'F':
-				format = optarg;
-				if(strstr(format, "NV12")){
-					fenum = CSI_PIX_FMT_NV12;
-				}
-				else if(strstr(format, "I420")){
-					fenum = CSI_PIX_FMT_I420;
-				}
-				else{
-					fenum = CSI_PIX_FMT_I420;
-				}
+                idx = 0;
+                sCur=strtok(optarg, devDelim);
+                while (sCur != NULL){
+                    fenum[idx] = parse_format(sCur);
+                    sCur=strtok(NULL, devDelim);
+                    idx++;
+                }
 				continue;
 			case 'C':
-				channelIdx = atoi(optarg);
+                idx = 0;
+                sCur=strtok(optarg, devDelim);
+                while (sCur != NULL){
+                    channelIdx[idx] =  atoi(sCur);
+                    sCur=strtok(NULL, devDelim);
+                    idx++;
+                }
+                chNum = idx;
 				continue;
 			case '?':
 			case 'h':
@@ -105,11 +285,23 @@ int main(int argc, char *argv[])
 		}
 	}
 
-	const csi_camera_channel_id_e CAMERA_CHANNEL_ID = CSI_CAMERA_CHANNEL_0 + channelIdx;
-	const csi_camera_event_type_e CAMERA_CHANNEL_EVENT_TYPE = CSI_CAMERA_EVENT_TYPE_CHANNEL0 + channelIdx;
-	if (fNum == 0)
-		running == true;
+    /* get semaphore ID and share-memory ID if mi >=2 */
+    if(mi >= 2){
+        semid = getsem();
+        getseg(&buf);
+        printf("------IPC mode enable - finish-------\n");
+    }
 
+    /* init the target channel ID and channel event type array */
+    for (int j=0; j<chNum; j++){
+        CAMERA_CHANNEL_ID[j] =  CSI_CAMERA_CHANNEL_0 + channelIdx[j];
+        CAMERA_CHANNEL_EVENT_TYPE[j] =  CSI_CAMERA_EVENT_TYPE_CHANNEL0 + channelIdx[j];
+    }
+
+	if (fNum[0] == 0){
+		running = 1;
+        printf("------running = 1-------\n");
+	}
 
 	// 打印HAL接口版本号
 	csi_api_version_u version;
@@ -150,12 +342,11 @@ int main(int argc, char *argv[])
 
 
 	// 打开Camera设备获取句柄,作为后续操对象
-	csi_cam_handle_t cam_handle;
-	//csi_camera_open(&cam_handle, camera_info.device_name);
 	strcpy(camera_info.device_name, device);
-	//camera_info.device_name = device;
+	gettimeofday(&init_time, 0);
 	csi_camera_open(&cam_handle, camera_info.device_name);
-	//csi_camera_open(&cam_handle, device);
+	gettimeofday(&cur_time, 0);
+	video_open = 1000000 * (cur_time.tv_sec-init_time.tv_sec)+ cur_time.tv_usec-init_time.tv_usec;
 	// 获取Camera支持的工作模式
 	struct csi_camera_modes camera_modes;
 	csi_camera_get_modes(cam_handle, &camera_modes);
@@ -169,6 +360,7 @@ int main(int argc, char *argv[])
 	}
 	printf("}\n");
 
+
 	// 设置camera的工作模式及其配置
 	csi_camera_mode_cfg_s camera_cfg;
 	camera_cfg.mode_id = 1;
@@ -178,17 +370,9 @@ int main(int argc, char *argv[])
 
 	// 获取单个可控单元的属性
 	csi_camera_property_description_s description;
-	/* id=0x0098090x, type=2 default=0 value=1 */
-	/* Other example:
-	 * id=0x0098090y, type=3 min=0 max=255 step=1 default=127 value=116
-	 * id=0x0098090z, type=4 min=0 max=3 default=0 value=2
-	 *                                0: IDLE
-	 *                                1: BUSY
-	 *                                2: REACHED
-	 *                                3: FAILED
-	 */
 
 	// 轮询获取所有可控制的单元
+
 	printf("all properties are:\n");
 	description.id = CSI_CAMERA_PID_HFLIP;
 	while (!csi_camera_query_property(cam_handle, &description)) {
@@ -225,167 +409,868 @@ int main(int argc, char *argv[])
 		description.id |= CSI_CAMERA_FLAG_NEXT_CTRL;
 	}
 
-	// 同时配置多个参数
-	csi_camera_properties_s properties;
-	csi_camera_property_s property[3];
-	property[0].id = CSI_CAMERA_PID_HFLIP;
-	property[0].type = CSI_CAMERA_PROPERTY_TYPE_BOOLEAN;
-	property[0].value.bool_value = false;
-	property[1].id = CSI_CAMERA_PID_VFLIP;
-	property[1].type = CSI_CAMERA_PROPERTY_TYPE_BOOLEAN;
-	property[1].value.bool_value = false;
-	property[2].id = CSI_CAMERA_PID_ROTATE;
-	property[2].type = CSI_CAMERA_PROPERTY_TYPE_INTEGER;
-	property[2].value.int_value = 0;
-	properties.count = 3;
-	properties.property = property;
-	if (csi_camera_set_property(cam_handle, &properties) < 0) {
-		LOG_O("set_property fail!\n");
-	}
-	LOG_O("set_property ok!\n");
+    if (pArgs[0] != '\0'){
+        set_properties(cam_handle, pArgs);
+    }
 
 	// 查询输出channel
-	csi_camera_channel_cfg_s chn_cfg;
-	chn_cfg.chn_id = CAMERA_CHANNEL_ID;
-	csi_camera_channel_query(cam_handle, &chn_cfg);
-	if (chn_cfg.status != CSI_CAMERA_CHANNEL_CLOSED) {
-		printf("Can't open CSI_CAMERA_CHANNEL_0\n");
-		exit(-1);
-	}
+    csi_camera_channel_cfg_s chn_cfg[chnMAX];
+    for (int j=0; j<chNum; j++){
+        chn_cfg[j].chn_id = CAMERA_CHANNEL_ID[j];
+        csi_camera_channel_query(cam_handle, &chn_cfg[j]);
+        if (chn_cfg[j].status != CSI_CAMERA_CHANNEL_CLOSED) {
+            printf("Can't open channel: %d\n", CAMERA_CHANNEL_ID[j]);
+            exit(-1);
+        }
+    }
 
 	// 打开输出channel
-	chn_cfg.chn_id = channelIdx;
-	chn_cfg.frm_cnt = 4;
-	chn_cfg.img_fmt.width = hres;
-	chn_cfg.img_fmt.height = vres;
-	chn_cfg.img_fmt.pix_fmt = fenum;
-	chn_cfg.img_type = CSI_IMG_TYPE_DMA_BUF;
-	chn_cfg.meta_fields = CSI_CAMERA_META_DEFAULT_FIELDS;
-	chn_cfg.capture_type = CSI_CAMERA_CHANNEL_CAPTURE_VIDEO |
-		CSI_CAMERA_CHANNEL_CAPTURE_META;
-	csi_camera_channel_open(cam_handle, &chn_cfg);
-
-	// 订阅Event
+    if (sramMode == 1){
+        csi_camera_set_pp_path_param(cam_handle,0,1);
+    }
 	csi_cam_event_handle_t event_handle;
-	csi_camera_create_event(&event_handle, cam_handle);
 	csi_camera_event_subscription_s subscribe;
-	subscribe.type =
-		CSI_CAMERA_EVENT_TYPE_CAMERA;      // 订阅Camera的ERROR事件
-	subscribe.id = CSI_CAMERA_EVENT_WARNING | CSI_CAMERA_EVENT_ERROR;
-	csi_camera_subscribe_event(event_handle, &subscribe);
-	subscribe.type =
-		CAMERA_CHANNEL_EVENT_TYPE;    // 订阅Channel0的FRAME_READY事件
-	subscribe.id = CSI_CAMERA_CHANNEL_EVENT_FRAME_READY |
-		CSI_CAMERA_CHANNEL_EVENT_OVERFLOW;
-	csi_camera_subscribe_event(event_handle, &subscribe);
-
-	// 开始从channel中取出准备好的frame
-	csi_camera_channel_start(cam_handle, CAMERA_CHANNEL_ID);
+    for (int j=0; j<chNum; j++){
+        chn_cfg[j].chn_id = CAMERA_CHANNEL_ID[j];
+        chn_cfg[j].frm_cnt = fCount;
+        chn_cfg[j].img_fmt.width = hres[j];
+        chn_cfg[j].img_fmt.height = vres[j];
+        chn_cfg[j].img_fmt.pix_fmt = fenum[j];
+        chn_cfg[j].img_type = CSI_IMG_TYPE_DMA_BUF;
+        chn_cfg[j].meta_fields = CSI_CAMERA_META_DEFAULT_FIELDS;
+        chn_cfg[j].capture_type = CSI_CAMERA_CHANNEL_CAPTURE_VIDEO |
+            CSI_CAMERA_CHANNEL_CAPTURE_META;
+        parse_fmt_res(j);
+        gettimeofday(&init_time, 0);
+        ret = csi_camera_channel_open(cam_handle, &chn_cfg[j]);
+        if (ret) {
+            exit(-1);
+        }
+        gettimeofday(&cur_time, 0);
+        channel_open = 1000000 * (cur_time.tv_sec-init_time.tv_sec)+ cur_time.tv_usec-init_time.tv_usec;
+    }
+
+        // 订阅Event
+    csi_camera_create_event(&event_handle, cam_handle);
+    for (int j=0; j<chNum; j++){
+        subscribe.type =
+            CSI_CAMERA_EVENT_TYPE_CAMERA;      // 订阅Camera的ERROR事件
+        subscribe.id = CSI_CAMERA_EVENT_WARNING | CSI_CAMERA_EVENT_ERROR;
+        csi_camera_subscribe_event(event_handle, &subscribe);
+        subscribe.type =
+            CAMERA_CHANNEL_EVENT_TYPE[j];    // 订阅Channel0的FRAME_READY事件
+        subscribe.id = CSI_CAMERA_CHANNEL_EVENT_FRAME_READY |
+            CSI_CAMERA_CHANNEL_EVENT_OVERFLOW;
+        csi_camera_subscribe_event(event_handle, &subscribe);
+    }
+
+    if ( flashMode == 1){
+        csi_camera_floodlight_led_set_flash_bright(cam_handle, 500); //500ma
+        csi_camera_projection_led_set_flash_bright(cam_handle, 500); //500ma
+        csi_camera_projection_led_set_mode(cam_handle, LED_IR_ENABLE);
+        csi_camera_floodlight_led_set_mode(cam_handle, LED_IR_ENABLE);
+        csi_camera_led_enable(cam_handle, LED_FLOODLIGHT_PROJECTION);
+    }
+	// start all channels
+    for (int j=0; j<chNum; j++){
+        gettimeofday(&init_time, 0);
+	    csi_camera_channel_start(cam_handle, CAMERA_CHANNEL_ID[j]);
+        gettimeofday(&cur_time, 0);
+        channel_start = 1000000 * (cur_time.tv_sec-init_time.tv_sec)+ cur_time.tv_usec-init_time.tv_usec;
+    }
+    gettimeofday(&init_time, 0);
 
 	// 处理订阅的Event
-	csi_frame_s frame;
 	struct csi_camera_event event;
+    int fnumTotal = fNum[0] * chNum;
+    int frameTotal = fnumTotal;
 
-	while (running || fNum >= 0 ) {
+	while (running || fnumTotal > 0 ) {
 		int timeout = -1; // unit: ms, -1 means wait forever, or until error occurs
 		csi_camera_get_event(event_handle, &event, timeout);
+		printf("%s event.type = %d, event.id = %d\n", __func__, event.type, event.id);
 		if(event.type == CSI_CAMERA_EVENT_TYPE_CAMERA){
 			switch (event.id) {
 				case CSI_CAMERA_EVENT_ERROR:
 					// do sth.
-					LOG_D("get CAMERA EVENT CSI_CAMERA_EVENT_ERROR!\n");
+					printf("-------get CAMERA EVENT CSI_CAMERA_EVENT_ERROR!----------\n");
 					break;
+                case CSI_CAMERA_EVENT_WARNING:
+            		printf("-------get CAMERA EVENT CSI_CAMERA_EVENT_WRN,RC: %s-------\n",event.bin);
+				    break;
 				default:
 					break;
 			}
 		}
-		if(event.type == CAMERA_CHANNEL_EVENT_TYPE){
-			switch (event.id) {
-				case CSI_CAMERA_CHANNEL_EVENT_FRAME_READY: {
-					   int read_frame_count = csi_camera_get_frame_count(cam_handle,
-							   CAMERA_CHANNEL_ID);
-					   for (int i = 0; i < read_frame_count; i++) {
-						   csi_camera_get_frame(cam_handle, CAMERA_CHANNEL_ID, &frame, timeout);
-						   fNum--;
+        for (int j=0; j<chNum; j++){
+            if(event.type == CAMERA_CHANNEL_EVENT_TYPE[j]){
+                switch (event.id) {
+                    case CSI_CAMERA_CHANNEL_EVENT_OVERFLOW:
+                        printf("-------get channel EVENT CSI_CAMERA_CHANNEL_EVENT_OVERFLOW-------\n");
+                        break;
+                    case CSI_CAMERA_CHANNEL_EVENT_FRAME_READY: {
+                           int read_frame_count = csi_camera_get_frame_count(cam_handle,
+                                   CAMERA_CHANNEL_ID[j]);
+                           printf("-------read_frame_count=%d-------\n", read_frame_count);
+                           for (int i = 0; i < fCount; i++) {
+                               if (tid[j] != 0){
+                                    /* wait for previous image save thread end */
+                                    pthread_join(tid[j], NULL);
+                               }
+                               csi_camera_get_frame(cam_handle, CAMERA_CHANNEL_ID[j], &frame[j], timeout);
+                               if (afterOnOff[j] != 0 ){
+                               /* drop the first event after on/off operation */
+                                   afterOnOff[j]--;
+                                   csi_camera_put_frame(&frame[j]);
+                                //    csi_frame_release(&frame[j]);
+                                   continue;
+                               }
+                               fNum[j]--;
+                               fNumInc[j]++;
+                               if (fNum[j] < 0 && running == 0 ){
+                                   //csi_camera_frame_unlock(cam_handle, &frame[j]);
+                                   csi_camera_put_frame(&frame[j]);
+                                //    csi_frame_release(&frame[j]);
+                                   continue;
+                               }
 
-#ifdef PLATFORM_SIMULATOR
-						   show_frame_image(frame.img.usr_addr[0], frame.img.height, frame.img.width);
-#endif
-
-						   if (outMode == 0)
-							   save_camera_img(&frame);
-						   else
-							   save_camera_stream(&frame);
-
-						   csi_frame_release(&frame);
-					   }
-					   break;
-				   }
-				default:
-					   break;
-			}
-		}
-	}
-	csi_camera_channel_stop(cam_handle, CAMERA_CHANNEL_ID);
+    #ifdef PLATFORM_SIMULATOR
+                               show_frame_image(frame[j].img.usr_addr[0], frame[j].img.height, frame.img.width);
+    #endif
+                               fid[j]++;
+                               fnumTotal--;
+                               if (outMode == 0){
+                                   int * tIdx = malloc(sizeof(int));
+                                   *tIdx = j;
+                                   /* submit thread to save image for current channel then we can go to handle other channel */
+                                   pthread_create(&tid[j], NULL, save_camera_img, (void *)tIdx);
+                               }
+                               else if (outMode == 1){
+                                   int * tIdx = malloc(sizeof(int));
+                                   *tIdx = j;
+                                   pthread_create(&tid[j], NULL, save_camera_stream, (void *)tIdx);
+                                }
+                                else if(outMode == 3){
+                                   /* mode 3 only do performance test, no actual image saving */
+                                   gettimeofday(&cur_time, 0);
+                                   if (fid[j] == 1){
+                                       /* first frame */
+                                        first_frame = 1000000 * (cur_time.tv_sec-init_time.tv_sec)+ cur_time.tv_usec-init_time.tv_usec + video_open + channel_open + channel_start;
+                                   }
+                                   if (fnumTotal == 0){
+                                       /* last frame */
+                                        total_frame = 1000000 * (cur_time.tv_sec-init_time.tv_sec)+ cur_time.tv_usec-init_time.tv_usec;
+                                        fps = (float)frameTotal / total_frame * 1000000.0f;
+                                        printf("\n");
+                                        printf("\n");
+                                        printf("Performance data:\n");
+                                        printf("video_open:%lu ms\n", video_open/1000);
+                                        printf("channel_open:%lu ms\n", channel_open/1000);
+                                        printf("channel_start:%lu ms\n", channel_start/1000);
+                                        printf("first_frame:%lu ms\n", first_frame/1000);
+                                        printf("fps:%f fps\n", fps);
+                                        printf("\n");
+                                        printf("\n");
+                                   }
+                                   /* for mode 3, unlock in this branch, for mode 0,1 unlock in thread */
+                                   //csi_camera_frame_unlock(cam_handle, &frame[j]);
+                                   csi_camera_put_frame(&frame[j]);
+                                 
+                                }
+                                else{
+                                   chn_cfg[j].chn_id = j;
+                                   csi_camera_channel_query(cam_handle, &chn_cfg[j]);
+                                //    display_camera_frame(cam_handle, &chn_cfg[j], &frame[j]);
+                                   //csi_camera_frame_unlock(cam_handle, &frame[j]);
+                                   csi_camera_put_frame(&frame[j]);
+                                 
+                                }
+                           }
+                           break;
+                       }
+                    default:
+                           break;
+                }
+            }
+	    }
+    }
+    /* for IPC, update finish status to share-memory */
+    if(mi >= 2){
+        writer(buf, 0, 1);
+    }
+    for (int j=0; j<chNum; j++){
+        /* for IPC only do stop when share memory value equals mi */
+        if(mi >= 2){
+            while (1){
+                reader(buf, 0, &srv1);
+                if (srv1 != mi){
+                    sleep(2);
+                }
+                else{
+                    /* update the second value in share-memory which is used to decide whether to remove share-memory */
+                    writer(buf, 1, 1);
+                    reader(buf, 1, &srv2);
+                    if (srv2 == mi){
+                        /* I am the last process to update the buf[1], remove the share-memory */
+                        remove_s();
+                        printf("------IPC mode: remove-------\n");
+                    }
+                    break;
+                }
+            }
+        }
+	    csi_camera_channel_stop(cam_handle, CAMERA_CHANNEL_ID[j]);
+    }
+    if ( flashMode == 1){
+        csi_camera_led_disable(cam_handle, LED_FLOODLIGHT_PROJECTION);
+    }
 	usleep (1000000);
 	// 取消订阅某一个event, 也可以直接调用csi_camera_destory_event,结束所有的订阅
-	subscribe.type = CAMERA_CHANNEL_EVENT_TYPE;
-	subscribe.id = CSI_CAMERA_CHANNEL_EVENT_FRAME_READY;
-	csi_camera_unsubscribe_event(event_handle, &subscribe);
+    for (int j=0; j<chNum; j++){
+        subscribe.type = CAMERA_CHANNEL_EVENT_TYPE[j];
+        subscribe.id = CSI_CAMERA_CHANNEL_EVENT_FRAME_READY;
+        csi_camera_unsubscribe_event(event_handle, &subscribe);
+    }
 
 	csi_camera_destory_event(event_handle);
 
-	csi_camera_channel_close(cam_handle, CAMERA_CHANNEL_ID);
+    for (int j=0; j<chNum; j++){
+	    csi_camera_channel_close(cam_handle, CAMERA_CHANNEL_ID[j]);
+    }
 	csi_camera_close(cam_handle);
 }
 
-static void dump_camera_meta(csi_frame_s *frame)
+int pr_error(char *mess){
+    perror(mess);
+    exit(1);
+}
+
+/* function: get or create share-memory*/
+void getseg(struct databuf* *pdata){
+    /* try to get share-memory */
+    if((shmid = shmget(SHMKEY, sizeof(struct databuf), 0600 | IFLAGS)) < 0){
+        if(errno == EEXIST){
+            /* exist, return its ID */
+            shmid = shmget(SHMKEY, sizeof(struct databuf), 0600 | IPC_CREAT);
+            if(shmid < 0){
+                pr_error("--------share-memory getting: error!!!!!---------");
+            }
+        }
+        else {
+            pr_error("--------share-memory getting: other error!!!!!---------");
+        }
+    }
+    if((*pdata = (struct databuf *)(shmat(shmid, 0, 0))) < 0 ){
+        /* mapping share-memory */
+        pr_error("--------share-memory mapping error!!!!!---------");
+    }
+}
+
+/* function: get semaphore */
+int getsem(){
+    /* try to get or create semaphore */
+    if((semid = semget(SEMKEY, 1, 0600|IFLAGS)) < 0){
+        if(errno ==  EEXIST){
+            /* exist, reurn its ID */
+            semid = semget(SEMKEY, 1, 0600 | IPC_CREAT);
+            if(semid < 0){
+                pr_error("--------semaphore getting ID: error!!!!!---------");
+            }
+            else{
+                /* semaphore already exsit and return ID directly */
+                return semid;
+            }
+        }
+        else{
+            pr_error("--------semaphore getting: error!!!!!---------");
+        }
+    }
+    /* do semaphore init to 1 once just after semaphore creating */
+    if(semctl(semid, 0, SETVAL, 1) < 0){
+        pr_error("-----------semctl-----------");
+    }
+    return semid;
+}
+
+/* function remove share-memory and semaphore */
+void remove_s(){
+    if(shmctl(shmid, IPC_RMID, NULL) < 0)
+        pr_error("-----------shmctl when removing-----------");
+    if(semctl(semid, 0, IPC_RMID) < 0)
+        pr_error("-----------semctl when removing-----------");
+}
+
+/* function writer to share-memory */
+void writer(struct databuf *buf, int index, int value){
+    /* get semaphore before update share-memory */
+    semop(semid, &p1, 1);
+    /* update share-memory */
+    buf->d_buf[index] += value;
+    /* release semaphore */
+    semop(semid, &v1, 1);
+}
+
+/* function read to share-memory */
+void reader(struct databuf *buf, int index, int *rv){
+    /* get semaphore before update share-memory */
+    semop(semid, &p1, 1);
+    /* get share-memory value */
+    *rv = buf->d_buf[index];
+    /* release semaphore */
+    semop(semid, &v1, 1);
+}
+
+static void dump_camera_meta(csi_frame_ex_s *frame, int idx)
 {
 	int i;
 	//printf("%s\n", __func__);
-	if (frame->meta.type != CSI_META_TYPE_CAMERA)
+	if (frame->frame_meta.type != CSI_META_TYPE_CAMERA)
 		return;
 
-	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->meta.data;
+	csi_camera_meta_s *meta_data = (csi_camera_meta_s *)frame->frame_meta.data;
 	int meta_count = meta_data->count;
-	csi_camrea_meta_unit_s meta_unit;
+	csi_camera_meta_unit_s meta_unit;
+    csi_camera_meta_id_e meta_id;
 
-	for (i = 0; i < meta_count; i++) {
-		csi_camera_frame_get_meta_unit(
-				&meta_unit, meta_data, CSI_CAMERA_META_ID_FRAME_ID);
-		//printf("meta_id=%d, meta_type=%d, meta_value=%d",
-		//       meta_unit.id, meta_unit.type, meta_unit.int_value);
-	}
+    if(meta_mode > 0){
+        meta_id = (1<<(meta_mode - 1));
+        csi_camera_frame_get_meta_unit(
+                        &meta_unit, meta_data, meta_id);
+    }
+    if(meta_mode == 1 || meta_mode == 2){
+        /* camera_name and channel_id - which should keep same during testing */
+        cur_metaint[idx] = meta_unit.int_value;
+        if(pre_metaint[idx] == -1){
+            pre_metaint[idx] = cur_metaint[idx];
+        }
+        else{
+            if(cur_metaint[idx] != pre_metaint[idx]){
+                pr_error("-----meta test fail: camera_id or channel_id changes during test--------");
+            }
+            pre_metaint[idx] = cur_metaint[idx];
+            printf("-----meta test camera_name or channel_id:%d--------\n", cur_metaint[idx]);
+        }
+    }
+    else if(meta_mode == 3){
+        /* frame id - which should increase from 0 */
+        if(cur_metaint[idx] == -1 && meta_unit.int_value != 1){
+            pr_error("-----meta test fail: first frame ID is not 1--------\n");
+        }
+        cur_metaint[idx] = meta_unit.int_value;
+        if(pre_metaint[idx] == -1){
+            pre_metaint[idx] = cur_metaint[idx];
+        }
+        else{
+            if(cur_metaint[idx] != (pre_metaint[idx]+1)){
+                pr_error("-----meta test fail: frame_id is not continuous--------\n");
+            }
+            printf("-----meta test: meta_id: %d, frame_id:%d, previous_id: %d--------\n", meta_unit.id, cur_metaint[idx], pre_metaint[idx]);
+            pre_metaint[idx] = cur_metaint[idx];
+        }
+    }
+    else if(meta_mode == 4){
+        /* timestamps - which should be larger or equal to previous */
+        cur_metasec[idx] = meta_unit.time_value.tv_sec;
+        cur_metausec[idx] = meta_unit.time_value.tv_usec;
+        if(pre_metasec[idx] == -1){
+            pre_metasec[idx] = cur_metasec[idx];
+            pre_metausec[idx] = cur_metausec[idx];
+        }
+        else{
+            if(cur_metasec[idx] <= pre_metasec[idx] && cur_metausec[idx] <= pre_metausec[idx]){
+                pr_error("-----meta test fail: timestamp decrease--------");
+            }
+            printf("-----meta test time - second:%d--------\n", cur_metasec[idx]);
+            printf("-----meta test time - usecond:%d--------\n", cur_metausec[idx]);
+            pre_metasec[idx] = cur_metasec[idx];
+            pre_metausec[idx] = cur_metausec[idx];
+        }
+    }
+    else{
+        /* means meta_mode = 0 */
+        for (i = 0; i < meta_count; i++) {
+            meta_id = (1<<i);
+            csi_camera_frame_get_meta_unit(
+                    &meta_unit, meta_data, meta_id);
+            printf("meta_id=%d, meta_type=%d, meta_value=%d\n",
+                meta_unit.id, meta_unit.type, meta_unit.int_value);
+        }
+    }
 }
 
-static int save_camera_img(csi_frame_s *frame)
+/*
+function: parse the format and resolution to generate the output information used to save img
+Input args: index of channel will be tested whose order is decided when running
+Below information should be included:
+1. how may planars which will be store in global int PLANE[] array
+2. the pix bit  which will be store in global int PBIT[] array
+3. the bytes of each plane for the give channel to store in global int PLNS[][3] array
+4. the line numbers of each plane for the give channel to store in global int LNN[][3] array
+5. the bytes to store for each line size in each plane to store in  global int LSZ[][3] array
+*/
+static void parse_fmt_res(int cindx){
+    /* fetch the format the resolution information */
+    enum csi_pixel_fmt fmt = fenum[cindx];
+    int iw = hres[cindx];
+    int ih = vres[cindx];
+    /* decide the pixel bit number */
+	switch(fmt) {
+        case CSI_PIX_FMT_RAW_10BIT:
+            PBIT[cindx] = 10;
+			break;
+        case CSI_PIX_FMT_RAW_12BIT:
+            PBIT[cindx] = 12;
+			break;
+        case CSI_PIX_FMT_RAW_14BIT:
+            PBIT[cindx] = 14;
+			break;
+        case CSI_PIX_FMT_RAW_16BIT:
+            PBIT[cindx] = 16;
+			break;
+		default:
+            PBIT[cindx] = 8;
+			break;
+    }
+    /* decide plane numbers, each plane size(byte) and line and line size*/
+	switch(fmt) {
+        case CSI_PIX_FMT_RAW_8BIT:
+            PLNS[cindx][0] = iw * ih;
+            LNN[cindx][0] = ih;
+            LSZ[cindx][0] = iw * 2 ;
+            LNNV[cindx][0] = iw;
+            LSZV[cindx][0] = ih * 2 ;
+            PLANE[cindx] = 1;
+            NOSTRD[cindx] = 0;
+			break;
+        case CSI_PIX_FMT_RAW_10BIT:
+        case CSI_PIX_FMT_RAW_12BIT:
+        case CSI_PIX_FMT_RAW_14BIT:
+        case CSI_PIX_FMT_RAW_16BIT:
+            PLNS[cindx][0] = iw * ih * 2;
+            LNN[cindx][0] = ih;
+            LSZ[cindx][0] = iw * 2 ;
+            LNNV[cindx][0] = iw;
+            LSZV[cindx][0] = ih * 2 ;
+            PLANE[cindx] = 1;
+            NOSTRD[cindx] = 0;
+			break;
+        case CSI_PIX_FMT_RGB_INTEVLEAVED_888:
+        case CSI_PIX_FMT_YUV_TEVLEAVED_444:
+            PLNS[cindx][0] = (iw * ih * PBIT[cindx] / 8) * 3;
+            LNN[cindx][0] = ih;
+            LSZ[cindx][0] = (iw * PBIT[cindx] / 8) * 3;
+            LNNV[cindx][0] = iw;
+            LSZV[cindx][0] = (ih * PBIT[cindx] / 8) * 3;
+            PLANE[cindx] = 1;
+			break;
+        case CSI_PIX_FMT_YUV_TEVLEAVED_422:
+            PLNS[cindx][0] = (iw * ih * PBIT[cindx] / 8) * 2;
+            LNN[cindx][0] = ih;
+            LSZ[cindx][0] = (iw * PBIT[cindx] / 8) * 2;
+            LNNV[cindx][0] = iw;
+            LSZV[cindx][0] = (ih * PBIT[cindx] / 8) * 2;
+            PLANE[cindx] = 1;
+            break;
+        case CSI_PIX_FMT_YUV_TEVLEAVED_420:
+            PLNS[cindx][0] = ((iw * ih * PBIT[cindx] / 8) * 3) / 2;
+            LNN[cindx][0] = ih;
+            LSZ[cindx][0] = ((iw * PBIT[cindx] / 8) * 3) / 2;
+            LNNV[cindx][0] = iw;
+            LSZV[cindx][0] = ((ih * PBIT[cindx] / 8) * 3) / 2;
+            PLANE[cindx] = 1;
+			break;
+        case CSI_PIX_FMT_BGR:
+        case CSI_PIX_FMT_RGB_PLANAR_888:
+        case CSI_PIX_FMT_YUV_PLANAR_444:
+            PLNS[cindx][0] = (iw * ih * PBIT[cindx] / 8);
+            PLNS[cindx][1] = (iw * ih * PBIT[cindx] / 8);
+            PLNS[cindx][2] = (iw * ih * PBIT[cindx] / 8);
+            LNN[cindx][0] = ih;
+            LNN[cindx][1] = ih;
+            LNN[cindx][2] = ih;
+            LSZ[cindx][0] = LSZ[cindx][1] = LSZ[cindx][2] = (iw * PBIT[cindx] / 8);
+            LNNV[cindx][0] = iw;
+            LNNV[cindx][1] = iw;
+            LNNV[cindx][2] = iw;
+            LSZV[cindx][0] = LSZV[cindx][1] = LSZV[cindx][2] = (ih * PBIT[cindx] / 8);
+            PLANE[cindx] = 3;
+			break;
+        case CSI_PIX_FMT_YUV_PLANAR_422:
+            PLNS[cindx][0] = (iw * ih * PBIT[cindx] / 8);
+            PLNS[cindx][1] = (iw * ih * PBIT[cindx] / 8) / 2;
+            PLNS[cindx][2] = (iw * ih * PBIT[cindx] / 8) / 2;
+            LNN[cindx][0] = ih;
+            LNN[cindx][1] = ih / 2;
+            LNN[cindx][2] = ih / 2;
+            LSZ[cindx][0] = (iw * PBIT[cindx] / 8);
+            LSZ[cindx][1] = LSZ[cindx][2] = (iw * PBIT[cindx] / 8) / 2;
+            LNNV[cindx][0] = iw;
+            LNNV[cindx][1] = iw /2;
+            LNNV[cindx][2] = iw /2;
+            LSZV[cindx][0] = (ih * PBIT[cindx] / 8);
+            LSZV[cindx][1] = LSZV[cindx][2] = (ih * PBIT[cindx] / 8) / 2;
+            PLANE[cindx] = 3;
+			break;
+        case CSI_PIX_FMT_YUV_PLANAR_420:
+            PLNS[cindx][0] = (iw * ih * PBIT[cindx] / 8);
+            PLNS[cindx][1] = PLNS[cindx][2] = (iw * ih * PBIT[cindx] / 8) / 4;
+            LNN[cindx][0] = ih;
+            LNN[cindx][1] = LNN[cindx][2] = ih / 4;
+            LSZ[cindx][0] = (iw * PBIT[cindx] / 8);
+            LSZ[cindx][1] = LSZ[cindx][2] = (iw * PBIT[cindx] / 8) / 4;
+            LNNV[cindx][0] = iw;
+            LNNV[cindx][1] = LNNV[cindx][2] = iw / 4;
+            LSZV[cindx][0] = (ih * PBIT[cindx] / 8);
+            LSZV[cindx][1] = LSZV[cindx][2] = (ih * PBIT[cindx] / 8) / 4;
+            PLANE[cindx] = 3;
+			break;
+        case CSI_PIX_FMT_I420:
+        case CSI_PIX_FMT_NV12:
+        case CSI_PIX_FMT_YUV_SEMIPLANAR_420:
+            PLNS[cindx][0] = (iw * ih * PBIT[cindx] / 8);
+            PLNS[cindx][1] = (iw * ih * PBIT[cindx] / 8) / 2;
+            LNN[cindx][0] = ih;
+            LNN[cindx][1] = ih / 2;
+            LSZ[cindx][0] = LSZ[cindx][1] = (iw * PBIT[cindx] / 8);
+            LNNV[cindx][0] = iw;
+            LNNV[cindx][1] = iw / 2;
+            LSZV[cindx][0] = LSZV[cindx][1] = (ih * PBIT[cindx] / 8);
+            PLANE[cindx] = 2;
+			break;
+        case CSI_PIX_FMT_YUV_SEMIPLANAR_422:
+            PLNS[cindx][0] = PLNS[cindx][1] = (iw * ih * PBIT[cindx] / 8);
+            LNN[cindx][0] = ih;
+            LNN[cindx][1] = ih;
+            LSZ[cindx][0] = LSZ[cindx][0] = (iw * PBIT[cindx] / 8);
+            LNNV[cindx][0] = iw;
+            LNNV[cindx][1] = iw;
+            LSZV[cindx][0] = LSZV[cindx][0] = (ih * PBIT[cindx] / 8);
+            PLANE[cindx] = 2;
+			break;
+        case CSI_PIX_FMT_YUV_SEMIPLANAR_444:
+            PLNS[cindx][0] = (iw * ih * PBIT[cindx] / 8);
+            PLNS[cindx][1] = (iw * ih * PBIT[cindx] / 8) * 2;
+            LNN[cindx][0] = ih;
+            LNN[cindx][1] = ih * 2;
+            LSZ[cindx][0] = (iw * PBIT[cindx] / 8);
+            LSZ[cindx][1] = (iw * PBIT[cindx] / 8);
+            LNNV[cindx][0] = iw;
+            LNNV[cindx][1] = iw * 2;
+            LSZV[cindx][0] = (ih * PBIT[cindx] / 8);
+            LSZV[cindx][1] = (ih * PBIT[cindx] / 8);
+            PLANE[cindx] = 2;
+			break;
+		default:
+            PLNS[cindx][0] = (iw * ih * PBIT[cindx] / 8);
+            PLNS[cindx][1] = (iw * ih * PBIT[cindx] / 8) / 2;
+            LNN[cindx][0] = ih;
+            LNN[cindx][1] = ih / 2;
+            LSZ[cindx][0] = LSZ[cindx][1] = (iw * PBIT[cindx] / 8);
+            LNNV[cindx][0] = iw;
+            LNNV[cindx][1] = iw / 2;
+            LSZV[cindx][0] = LSZV[cindx][1] = (ih * PBIT[cindx] / 8);
+            PLANE[cindx] = 2;
+			break;
+    }
+}
+
+/*
+function: store image of each frame
+input1: frame
+input2: channel index
+input3: target file point
+input4: reverse mdoe for rotating 90 and 270 degree
+*/
+static void i_save(csi_frame_ex_s *framei, int cid, FILE *fp, int vmode)
+{
+    int lindex = 0;
+    int smode = 0;
+    if( vmode == 0){
+        if(framei->frame_data.stride[0] != LSZ[cid][0] && NOSTRD[cid] == 0){
+        //if(NOSTRD[cid] == 0){
+            smode = 1;
+            printf("-------------In Stride mode, framei->img.strides[0]=%d---------------\n", framei->frame_data.stride[0]);
+        }
+        else{
+            printf("-------------No Stride, framei->img.strides[0]=%d---------------\n", framei->frame_data.stride[0]);
+        }
+        for (int p = 0; p < PLANE[cid]; p++){
+            /* loop for each planar */
+            //printf("-------------framei->img.usr_addr[%d]=0x%llx---------------\n", p, framei->img.usr_addr[p]);
+            lindex = 0;
+            //int size = 0;
+            if(smode == 0){
+                /* no stride, write plane by plane*/
+            printf("-------------No Stride, length is = %d---------------\n", PLNS[cid][p]);
+                //while(size < PLNS[cid][p]){
+                 //   size += fwrite(framei->img.usr_addr[p] + size, sizeof(char), PLNS[cid][p] - size, fp);
+               // }
+                    fwrite(framei->frame_data.vir_addr[p], sizeof(char), PLNS[cid][p], fp);
+            }
+            else{
+                /* stride mode, write line by line */
+                for(int l = 0; l < LNN[cid][p]; l++){
+                    if(framei->frame_data.stride[p] == 0){
+                        printf("-------------Error: stride[%d] is 0---------------\n", p);
+                        lindex = LSZ[cid][p] * l;
+                    }
+                    else{
+                        /* for each plane, the strides[x] is the same */
+                        lindex = framei->frame_data.stride[0] * l;
+                    }
+                    fwrite(framei->frame_data.vir_addr[p] + lindex, sizeof(char), LSZ[cid][p], fp);
+                }
+            }
+        }
+    }
+    else{
+        if(framei->frame_data.stride[0] != LSZV[cid][0] && NOSTRD[cid] == 0){
+            smode = 1;
+            printf("-------------In Stride mode, framei->img.strides[0]=%d---------------\n", framei->frame_data.stride[0]);
+        }
+        else{
+            printf("-------------No Stride, framei->img.strides[0]=%d---------------\n", framei->frame_data.stride[0]);
+        }
+        for (int p = 0; p < PLANE[cid]; p++){
+            /* loop for each planar */
+            //printf("-------------framei->img.usr_addr[%d]=0x%llx---------------\n", p, framei->img.usr_addr[p]);
+            lindex = 0;
+            int size = 0;
+            if(smode == 0){
+                /* no stride, write plane by plane*/
+            printf("-------------No Stride, length is = %d---------------\n", PLNS[cid][p]);
+                while(size < PLNS[cid][p]){
+                    size += fwrite(framei->frame_data.vir_addr[p] + size, sizeof(char), PLNS[cid][p] - size, fp);
+                }
+            }
+            else{
+                /* stride mode, write line by line */
+                for(int l = 0; l < LNNV[cid][p]; l++){
+                    if(framei->frame_data.stride[p] == 0){
+                        printf("-------------Error: stride[%d] is 0---------------\n", p);
+                        lindex = LSZV[cid][p] * l;
+                    }
+                    else{
+                        /* for each plane, the strides[x] is the same */
+                        lindex = framei->frame_data.stride[0] * l;
+                    }
+                    fwrite(framei->frame_data.vir_addr[p] + lindex, sizeof(char), LSZV[cid][p], fp);
+                }
+            }
+        }
+    }
+}
+
+/*
+function: convert dma-buf file point to target address
+input1: framei
+input2: channel index
+*/
+// static void handle_dma_buf(csi_frame_ex_s *framei, int cid)
+// {
+//     if (frame->img.type == CSI_IMG_TYPE_DMA_BUF) {
+//         void *p[3] = {0};
+//         /*
+//            The first plane which exists always.
+//            All data for packed; Y data for planar or semi-planar
+//         */
+//         void *phyaddr = vi_mem_import(framei->img.dmabuf[0].fds);
+//         p[0] = vi_mem_map(phyaddr) + framei->img.dmabuf[0].offset;
+//         framei->img.usr_addr[0] = p[0];
+//         /*
+//            For other planes, in our solution, we only have plane[1] for
+//            planar or sp; or no other plane for packed.
+//         */
+//         for (int i=1; i<PLANE[cid]; i++){
+//             if (framei->img.dmabuf[i].offset != NULL){
+//                 p[i] = framei->img.dmabuf[i].offset + p[0];
+//                 framei->img.usr_addr[i] = p[i];
+//             }
+//             else{
+//                 printf("-------------DMA ERROR, no usr_addr for plane=%d---------------\n", i);
+//             }
+//         }
+//         vi_mem_release(phyaddr);
+//     }
+// }
+
+/*
+function: save data as image
+input1: channel index
+*/
+static void* save_camera_img(void * idx)
 {
-	static int fcount = 0;
-	char fname[20]; 
+    int index = *(int*)(idx);
+    free(idx);
+	char fname[512];
+	char fidname[256];
 	FILE *fp;
-	fcount = fcount%4;
-	sprintf(fname, "%s%d%s", "hal_image", fcount, ".yuv");
-	fcount++;
+	char fidc[128];
+    int fcount;
+    int fidi = fid[index];
+    int cid = channelIdx[index];
+    int hresi = hres[index];
+    int vresi = vres[index];
+    enum csi_pixel_fmt fmt = fenum[index];
+    csi_frame_ex_s *framei = &frame[index];
+    int vmode = 0;
+
+    if(framei->frame_info.width == vresi && framei->frame_info.height == hresi && vresi != hresi){
+        vmode = 1;
+        vresi = framei->frame_info.height;
+        hresi = framei->frame_info.width;
+    }
 
+    /* generate the image name */
+	fcount = fidi%tframes;
+	sprintf(fname, "%s%s%s%s%d%s%d%s%d%s%d%s%d%s%s", path, "/img_", dname, "_", PLANE[index], "P_", cid, "_", hresi, "x", vresi, "_", fcount, ".", fmtArray[fmt]);
+    /* dma-buf to address */
+    // handle_dma_buf(framei, index);
 	if((fp = fopen(fname, "wb")) == NULL){
 		printf("Error: Can't open file\n");
-		return -1;
+		return NULL;
 	}
-	fwrite(frame->img.usr_addr[0], sizeof(char), frame->img.size, fp);
-	fclose(fp);
-	return 0;
+    /* data saving */
+    i_save(framei, index, fp, vmode);
+    fclose(fp);
+
+    /* frame ID saving */
+    sprintf(fidc, "%d\n", fidi);
+    sprintf(fidname, "%s%s%s%s%d%s", path, "/fid_", dname, "_chn_", cid, ".txt");
+    if((fp = fopen(fidname, "a+")) == NULL){
+        printf("Error: Can't open file\n");
+        return NULL;
+    }
+    fwrite(fidc, sizeof(char), strlen(fidc), fp);
+    fclose(fp);
+    if(meta_mode >= 0){
+        dump_camera_meta(framei, index);
+    }
+    //csi_camera_frame_unlock(cam_handle, framei);
+    csi_camera_put_frame(framei);
+    // csi_frame_release(framei);
+    if (onoffMode == 1 && fNumInc[index] % onoffFrame == 0){
+        afterOnOff[index] = onoffDrop;
+        // stop stream, sleep, start stream
+        csi_camera_channel_stop(cam_handle, CAMERA_CHANNEL_ID[index]);
+        //sleep(1);
+        csi_camera_channel_start(cam_handle, CAMERA_CHANNEL_ID[index]);
+    }
+    return NULL;
 }
 
-static int save_camera_stream(csi_frame_s *frame)
+/*
+function: save data as stream
+input1: channel index
+*/
+static void* save_camera_stream(void *idx)
 {
-	FILE *fp;
-	char *fname = "hal_stream.yuv";
-	if((fp = fopen(fname, "ab+")) == NULL){
-		printf("Error: Can't open file\n");
-		return -1;
-	}
-	fwrite(frame->img.usr_addr[0], sizeof(char), frame->img.size, fp);
-	fclose(fp);
-	return 0;
+    int index = *(int*)(idx);
+
+    free(idx);
+    FILE *fp;
+    char fname[256];
+    int cid = channelIdx[index];
+    int hresi = hres[index];
+    int vresi = vres[index];
+    enum csi_pixel_fmt fmt = fenum[index];
+    csi_frame_ex_s *framei = &frame[index];
+    int vmode = 0;
+
+    if(framei->frame_info.width == vresi && framei->frame_info.height == hresi && vresi != hresi){
+        vmode = 1;
+        vresi = framei->frame_info.height;
+        hresi = framei->frame_info.width;
+    }
+
+    /* generate stream name - for each time it is the same name */
+	sprintf(fname, "%s%s%s%s%d%s%d%s%d%s%d%s%s", path, "/str_", dname, "_", PLANE[index], "P_", cid, "_", hresi, "x", vresi, ".", fmtArray[fmt]);
+    // handle_dma_buf(framei, index);
+    if((fp = fopen(fname, "ab+")) == NULL){
+        printf("Error: Can't open file\n");
+        return NULL;
+    }
+    i_save(framei, index, fp, vmode);
+    fclose(fp);
+    if(meta_mode >= 0){
+        dump_camera_meta(framei, index);
+    }
+
+    //csi_camera_frame_unlock(cam_handle, framei);
+    csi_camera_put_frame(framei);
+    // csi_frame_release(framei);
+    if (onoffMode == 1 && fNumInc[index] % onoffFrame == 0){
+        afterOnOff[index] = onoffDrop;
+        // stop stream, sleep, start stream
+        csi_camera_channel_stop(cam_handle, CAMERA_CHANNEL_ID[index]);
+        //sleep(1);
+        csi_camera_channel_start(cam_handle, CAMERA_CHANNEL_ID[index]);
+    }
+    return NULL;
 }
 
+// 同时配置多个参数
+static int set_properties(csi_cam_handle_t cam_handle, char *pArgs)
+{
+    csi_camera_properties_s properties;
+    csi_camera_property_s property[30];
+
+    char *pDelim=":/";
+    int pid;
+    int ptype;
+    int pvalueInt;
+    char *pvalueStr;
+    char *pFirst;
+    /*
+    parse multi-properties which delimited by : or /
+    1. / is used to seprate multi properties
+    2. : is used to sperate pid:type:value
+    for example: 1:2:1/2:2:1/3:1:90
+    */
+    pFirst = strtok(pArgs, pDelim);
+    int i = 0;
+    while(pFirst != NULL){
+        pid = atoi(pFirst);
+        property[i].id = pid + CSI_CAMERA_PID_BASE;
+        /*
+           property type difinition:
+           CSI_CAMERA_PROPERTY_TYPE_INTEGER    = 1,
+           CSI_CAMERA_PROPERTY_TYPE_BOOLEAN    = 2,
+           CSI_CAMERA_PROPERTY_TYPE_ENUM       = 3,
+           CSI_CAMERA_PROPERTY_TYPE_STRING     = 7,
+           CSI_CAMERA_PROPERTY_TYPE_BITMASK    = 8,
+         */
+        ptype = atoi(strtok(NULL, pDelim));
+        property[i].type = ptype;
+        if (ptype == CSI_CAMERA_PROPERTY_TYPE_STRING) {
+            pvalueStr = strtok(NULL, pDelim);
+            strcpy(property[i].value.str_value, pvalueStr);
+        }
+        else {
+            pvalueInt = atoi(strtok(NULL, pDelim));
+            property[i].value.int_value = pvalueInt;
+        }
+        i++;
+        pFirst = strtok(NULL, pDelim);
+    }
+
+    /* set multi-properties(here the property number is i) by calling API just one time */
+    properties.count = i;
+    properties.property = property;
+    if (csi_camera_set_property(cam_handle, &properties) < 0) {
+        printf("set_property fail!\n");
+        return -1;
+    }
+    printf("set_property ok!\n");
+    return 0;
+}
+
+static enum csi_pixel_fmt parse_format(char *fmt)
+{
+    for(int i=0; i<fmtMAX; i++){
+        if(strstr(fmtArray[i], fmt)){
+            return CSI_PIX_FMT_I420 + i;
+        }
+    }
+    return CSI_PIX_FMT_NV12;
+}

+ 1 - 1
examples/frame/frame_demo2_consumer.c

@@ -132,7 +132,7 @@ int consumer_process(int socket_fd)
 	csi_dump_img_info(&camera_frame.img);
 
 	csi_camera_meta_s *camera_meta_data = (csi_camera_meta_s *)camera_frame.meta.data;
-	camera_meta_data->units = (csi_camrea_meta_unit_s *)((char *)camera_meta_data + sizeof(csi_camera_meta_s));
+	camera_meta_data->units = (csi_camera_meta_unit_s *)((char *)camera_meta_data + sizeof(csi_camera_meta_s));
 	fdc_dump_camera_meta(camera_meta_data);
 
 	LOG_D("csi frame meta = {type=%d, size=%zd, data=%p}\n",

+ 1 - 1
examples/frame/frame_demo_common.c

@@ -164,7 +164,7 @@ int fdc_create_csi_frame(csi_frame_s *camera_frame,
 void fdc_dump_camera_meta(csi_camera_meta_s *camera_meta)
 {
 	int ret;
-	csi_camrea_meta_unit_s meta_unit;
+	csi_camera_meta_unit_s meta_unit;
 	ret = csi_camera_frame_get_meta_unit(&meta_unit, camera_meta, CSI_CAMERA_META_ID_TIMESTAMP);
 	if (ret == 0) {
 		struct timeval tv = meta_unit.time_value;

+ 7 - 4
include/hal/csi_camera.h

@@ -41,7 +41,7 @@ extern "C" {
  */
 
 #define CSI_CAMERA_VERSION_MAJOR	0
-#define CSI_CAMERA_VERSION_MINOR	2
+#define CSI_CAMERA_VERSION_MINOR	3
 
 #define CSI_CAMERA_NAME_MAX_LEN 32
 typedef void *csi_cam_handle_t;
@@ -110,6 +110,7 @@ typedef enum csi_camera_property_type {
 	CSI_CAMERA_PROPERTY_TYPE_ENUM		= 3,
 	CSI_CAMERA_PROPERTY_TYPE_STRING		= 7,
 	CSI_CAMERA_PROPERTY_TYPE_BITMASK	= 8,
+	CSI_CAMERA_PROPERTY_TYPE_FLOAT      = 9,
 } csi_camera_property_type_e;
 
 typedef union csi_camera_property_data {
@@ -118,6 +119,7 @@ typedef union csi_camera_property_data {
 	int      enum_value;
 	uint32_t bitmask_value;
 	char     str_value[32];
+    float    float_value;
 } csi_camera_property_data_u;
 
 typedef struct csi_camera_property_description {
@@ -177,6 +179,7 @@ typedef struct csi_camera_channel_cfg {
 	csi_img_type_e			img_type;
 	unsigned int			meta_fields;	/* bitmask of: csi_camera_meta_id_e */
 	csi_camera_channel_status_e	status;
+    csi_frame_alloctor_s   alloctor; /***external frame buffer allocater***/
 } csi_camera_channel_cfg_s;
 
 typedef enum csi_camera_event_type {
@@ -227,7 +230,7 @@ typedef struct csi_camera_event {
 typedef enum csi_camera_error{
     CSI_CAMERA_RET_ERR_INVALID_DEV = -1001,/* device is not valid */
     CSI_CAMERA_RET_ERR_INVALID_PARA, /* input params is not valid */
-    CSI_CAMERA_RET_ERR_NULL_PTR, 
+    CSI_CAMERA_RET_ERR_NULL_PTR,
     CSI_CAMERA_RET_ERR_DEV_BUSY,  /* device is budy */
     CSI_CAMERA_RET_ERR_NOMEM,   /* malloc fail */
     CSI_CAMERA_RET_ERR_TIMEOUT, /* evet or frame wait timeout */
@@ -274,9 +277,9 @@ int csi_camera_get_frame_count(csi_cam_handle_t cam_handle,
 			       csi_camera_channel_id_e chn_id);
 int csi_camera_get_frame(csi_cam_handle_t cam_handle,
 			 csi_camera_channel_id_e chn_id,
-			 csi_frame_s *frame, int timeout);
+			 csi_frame_ex_s *frame, int timeout);
 
-int csi_camera_put_frame(csi_frame_s *frame);
+int csi_camera_put_frame(csi_frame_ex_s *frame);
 
 
 int csi_camera_dequeue_frame(csi_cam_handle_t cam_handle,

+ 3 - 3
include/hal/csi_camera_frame.h

@@ -46,18 +46,18 @@ typedef struct csi_camrea_meta_unit {
 		char		str_value[32];
 		struct timeval  time_value;
 	};
-} csi_camrea_meta_unit_s;
+} csi_camera_meta_unit_s;
 
 typedef struct csi_camera_meta {
 	unsigned int            count;
 	size_t                  size;
-	csi_camrea_meta_unit_s *units;	// Is meta_unit array head
+	csi_camera_meta_unit_s *units;	// Is meta_unit array head
 } csi_camera_meta_s;
 
 int csi_camera_frame_alloc_meta(csi_camera_meta_s **meta, int meta_count, size_t *meta_data_size);
 int csi_camera_frame_free_meta(csi_camera_meta_s *meta);
 
-int csi_camera_frame_get_meta_unit(csi_camrea_meta_unit_s *meta_unit,
+int csi_camera_frame_get_meta_unit(csi_camera_meta_unit_s *meta_unit,
 				   csi_camera_meta_s      *meta_data,
 				   csi_camera_meta_id_e    meta_field);
 

+ 2 - 0
include/hal/csi_camera_property.h

@@ -92,6 +92,8 @@ enum CSI_CAMERA_AUTO_PRESET_WHITE_BALANCE_MODE {
 #define CSI_CAMERA_PID_BAND_STOP_FILTER    (CSI_CAMERA_PID_BASE + 0x62)
 #define CSI_CAMERA_PID_IMAGE_STABILIZATION (CSI_CAMERA_PID_BASE + 0x63)
 
+#define CSI_CAMERA_PID_GAIN                (CSI_CAMERA_PID_BASE + 0x64)
+
 #ifdef  __cplusplus
 }
 #endif

+ 1 - 25
include/hal/csi_frame.h

@@ -14,7 +14,7 @@
 #include <stdint.h>
 #include <unistd.h>
 #include <sys/types.h>
-
+#include "csi_meta.h"
 #ifdef __cplusplus
 extern "C" {
 #endif
@@ -62,14 +62,6 @@ typedef enum csi_color_gamut {
 	CSI_COLOR_GAMUT_BT2020,
 } csi_color_gamut_e;
 
-typedef enum csi_meta_type {
-	CSI_META_TYPE_SYSTEM,
-	CSI_META_TYPE_CAMERA,
-	CSI_META_TYPE_VDEC,
-	CSI_META_TYPE_GPU,
-	CSI_META_TYPE_G2D,
-} csi_meta_type_e;
-
 typedef enum csi_img_type {
 	CSI_IMG_TYPE_DMA_BUF,		// memory allocated via dma-buf
 	CSI_IMG_TYPE_SYSTEM_CONTIG,	// memory allocated via kmalloc
@@ -78,15 +70,6 @@ typedef enum csi_img_type {
 	CSI_IMG_TYPE_SHM,		// memory allocated from share memory(<sys/shm.h>)
 } csi_img_type_e;
 
-typedef enum csi_meta_value_type {
-	CSI_META_VALUE_TYPE_BOOL,
-	CSI_META_VALUE_TYPE_INT,
-	CSI_META_VALUE_TYPE_UINT,
-	CSI_META_VALUE_TYPE_STR,
-	CSI_META_VALUE_TYPE_TIMEVAL,
-} csi_meta_value_type_e;
-
-
 /*
  * CSI frame config design
  *
@@ -138,13 +121,6 @@ typedef struct csi_img {
 	uint64_t modifier;
     void *priv;
 } csi_img_s;
-
-typedef struct csi_meta {
-	csi_meta_type_e  type;
-	size_t           size;
-	void            *data;
-} csi_meta_s;
-
 typedef struct csi_frame {
 	csi_img_s  img;
 	csi_meta_s meta;

+ 9 - 60
include/hal/csi_frame_ex.h

@@ -5,67 +5,12 @@
 #define _CSI_FRAME_EX_H
 
 #include "csi_common.h"
+#include "csi_meta.h"
 #ifdef __cplusplus
 extern "C" {
 #endif
 #define MAX_PLANE_COUNT  3
 
-typedef enum {
-	CSI_PIXEL_FORMAT_RGB_444 = 0,
-	CSI_PIXEL_FORMAT_RGB_555,
-	CSI_PIXEL_FORMAT_RGB_565,
-	CSI_PIXEL_FORMAT_RGB_888,
-
-	CSI_PIXEL_FORMAT_BGR_444,
-	CSI_PIXEL_FORMAT_BGR_555,
-	CSI_PIXEL_FORMAT_BGR_565,
-	CSI_PIXEL_FORMAT_BGR_888,
-
-	CSI_PIXEL_FORMAT_ARGB_1555,
-	CSI_PIXEL_FORMAT_ARGB_4444,
-	CSI_PIXEL_FORMAT_ARGB_8565,
-	CSI_PIXEL_FORMAT_ARGB_8888,
-	CSI_PIXEL_FORMAT_ARGB_2BPP,
-
-	CSI_PIXEL_FORMAT_ABGR_1555,
-	CSI_PIXEL_FORMAT_ABGR_4444,
-	CSI_PIXEL_FORMAT_ABGR_8565,
-	CSI_PIXEL_FORMAT_ABGR_8888,
-
-	CSI_PIXEL_FORMAT_RGB_BAYER_8BPP,
-	CSI_PIXEL_FORMAT_RGB_BAYER_10BPP,
-	CSI_PIXEL_FORMAT_RGB_BAYER_12BPP,
-	CSI_PIXEL_FORMAT_RGB_BAYER_14BPP,
-	CSI_PIXEL_FORMAT_RGB_BAYER_16BPP,
-
-	CSI_PIXEL_FORMAT_YVU_PLANAR_422,
-	CSI_PIXEL_FORMAT_YVU_PLANAR_420,
-	CSI_PIXEL_FORMAT_YVU_PLANAR_444,
-
-	CSI_PIXEL_FORMAT_YVU_SEMIPLANAR_422,
-	CSI_PIXEL_FORMAT_YVU_SEMIPLANAR_420,
-	CSI_PIXEL_FORMAT_YVU_SEMIPLANAR_444,
-
-	CSI_PIXEL_FORMAT_YUV_SEMIPLANAR_422,
-	CSI_PIXEL_FORMAT_YUV_SEMIPLANAR_420,
-	CSI_PIXEL_FORMAT_YUV_SEMIPLANAR_444,
-
-	CSI_PIXEL_FORMAT_YUYV_PACKAGE_422,
-	CSI_PIXEL_FORMAT_YVYU_PACKAGE_422,
-	CSI_PIXEL_FORMAT_UYVY_PACKAGE_422,
-	CSI_PIXEL_FORMAT_VYUY_PACKAGE_422,
-	CSI_PIXEL_FORMAT_YYUV_PACKAGE_422,
-	CSI_PIXEL_FORMAT_YYVU_PACKAGE_422,
-	CSI_PIXEL_FORMAT_UVYY_PACKAGE_422,
-	CSI_PIXEL_FORMAT_VUYY_PACKAGE_422,
-	CSI_PIXEL_FORMAT_VY1UY0_PACKAGE_422,
-
-	CSI_PIXEL_FORMAT_YUV_400,
-	CSI_PIXEL_FORMAT_UV_420,
-
-	CSI_PIXEL_FORMAT_MAX
-} csi_pixel_format_e;
-
 #if 0
 typedef enum {
 	CSI_PICTURE_TYPE_NONE = 0, /* undefined */
@@ -129,13 +74,12 @@ typedef enum {
 	CSI_VIDEO_FORMAT_MAC
 } csi_video_format_e;
 
-
 typedef struct csi_frame_info {
 	int32_t width;
 	int32_t height;
 	/* the region of interest of the frame */
 	//csi_rect_s roi;
-	csi_pixel_format_e pixel_format;
+	int32_t pixel_format;   //define in csi_pixel_fmt_e
 	//csi_frame_compress_mode compress_mode;
 	csi_color_space_e  color_space;
 	csi_chroma_location_e chroma_location;
@@ -159,13 +103,18 @@ typedef struct csi_frame_data {
 	};
 } csi_frame_data_s;
 
-
 typedef struct csi_frame_ex {
 	csi_frame_info_s frame_info;
 	csi_frame_data_s frame_data;
-	void *opaque; /* not for user, DO NOT use or modify it */
+    csi_meta_s frame_meta;
+	void *opaque; /* for user private data, csi NOT use or modify it */
+    void *csi_priv;/**for csi private data,user NOT use or modify it***************/
 } csi_frame_ex_s;
 
+typedef struct csi_frame_alloctor{
+    int (*alloc)(csi_frame_ex_s * frame); /* base on the frame info,alloc fill the fd */
+    int (*free)(csi_frame_ex_s * frame);
+}csi_frame_alloctor_s;
 #if 0
 typedef struct csi_bitstream {
 	void *buf;

+ 46 - 0
include/hal/csi_meta.h

@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2021 Alibaba Group Holding Limited
+ * Author: LuChongzhi <chongzhi.lcz@alibaba-inc.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+
+#ifndef __CSI_META_H__
+#define __CSI_META_H__
+
+#include <stddef.h>
+#include <stdint.h>
+#include <unistd.h>
+#include <sys/types.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+typedef enum csi_meta_type {
+	CSI_META_TYPE_SYSTEM,
+	CSI_META_TYPE_CAMERA,
+	CSI_META_TYPE_VDEC,
+	CSI_META_TYPE_GPU,
+	CSI_META_TYPE_G2D,
+} csi_meta_type_e;
+typedef enum csi_meta_value_type {
+	CSI_META_VALUE_TYPE_BOOL,
+	CSI_META_VALUE_TYPE_INT,
+	CSI_META_VALUE_TYPE_UINT,
+	CSI_META_VALUE_TYPE_STR,
+	CSI_META_VALUE_TYPE_TIMEVAL,
+} csi_meta_value_type_e;
+
+typedef struct csi_meta {
+	csi_meta_type_e  type;
+	size_t           size;
+	void            *data;
+} csi_meta_s;
+
+#ifdef  __cplusplus
+}
+#endif
+
+#endif /* __CSI_META_H__ */

+ 2 - 2
src/lib_camera/camera_action/include/platform_action.h

@@ -11,8 +11,8 @@
 #define __PLATFORM_ACTION_H__
 
 #include <csi_camera.h>
-int camera_action_image_save(csi_frame_s *frame);
-int camera_action_image_display(csi_frame_s *frame);
+int camera_action_image_save(csi_frame_ex_s *frame);
+int camera_action_image_display(csi_frame_ex_s *frame);
 
 #endif
 

+ 2 - 2
src/lib_camera/camera_action/src/platform/light/platform_action_light.c

@@ -14,13 +14,13 @@
 
 #include <stdio.h>
 
-int camera_action_image_save(csi_frame_s *frame)
+int camera_action_image_save(csi_frame_ex_s *frame)
 {
 	//wait to complete
 	return 0;
 }
 
-int camera_action_image_display(csi_frame_s *frame)
+int camera_action_image_display(csi_frame_ex_s *frame)
 {
 	//wait to complete
 	return 0;

+ 1 - 1
src/platform/light/csi_camera_frame.c

@@ -24,7 +24,7 @@ int csi_camera_frame_free_meta(csi_camera_meta_s *meta)
 	return 0;
 }
 
-int csi_camera_frame_get_meta_unit(csi_camrea_meta_unit_s *meta_unit,
+int csi_camera_frame_get_meta_unit(csi_camera_meta_unit_s *meta_unit,
 				   csi_camera_meta_s      *meta_data,
 				   csi_camera_meta_id_e    meta_field)
 {

+ 5 - 5
src/platform/simulator/csi_camera_frame.c

@@ -23,8 +23,8 @@ int csi_camera_frame_alloc_meta(csi_camera_meta_s **meta, int meta_count, size_t
 		return -1;
 	}
 
-	malloc_size = sizeof(csi_camera_meta_s) + sizeof(csi_camrea_meta_unit_s) * meta_count;
-	LOG_D("malloc_size=(%zd+%zd)=%zd\n", sizeof(csi_camera_meta_s), sizeof(csi_camrea_meta_unit_s) * meta_count, malloc_size);
+	malloc_size = sizeof(csi_camera_meta_s) + sizeof(csi_camera_meta_unit_s) * meta_count;
+	LOG_D("malloc_size=(%zd+%zd)=%zd\n", sizeof(csi_camera_meta_s), sizeof(csi_camera_meta_unit_s) * meta_count, malloc_size);
 
 	*meta = malloc(malloc_size);
 	if (*meta == NULL) {
@@ -34,8 +34,8 @@ int csi_camera_frame_alloc_meta(csi_camera_meta_s **meta, int meta_count, size_t
 
 	memset(*meta, 0, malloc_size);
 	(*meta)->count = meta_count;
-	(*meta)->size = sizeof(csi_camrea_meta_unit_s) * meta_count;
-	(*meta)->units = (csi_camrea_meta_unit_s *)((char*)(*meta) + sizeof(csi_camera_meta_s));
+	(*meta)->size = sizeof(csi_camera_meta_unit_s) * meta_count;
+	(*meta)->units = (csi_camera_meta_unit_s *)((char*)(*meta) + sizeof(csi_camera_meta_s));
 
 	LOG_D("*meta=%p, (*meta)->units=%p\n", *meta, (*meta)->units);
 
@@ -55,7 +55,7 @@ int csi_camera_frame_free_meta(csi_camera_meta_s *meta)
 	return 0;
 }
 
-int csi_camera_frame_get_meta_unit(csi_camrea_meta_unit_s *meta_unit,
+int csi_camera_frame_get_meta_unit(csi_camera_meta_unit_s *meta_unit,
 				   csi_camera_meta_s      *meta_data,
 				   csi_camera_meta_id_e    meta_field)
 {