diff --git a/configure b/configure index 21da64841a..b6a17b1c5a 100755 --- a/configure +++ b/configure @@ -725,6 +725,8 @@ HAVE_LIST=" getrusage imlib2 inet_aton + libdc1394_1 + libdc1394_2 llrint lrint lrintf @@ -1633,7 +1635,6 @@ enabled avisynth && require2 vfw32 "windows.h vfw.h" AVIFileInit -lvfw32 enabled liba52 && require liba52 a52dec/a52.h a52_init -la52 enabled libamr_nb && require libamrnb amrnb/interf_dec.h Speech_Decode_Frame_init -lamrnb -lm enabled libamr_wb && require libamrwb amrwb/dec_if.h D_IF_init -lamrwb -lm -enabled libdc1394 && require libdc1394 libdc1394/dc1394_control.h dc1394_create_handle -ldc1394_control -lraw1394 enabled libfaac && require2 libfaac "stdint.h faac.h" faacEncGetVersion -lfaac enabled libfaad && require2 libfaad faad.h faacDecOpen -lfaad enabled libgsm && require libgsm gsm.h gsm_create -lgsm @@ -1648,6 +1649,16 @@ enabled mlib && require mediaLib mlib_types.h mlib_VectorSub_S16_U8_Mod - # disable the native AC-3 decoder if liba52 is enabled enabled liba52 && disable ac3_decoder +# libdc1394 check +if enabled libdc1394; then + { check_lib dc1394/dc1394.h dc1394_new -ldc1394 -lraw1394 && + enable libdc1394_2; } || + { check_lib libdc1394/dc1394_control.h dc1394_create_handle -ldc1394_control -lraw1394 && + enable libdc1394_1; } || + die "ERROR: No version of libdc1394 found " +fi + + _restrict= for restrict_keyword in restrict __restrict__ __restrict; do check_cc < +#elif ENABLE_LIBDC1394_1 #include #include +#define DC1394_VIDEO_MODE_320x240_YUV422 MODE_320x240_YUV422 +#define DC1394_VIDEO_MODE_640x480_YUV411 MODE_640x480_YUV411 +#define DC1394_VIDEO_MODE_640x480_YUV422 MODE_640x480_YUV422 +#define DC1394_FRAMERATE_1_875 FRAMERATE_1_875 +#define DC1394_FRAMERATE_3_75 FRAMERATE_3_75 +#define DC1394_FRAMERATE_7_5 FRAMERATE_7_5 +#define DC1394_FRAMERATE_15 FRAMERATE_15 +#define DC1394_FRAMERATE_30 FRAMERATE_30 +#define DC1394_FRAMERATE_60 FRAMERATE_60 +#endif + #undef free typedef struct dc1394_data { +#if ENABLE_LIBDC1394_1 raw1394handle_t handle; dc1394_cameracapture camera; +#elif ENABLE_LIBDC1394_2 + dc1394_t *d; + dc1394camera_t *camera; + dc1394video_frame_t *frame; +#endif int current_frame; int fps; @@ -41,9 +63,9 @@ struct dc1394_frame_format { enum PixelFormat pix_fmt; int frame_size_id; } dc1394_frame_formats[] = { - { 320, 240, PIX_FMT_UYVY422, MODE_320x240_YUV422 }, - { 640, 480, PIX_FMT_UYYVYY411, MODE_640x480_YUV411 }, - { 640, 480, PIX_FMT_UYVY422, MODE_640x480_YUV422 }, + { 320, 240, PIX_FMT_UYVY422, DC1394_VIDEO_MODE_320x240_YUV422 }, + { 640, 480, PIX_FMT_UYYVYY411, DC1394_VIDEO_MODE_640x480_YUV411 }, + { 640, 480, PIX_FMT_UYVY422, DC1394_VIDEO_MODE_640x480_YUV422 }, { 0, 0, 0, 0 } /* gotta be the last one */ }; @@ -51,21 +73,20 @@ struct dc1394_frame_rate { int frame_rate; int frame_rate_id; } dc1394_frame_rates[] = { - { 1875, FRAMERATE_1_875 }, - { 3750, FRAMERATE_3_75 }, - { 7500, FRAMERATE_7_5 }, - { 15000, FRAMERATE_15 }, - { 30000, FRAMERATE_30 }, - { 60000, FRAMERATE_60 }, + { 1875, DC1394_FRAMERATE_1_875 }, + { 3750, DC1394_FRAMERATE_3_75 }, + { 7500, DC1394_FRAMERATE_7_5 }, + { 15000, DC1394_FRAMERATE_15 }, + { 30000, DC1394_FRAMERATE_30 }, + { 60000, DC1394_FRAMERATE_60 }, { 0, 0 } /* gotta be the last one */ }; -static int dc1394_read_header(AVFormatContext *c, AVFormatParameters * ap) +static inline int dc1394_read_common(AVFormatContext *c, AVFormatParameters *ap, + struct dc1394_frame_format **select_fmt, struct dc1394_frame_rate **select_fps) { dc1394_data* dc1394 = c->priv_data; AVStream* vst; - nodeid_t* camera_nodes; - int res; struct dc1394_frame_format *fmt; struct dc1394_frame_rate *fps; enum PixelFormat pix_fmt = ap->pix_fmt == PIX_FMT_NONE ? PIX_FMT_UYVY422 : ap->pix_fmt; /* defaults */ @@ -90,7 +111,7 @@ static int dc1394_read_header(AVFormatContext *c, AVFormatParameters * ap) /* create a video stream */ vst = av_new_stream(c, 0); if (!vst) - return -1; + goto out; av_set_pts_info(vst, 64, 1, 1000); vst->codec->codec_type = CODEC_TYPE_VIDEO; vst->codec->codec_id = CODEC_ID_RAWVIDEO; @@ -110,6 +131,25 @@ static int dc1394_read_header(AVFormatContext *c, AVFormatParameters * ap) dc1394->fps = fps->frame_rate; vst->codec->bit_rate = av_rescale(dc1394->packet.size * 8, fps->frame_rate, 1000); + *select_fps = fps; + *select_fmt = fmt; + return 0; +out: + return -1; +} + +#if ENABLE_LIBDC1394_1 +static int dc1394_v1_read_header(AVFormatContext *c, AVFormatParameters * ap) +{ + dc1394_data* dc1394 = c->priv_data; + AVStream* vst; + nodeid_t* camera_nodes; + int res; + struct dc1394_frame_format *fmt = NULL; + struct dc1394_frame_rate *fps = NULL; + + if (dc1394_read_common(c,ap,&fmt,&fps) != 0) + return -1; /* Now lets prep the hardware */ dc1394->handle = dc1394_create_handle(0); /* FIXME: gotta have ap->port */ @@ -153,7 +193,7 @@ out: return -1; } -static int dc1394_read_packet(AVFormatContext *c, AVPacket *pkt) +static int dc1394_v1_read_packet(AVFormatContext *c, AVPacket *pkt) { struct dc1394_data *dc1394 = c->priv_data; int res; @@ -180,7 +220,7 @@ static int dc1394_read_packet(AVFormatContext *c, AVPacket *pkt) return res; } -static int dc1394_close(AVFormatContext * context) +static int dc1394_v1_close(AVFormatContext * context) { struct dc1394_data *dc1394 = context->priv_data; @@ -192,12 +232,137 @@ static int dc1394_close(AVFormatContext * context) return 0; } +#elif ENABLE_LIBDC1394_2 +static int dc1394_v2_read_header(AVFormatContext *c, AVFormatParameters * ap) +{ + dc1394_data* dc1394 = c->priv_data; + dc1394camera_list_t *list; + int res, i; + struct dc1394_frame_format *fmt = NULL; + struct dc1394_frame_rate *fps = NULL; + + if (dc1394_read_common(c,ap,&fmt,&fps) != 0) + return -1; + + /* Now lets prep the hardware */ + dc1394->d = dc1394_new(); + dc1394_camera_enumerate (dc1394->d, &list); + if ( !list || list->num == 0) { + av_log(c, AV_LOG_ERROR, "Unable to look for an IIDC camera\n\n"); + goto out; + } + + /* FIXME: To select a specific camera I need to search in list its guid */ + dc1394->camera = dc1394_camera_new (dc1394->d, list->ids[0].guid); + if (list->num > 1) { + av_log(c, AV_LOG_INFO, "Working with the first camera found\n"); + } + + /* Freeing list of cameras */ + dc1394_camera_free_list (list); + + /* Select MAX Speed possible from the cam */ + if (dc1394->camera->bmode_capable>0) { + dc1394_video_set_operation_mode(dc1394->camera, DC1394_OPERATION_MODE_1394B); + i = DC1394_ISO_SPEED_800; + } else { + i = DC1394_ISO_SPEED_400; + } + + for (res = DC1394_FAILURE; i >= DC1394_ISO_SPEED_MIN && res != DC1394_SUCCESS; i--) { + res=dc1394_video_set_iso_speed(dc1394->camera, i); + } + if (res != DC1394_SUCCESS) { + av_log(c, AV_LOG_ERROR, "Couldn't set ISO Speed\n"); + goto out_camera; + } + + if (dc1394_video_set_mode(dc1394->camera, fmt->frame_size_id) != DC1394_SUCCESS) { + av_log(c, AV_LOG_ERROR, "Couldn't set video format\n"); + goto out_camera; + } + + if (dc1394_video_set_framerate(dc1394->camera,fps->frame_rate_id) != DC1394_SUCCESS) { + av_log(c, AV_LOG_ERROR, "Couldn't set framerate %d \n",fps->frame_rate); + goto out_camera; + } + if (dc1394_capture_setup(dc1394->camera, 10, DC1394_CAPTURE_FLAGS_DEFAULT)!=DC1394_SUCCESS) { + av_log(c, AV_LOG_ERROR, "Cannot setup camera \n"); + goto out_camera; + } + + if (dc1394_video_set_transmission(dc1394->camera, DC1394_ON) !=DC1394_SUCCESS) { + av_log(c, AV_LOG_ERROR, "Cannot start capture\n"); + goto out_camera; + } + return 0; + +out_camera: + dc1394_capture_stop(dc1394->camera); + dc1394_video_set_transmission(dc1394->camera, DC1394_OFF); + dc1394_camera_free (dc1394->camera); +out: + dc1394_free(dc1394->d); + return -1; +} + +static int dc1394_v2_read_packet(AVFormatContext *c, AVPacket *pkt) +{ + struct dc1394_data *dc1394 = c->priv_data; + int res; + + /* discard stale frame */ + if (dc1394->current_frame++) { + if (dc1394_capture_enqueue(dc1394->camera, dc1394->frame) != DC1394_SUCCESS) + av_log(c, AV_LOG_ERROR, "failed to release %d frame\n", dc1394->current_frame); + } + + res = dc1394_capture_dequeue(dc1394->camera, DC1394_CAPTURE_POLICY_WAIT, &dc1394->frame); + if (res == DC1394_SUCCESS) { + dc1394->packet.data = (uint8_t *)(dc1394->frame->image); + dc1394->packet.pts = (dc1394->current_frame * 1000000) / (dc1394->fps); + res = dc1394->frame->image_bytes; + } else { + av_log(c, AV_LOG_ERROR, "DMA capture failed\n"); + dc1394->packet.data = NULL; + res = -1; + } + + *pkt = dc1394->packet; + return res; +} + +static int dc1394_v2_close(AVFormatContext * context) +{ + struct dc1394_data *dc1394 = context->priv_data; + + dc1394_video_set_transmission(dc1394->camera, DC1394_OFF); + dc1394_capture_stop(dc1394->camera); + dc1394_camera_free(dc1394->camera); + dc1394_free(dc1394->d); + + return 0; +} + AVInputFormat libdc1394_demuxer = { .name = "libdc1394", - .long_name = "dc1394 A/V grab", + .long_name = "dc1394 v.2 A/V grab", .priv_data_size = sizeof(struct dc1394_data), - .read_header = dc1394_read_header, - .read_packet = dc1394_read_packet, - .read_close = dc1394_close, + .read_header = dc1394_v2_read_header, + .read_packet = dc1394_v2_read_packet, + .read_close = dc1394_v2_close, .flags = AVFMT_NOFILE }; + +#endif +#if ENABLE_LIBDC1394_1 +AVInputFormat libdc1394_demuxer = { + .name = "libdc1394", + .long_name = "dc1394 v.1 A/V grab", + .priv_data_size = sizeof(struct dc1394_data), + .read_header = dc1394_v1_read_header, + .read_packet = dc1394_v1_read_packet, + .read_close = dc1394_v1_close, + .flags = AVFMT_NOFILE +}; +#endif