1 /* $Id: scan.c,v 1.52 2005/11/25 15:05:25 titer Exp $
3 This file is part of the HandBrake source code.
4 Homepage: <http://handbrake.m0k.org/>.
5 It may be used under the terms of the GNU General Public License. */
8 #include "a52dec/a52.h"
17 hb_list_t * list_title;
24 static void ScanFunc( void * );
25 static int DecodePreviews( hb_scan_t *, hb_title_t * title );
26 static void LookForAC3AndDCA( hb_title_t * title, hb_buffer_t * b );
27 static int AllAC3AndDCAOK( hb_title_t * title );
29 hb_thread_t * hb_scan_init( hb_handle_t * handle, const char * path,
30 int title_index, hb_list_t * list_title )
32 hb_scan_t * data = calloc( sizeof( hb_scan_t ), 1 );
35 data->path = strdup( path );
36 data->title_index = title_index;
37 data->list_title = list_title;
39 return hb_thread_init( "scan", ScanFunc, data, HB_NORMAL_PRIORITY );
42 static void ScanFunc( void * _data )
44 hb_scan_t * data = (hb_scan_t *) _data;
51 /* Try to open the path as a DVD. If it fails, try as a file */
52 hb_log( "scan: trying to open with libdvdread" );
53 if( ( data->dvd = hb_dvd_init( data->path ) ) )
55 hb_log( "scan: DVD has %d title(s)",
56 hb_dvd_title_count( data->dvd ) );
57 if( data->title_index )
59 /* Scan this title only */
60 hb_list_add( data->list_title, hb_dvd_title_scan( data->dvd,
61 data->title_index ) );
66 for( i = 0; i < hb_dvd_title_count( data->dvd ); i++ )
68 hb_list_add( data->list_title,
69 hb_dvd_title_scan( data->dvd, i + 1 ) );
73 else if ( (data->stream = hb_stream_open (data->path)) != NULL )
75 hb_list_add( data->list_title, hb_stream_title_scan( data->stream ) );
79 hb_log( "scan: unrecognized file type" );
83 for( i = 0; i < hb_list_count( data->list_title ); )
88 hb_title_t * title_tmp = NULL;
90 title = hb_list_item( data->list_title, i );
92 /* I've seen a DVD with strictly identical titles. Check this
93 here and ignore it if redundant */
94 for( j = 0; j < i; j++ )
96 title_tmp = hb_list_item( data->list_title, j );
97 if( title->vts == title_tmp->vts &&
98 title->block_start == title_tmp->block_start &&
99 title->block_end == title_tmp->block_end &&
100 title->block_count == title_tmp->block_count )
111 hb_log( "scan: title %d is duplicate with title %d",
112 title->index, title_tmp->index );
113 hb_list_rem( data->list_title, title );
114 free( title ); /* This _will_ leak! */
118 #define p state.param.scanning
120 state.state = HB_STATE_SCANNING;
121 p.title_cur = title->index;
122 p.title_count = data->dvd ? hb_dvd_title_count( data->dvd ) : hb_list_count(data->list_title);
123 hb_set_state( data->h, &state );
126 /* Decode previews */
127 /* this will also detect more AC3 / DTS information */
128 if( !DecodePreviews( data, title ) )
130 /* TODO: free things */
131 hb_list_rem( data->list_title, title );
137 // Stream based processing uses PID's to handle the different audio options for a given title
138 for( j = 0; j < hb_list_count( title->list_audio ); j++ )
140 audio = hb_list_item( title->list_audio, j );
141 hb_stream_update_audio(data->stream, audio);
146 /* Make sure we found AC3 rates and bitrates */
147 for( j = 0; j < hb_list_count( title->list_audio ); )
149 audio = hb_list_item( title->list_audio, j );
150 if( audio->codec == HB_ACODEC_AC3 &&
153 hb_list_rem( title->list_audio, audio );
161 /* Make sure we found AC3 / DCA rates and bitrates */
162 for( j = 0; j < hb_list_count( title->list_audio ); )
164 audio = hb_list_item( title->list_audio, j );
165 if( ( audio->codec == HB_ACODEC_AC3 || audio->codec == HB_ACODEC_DCA ) &&
168 hb_log( "scan: removing audio with codec of 0x%x because of no bitrate",
170 hb_list_rem( title->list_audio, audio );
177 /* Do we still have audio */
178 if( !hb_list_count( title->list_audio ) )
180 hb_list_rem( data->list_title, title );
185 /* set a default input channel layout of stereo for LPCM or MPEG2 audio */
186 /* AC3 and DCA will already have had their layout set via DecodePreviews above, */
187 /* which calls LookForAC3AndDCA */
188 for( j = 0; j < hb_list_count( title->list_audio ); j++ )
190 audio = hb_list_item( title->list_audio, j );
191 if( audio->codec == HB_ACODEC_LPCM || audio->codec == HB_ACODEC_MPGA )
193 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_STEREO;
200 /* Init jobs templates */
201 for( i = 0; i < hb_list_count( data->list_title ); i++ )
205 title = hb_list_item( data->list_title, i );
206 job = calloc( sizeof( hb_job_t ), 1 );
211 /* Set defaults settings */
212 job->chapter_start = 1;
213 job->chapter_end = hb_list_count( title->list_chapter );
215 /* Autocrop by default. Gnark gnark */
216 memcpy( job->crop, title->crop, 4 * sizeof( int ) );
218 if( title->aspect == 16 )
220 hb_reduce( &job->pixel_aspect_width, &job->pixel_aspect_height,
221 16 * title->height, 9 * title->width );
225 hb_reduce( &job->pixel_aspect_width, &job->pixel_aspect_height,
226 4 * title->height, 3 * title->width );
229 job->width = title->width - job->crop[2] - job->crop[3];
230 // job->height = title->height - job->crop[0] - job->crop[1];
231 hb_fix_aspect( job, HB_KEEP_WIDTH );
232 if( job->height > title->height - job->crop[0] - job->crop[1] )
234 job->height = title->height - job->crop[0] - job->crop[1];
235 hb_fix_aspect( job, HB_KEEP_HEIGHT );
238 hb_log( "scan: title (%d) job->width:%d, job->height:%d",
239 i,job->width, job->height );
243 job->vcodec = HB_VCODEC_FFMPEG;
244 job->vquality = -1.0;
245 job->vbitrate = 1000;
247 job->vrate = title->rate;
248 job->vrate_base = title->rate_base;
253 job->acodec = HB_ACODEC_FAAC;
259 job->mux = HB_MUX_MP4;
264 hb_dvd_close( &data->dvd );
268 hb_stream_close(&data->stream);
275 /***********************************************************************
277 ***********************************************************************
278 * Decode 10 pictures for the given title.
279 * It assumes that data->reader and data->vts have successfully been
280 * DVDOpen()ed and ifoOpen()ed.
281 **********************************************************************/
282 static int DecodePreviews( hb_scan_t * data, hb_title_t * title )
285 hb_buffer_t * buf_ps, * buf_es, * buf_raw;
286 hb_list_t * list_es, * list_raw;
287 hb_libmpeg2_t * mpeg2;
288 int progressive_count = 0;
290 buf_ps = hb_buffer_init( HB_DVD_READ_BUFFER_SIZE );
291 list_es = hb_list_init();
292 list_raw = hb_list_init();
294 hb_log( "scan: decoding previews for title %d", title->index );
297 hb_dvd_start( data->dvd, title->index, 1 );
299 for( i = 0; i < 10; i++ )
305 //hb_log("Seeking to: %f", (float) ( i + 1 ) / 11.0 );
309 if( !hb_dvd_seek( data->dvd, (float) ( i + 1 ) / 11.0 ) )
314 else if (data->stream)
316 if (!hb_stream_seek(data->stream, (float) ( i + 1 ) / 11.0 ) )
322 hb_log( "scan: preview %d", i + 1 );
324 mpeg2 = hb_libmpeg2_init();
326 for( j = 0; j < 10240 ; j++ )
330 if( !hb_dvd_read( data->dvd, buf_ps ) )
332 hb_log( "Warning: Could not read data for preview %d, skipped", i + 1 );
336 else if (data->stream)
338 if ( !hb_stream_read(data->stream,buf_ps) )
340 hb_log( "Warning: Could not read data for preview %d, skipped", i + 1 );
344 hb_demux_ps( buf_ps, list_es );
346 while( ( buf_es = hb_list_item( list_es, 0 ) ) )
348 hb_list_rem( list_es, buf_es );
349 if( buf_es->id == 0xE0 && !hb_list_count( list_raw ) )
351 hb_libmpeg2_decode( mpeg2, buf_es, list_raw );
355 LookForAC3AndDCA( title, buf_es );
357 hb_buffer_close( &buf_es );
359 if( hb_list_count( list_raw ) &&
360 ( i || AllAC3AndDCAOK( title ) ) )
362 /* We got a picture */
367 if( hb_list_count( list_raw ) &&
368 ( i || AllAC3AndDCAOK( title ) ) )
374 if( !hb_list_count( list_raw ) )
376 hb_log( "scan: could not get a decoded picture" );
380 /* Get size and rate infos */
381 title->rate = 27000000;
383 hb_libmpeg2_info( mpeg2, &title->width, &title->height,
384 &title->rate_base, &ar );
386 if( title->rate_base == 1126125 )
388 /* Frame FPS is 23.976 (meaning it's progressive), so
389 start keeping track of how many are reporting at
390 that speed. When enough show up that way, we want
391 to make that the overall title FPS.
395 if( progressive_count < 6 )
397 /* Not enough frames are reporting as progressive,
398 which means we should be conservative and use
399 29.97 as the title's FPS for now.
401 title->rate_base = 900900;
405 /* A majority of the scan frames are progressive. Make that
406 the title's FPS, and announce it once to the log.
408 if( progressive_count == 6 )
410 hb_log("Title's mostly progressive NTSC, setting fps to 23.976");
412 title->rate_base = 1126125;
415 else if( title->rate_base == 900900 && progressive_count >= 6 )
418 * We've already deduced that the frame rate is 23.976, so set it
421 title->rate_base = 1126125;
424 if( i == 2) // Use the third frame's info, so as to skip opening logos
426 // The aspect ratio may have already been set by parsing the VOB/IFO details on a DVD, however
427 // if we're working with program/transport streams that data needs to come from within the stream.
428 if (title->aspect <= 0)
430 title->crop[0] = title->crop[1] = title->height / 2;
431 title->crop[2] = title->crop[3] = title->width / 2;
434 hb_libmpeg2_close( &mpeg2 );
436 while( ( buf_es = hb_list_item( list_es, 0 ) ) )
438 hb_list_rem( list_es, buf_es );
439 hb_buffer_close( &buf_es );
442 buf_raw = hb_list_item( list_raw, 0 );
444 hb_get_tempory_filename( data->h, filename, "%x%d",
445 (intptr_t)title, i );
447 file_preview = fopen( filename, "w" );
450 fwrite( buf_raw->data, title->width * title->height * 3 / 2,
452 fclose( file_preview );
456 hb_log( "scan: fopen failed (%s)", filename );
459 #define Y buf_raw->data
462 /* Detect black borders */
464 for( j = 0; j < title->width; j++ )
466 for( k = 0; k < title->crop[0]; k++ )
467 if( Y[ k * title->width + j ] > DARK )
472 for( k = 0; k < title->crop[1]; k++ )
473 if( Y[ ( title->height - k - 1 ) *
474 title->width + j ] > DARK )
480 for( j = 0; j < title->height; j++ )
482 for( k = 0; k < title->crop[2]; k++ )
483 if( Y[ j * title->width + k ] > DARK )
488 for( k = 0; k < title->crop[3]; k++ )
489 if( Y[ j * title->width +
490 title->width - k - 1 ] > DARK )
498 while( ( buf_raw = hb_list_item( list_raw, 0 ) ) )
500 hb_list_rem( list_raw, buf_raw );
501 hb_buffer_close( &buf_raw );
505 title->crop[0] = EVEN( title->crop[0] );
506 title->crop[1] = EVEN( title->crop[1] );
507 title->crop[2] = EVEN( title->crop[2] );
508 title->crop[3] = EVEN( title->crop[3] );
510 hb_log( "scan: %dx%d, %.3f fps, autocrop = %d/%d/%d/%d",
511 title->width, title->height, (float) title->rate /
512 (float) title->rate_base, title->crop[0], title->crop[1],
513 title->crop[2], title->crop[3] );
522 hb_buffer_close( &buf_ps );
523 while( ( buf_es = hb_list_item( list_es, 0 ) ) )
525 hb_list_rem( list_es, buf_es );
526 hb_buffer_close( &buf_es );
528 hb_list_close( &list_es );
529 while( ( buf_raw = hb_list_item( list_raw, 0 ) ) )
531 hb_list_rem( list_raw, buf_raw );
532 hb_buffer_close( &buf_raw );
534 hb_list_close( &list_raw );
536 hb_dvd_stop( data->dvd );
541 static void LookForAC3AndDCA( hb_title_t * title, hb_buffer_t * b )
550 /* Figure out if this is a AC3 or DCA buffer for a known track */
551 hb_audio_t * audio = NULL;
552 for( i = 0; i < hb_list_count( title->list_audio ); i++ )
554 audio = hb_list_item( title->list_audio, i );
555 /* check if we have an AC3 or DCA which we recognise */
556 if( ( audio->codec == HB_ACODEC_AC3 || audio->codec == HB_ACODEC_DCA ) &&
573 /* Already done for this track */
577 for( i = 0; i < b->size - 7; i++ )
580 if ( audio->codec == HB_ACODEC_AC3 )
584 if( a52_syncinfo( &b->data[i], &flags, &rate, &bitrate ) )
586 hb_log( "scan: AC3, rate=%dHz, bitrate=%d", rate, bitrate );
588 audio->bitrate = bitrate;
589 switch( flags & A52_CHANNEL_MASK )
595 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_MONO;
600 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_STEREO;
602 /* dolby (DPL1 aka Dolby Surround = 4.0 matrix-encoded) input */
604 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_DOLBY;
608 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_3F2R;
612 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_3F1R;
616 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_3F;
619 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_2F1R;
622 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_2F2R;
626 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_STEREO;
629 /* add in our own LFE flag if the source has LFE */
632 audio->input_channel_layout = audio->input_channel_layout | HB_INPUT_CH_LAYOUT_HAS_LFE;
635 /* store the AC3 flags for future reference
636 This enables us to find out if we had a stereo or Dolby source later on */
637 audio->config.a52.ac3flags = flags;
639 /* store the ac3 flags in the public ac3flags property too, so we can access it from the GUI */
640 audio->ac3flags = audio->config.a52.ac3flags;
643 if ( (flags & A52_CHANNEL_MASK) == A52_DOLBY ) {
644 sprintf( audio->lang + strlen( audio->lang ),
645 " (Dolby Surround)" );
647 sprintf( audio->lang + strlen( audio->lang ),
649 HB_INPUT_CH_LAYOUT_GET_DISCRETE_FRONT_COUNT(audio->input_channel_layout) +
650 HB_INPUT_CH_LAYOUT_GET_DISCRETE_REAR_COUNT(audio->input_channel_layout),
651 HB_INPUT_CH_LAYOUT_GET_DISCRETE_LFE_COUNT(audio->input_channel_layout));
659 else if ( audio->codec == HB_ACODEC_DCA )
662 hb_log( "scan: checking for DCA syncinfo" );
665 state = dca_init( 0 );
666 if( dca_syncinfo( state, &b->data[i], &flags, &rate, &bitrate, &frame_length ) )
668 hb_log( "scan: DCA, rate=%dHz, bitrate=%d", rate, bitrate );
670 audio->bitrate = bitrate;
671 switch( flags & DCA_CHANNEL_MASK )
675 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_MONO;
680 case DCA_STEREO_SUMDIFF:
681 case DCA_STEREO_TOTAL:
682 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_STEREO;
686 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_3F2R;
690 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_3F1R;
694 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_3F;
697 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_2F1R;
700 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_2F2R;
703 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_4F2R;
707 audio->input_channel_layout = HB_INPUT_CH_LAYOUT_STEREO;
710 /* add in our own LFE flag if the source has LFE */
713 audio->input_channel_layout = audio->input_channel_layout | HB_INPUT_CH_LAYOUT_HAS_LFE;
716 /* store the DCA flags for future reference
717 This enables us to find out if we had a stereo or Dolby source later on */
718 audio->config.dca.dcaflags = flags;
720 /* store the dca flags in the public dcaflags property too, so we can access it from the GUI */
721 audio->dcaflags = audio->config.dca.dcaflags;
724 if ( (flags & DCA_CHANNEL_MASK) == DCA_DOLBY ) {
725 sprintf( audio->lang + strlen( audio->lang ),
726 " (Dolby Surround)" );
728 sprintf( audio->lang + strlen( audio->lang ),
730 HB_INPUT_CH_LAYOUT_GET_DISCRETE_FRONT_COUNT(audio->input_channel_layout) +
731 HB_INPUT_CH_LAYOUT_GET_DISCRETE_REAR_COUNT(audio->input_channel_layout),
732 HB_INPUT_CH_LAYOUT_GET_DISCRETE_LFE_COUNT(audio->input_channel_layout));
742 static int AllAC3AndDCAOK( hb_title_t * title )
747 for( i = 0; i < hb_list_count( title->list_audio ); i++ )
749 audio = hb_list_item( title->list_audio, i );
750 if( ( audio->codec == HB_ACODEC_AC3 || audio->codec == HB_ACODEC_DCA ) &&