OSDN Git Service

60b0bcc332406a363634f8611938406e36667119
[handbrake-jp/handbrake-jp-git.git] / libhb / hb.c
1 #include "hb.h"
2 #include "hbffmpeg.h"
3 #include <stdio.h>
4 #include <unistd.h>
5 #include <fcntl.h>
6
7 #if defined( SYS_MINGW )
8 #include <io.h>
9 #if defined( PTW32_STATIC_LIB )
10 #include <pthread.h>
11 #endif
12 #endif
13
14 struct hb_handle_s
15 {
16     int            id;
17     
18     /* The "Check for update" thread */
19     int            build;
20     char           version[32];
21     hb_thread_t  * update_thread;
22
23     /* This thread's only purpose is to check other threads'
24        states */
25     volatile int   die;
26     hb_thread_t  * main_thread;
27     int            pid;
28
29     /* DVD/file scan thread */
30     hb_list_t    * list_title;
31     hb_thread_t  * scan_thread;
32
33     /* The thread which processes the jobs. Others threads are launched
34        from this one (see work.c) */
35     hb_list_t    * jobs;
36     hb_job_t     * current_job;
37     int            job_count;
38     int            job_count_permanent;
39     volatile int   work_die;
40     int            work_error;
41     hb_thread_t  * work_thread;
42
43     int            cpu_count;
44
45     hb_lock_t    * state_lock;
46     hb_state_t     state;
47
48     int            paused;
49     hb_lock_t    * pause_lock;
50     /* For MacGui active queue
51        increments each time the scan thread completes*/
52     int            scanCount;
53     volatile int   scan_die;
54     
55     /* Stash of persistent data between jobs, for stuff
56        like correcting frame count and framerate estimates
57        on multi-pass encodes where frames get dropped.     */
58     hb_interjob_t * interjob;
59
60 };
61
62 hb_lock_t *hb_avcodec_lock;
63 hb_work_object_t * hb_objects = NULL;
64 int hb_instance_counter = 0;
65 int hb_process_initialized = 0;
66
67 static void thread_func( void * );
68 hb_title_t * hb_get_title_by_index( hb_handle_t *, int );
69
70 void hb_avcodec_init()
71 {
72     hb_avcodec_lock  = hb_lock_init();
73     av_register_all();
74 }
75
76 int hb_avcodec_open(AVCodecContext *avctx, AVCodec *codec)
77 {
78     int ret;
79     hb_lock( hb_avcodec_lock );
80     ret = avcodec_open(avctx, codec);
81     hb_unlock( hb_avcodec_lock );
82     return ret;
83 }
84
85 int hb_av_find_stream_info(AVFormatContext *ic)
86 {
87     int ret;
88     hb_lock( hb_avcodec_lock );
89     ret = av_find_stream_info( ic );
90     hb_unlock( hb_avcodec_lock );
91     return ret;
92 }
93
94 struct SwsContext*
95 hb_sws_get_context(int srcW, int srcH, enum PixelFormat srcFormat,
96                    int dstW, int dstH, enum PixelFormat dstFormat,
97                    int flags)
98 {
99     struct SwsContext * ctx;
100
101 #if 0
102     // sws_getContext is being depricated.  But it appears that
103     // the new method isn't quite wrung out yet.  So when it is
104     // this code should be fixed up and enabled.
105     ctx = sws_alloc_context();
106     if ( ctx )
107     {
108         av_set_int(ctx, "srcw", srcW);
109         av_set_int(ctx, "srch", srcH);
110         av_set_int(ctx, "src_format", srcFormat);
111         av_set_int(ctx, "dstw", dstW);
112         av_set_int(ctx, "dsth", dstH);
113         av_set_int(ctx, "dst_format", dstFormat);
114         av_set_int(ctx, "sws_flags", flags);
115
116         if (sws_init_context(ctx, NULL, NULL) < 0) {
117             fprintf(stderr, "Cannot initialize resampling context\n");
118             sws_freeContext(ctx);
119             ctx = NULL;
120         } 
121     }
122 #else
123     ctx = sws_getContext(srcW, srcH, srcFormat, dstW, dstH, dstFormat, 
124                          flags, NULL, NULL, NULL);
125 #endif
126     return ctx;
127 }
128
129 int hb_avcodec_close(AVCodecContext *avctx)
130 {
131     int ret;
132     hb_lock( hb_avcodec_lock );
133     ret = avcodec_close(avctx);
134     hb_unlock( hb_avcodec_lock );
135     return ret;
136 }
137
138 int hb_ff_layout_xlat(int64_t ff_channel_layout, int channels)
139 {
140     int hb_layout;
141
142     switch (ff_channel_layout)
143     {
144         case CH_LAYOUT_MONO:
145             hb_layout = HB_INPUT_CH_LAYOUT_MONO;
146             break;
147         case CH_LAYOUT_STEREO:
148             hb_layout = HB_INPUT_CH_LAYOUT_STEREO;
149             break;
150         case CH_LAYOUT_SURROUND:
151             hb_layout = HB_INPUT_CH_LAYOUT_3F;
152             break;
153         case CH_LAYOUT_4POINT0:
154             hb_layout = HB_INPUT_CH_LAYOUT_3F1R;
155             break;
156         case CH_LAYOUT_2_2:
157             hb_layout = HB_INPUT_CH_LAYOUT_2F2R;
158             break;
159         case CH_LAYOUT_QUAD:
160             hb_layout = HB_INPUT_CH_LAYOUT_2F2R;
161             break;
162         case CH_LAYOUT_5POINT0:
163             hb_layout = HB_INPUT_CH_LAYOUT_3F2R;
164             break;
165         case CH_LAYOUT_5POINT1:
166             hb_layout = HB_INPUT_CH_LAYOUT_3F2R|HB_INPUT_CH_LAYOUT_HAS_LFE;
167             break;
168         case CH_LAYOUT_5POINT0_BACK:
169             hb_layout = HB_INPUT_CH_LAYOUT_3F2R;
170             break;
171         case CH_LAYOUT_5POINT1_BACK:
172             hb_layout = HB_INPUT_CH_LAYOUT_3F2R|HB_INPUT_CH_LAYOUT_HAS_LFE;
173             break;
174         case CH_LAYOUT_7POINT0:
175             hb_layout = HB_INPUT_CH_LAYOUT_3F4R;
176             break;
177         case CH_LAYOUT_7POINT1:
178             hb_layout = HB_INPUT_CH_LAYOUT_3F4R|HB_INPUT_CH_LAYOUT_HAS_LFE;
179             break;
180         case CH_LAYOUT_STEREO_DOWNMIX:
181             hb_layout = HB_INPUT_CH_LAYOUT_STEREO;
182             break;
183         default:
184             hb_layout = HB_INPUT_CH_LAYOUT_STEREO;
185             break;
186     }
187     // Now make sure the chosen layout agrees with the number of channels
188     // ffmpeg tells us there are.  It seems ffmpeg is sometimes confused
189     // about this. So we will make a best guess based on the number
190     // of channels.
191     int chans = HB_INPUT_CH_LAYOUT_GET_DISCRETE_COUNT( hb_layout );
192     if ( chans == channels )
193     {
194         return hb_layout;
195     }
196     hb_log( "Channels reported by ffmpeg (%d) != computed layout channels (%d).", channels, chans );
197     switch (channels)
198     {
199         case 1:
200             hb_layout = HB_INPUT_CH_LAYOUT_MONO;
201             break;
202         case 2:
203             hb_layout = HB_INPUT_CH_LAYOUT_STEREO;
204             break;
205         case 3:
206             hb_layout = HB_INPUT_CH_LAYOUT_3F;
207             break;
208         case 4:
209             hb_layout = HB_INPUT_CH_LAYOUT_3F1R;
210             break;
211         case 5:
212             hb_layout = HB_INPUT_CH_LAYOUT_3F2R;
213             break;
214         case 6:
215             hb_layout = HB_INPUT_CH_LAYOUT_3F2R|HB_INPUT_CH_LAYOUT_HAS_LFE;
216             break;
217         case 7:
218             hb_layout = HB_INPUT_CH_LAYOUT_3F4R;
219             break;
220         case 8:
221             hb_layout = HB_INPUT_CH_LAYOUT_3F4R|HB_INPUT_CH_LAYOUT_HAS_LFE;
222             break;
223         default:
224             hb_log("Unsupported number of audio channels (%d).\n", channels);
225             hb_layout = 0;
226             break;
227     }
228     return hb_layout;
229 }
230
231 /**
232  * Registers work objects, by adding the work object to a liked list.
233  * @param w Handle to hb_work_object_t to register.
234  */
235 void hb_register( hb_work_object_t * w )
236 {
237     w->next    = hb_objects;
238     hb_objects = w;
239 }
240
241 /**
242  * Ensures that the process has been initialized.
243  */
244 static void process_init()
245 {
246     if (!hb_process_initialized)
247     {
248 #if defined( SYS_MINGW ) && defined( PTW32_STATIC_LIB )
249         pthread_win32_process_attach_np();
250 #endif
251
252 #if defined( _WIN32 ) || defined( __MINGW32__ )
253         setvbuf( stdout, NULL, _IONBF, 0 );
254         setvbuf( stderr, NULL, _IONBF, 0 );
255 #endif
256         hb_process_initialized = 1;
257     }
258     
259 }
260
261 void (*hb_log_callback)(const char* message);
262 static void redirect_thread_func(void *);
263
264 #if defined( SYS_MINGW )
265 #define pipe(phandles)  _pipe (phandles, 4096, _O_BINARY)
266 #endif
267
268 /**
269  * Registers the given function as a logger. All logs will be passed to it.
270  * @param log_cb The function to register as a logger.
271  */
272 void hb_register_logger( void (*log_cb)(const char* message) )
273 {
274     process_init();
275
276     hb_log_callback = log_cb;
277     hb_thread_init("ioredirect", redirect_thread_func, NULL, HB_NORMAL_PRIORITY);
278 }
279
280 /**
281  * libhb initialization routine.
282  * @param verbose HB_DEBUG_NONE or HB_DEBUG_ALL.
283  * @param update_check signals libhb to check for updated version from HandBrake website.
284  * @return Handle to hb_handle_t for use on all subsequent calls to libhb.
285  */
286 hb_handle_t * hb_init( int verbose, int update_check )
287 {
288     process_init();
289
290     hb_handle_t * h = calloc( sizeof( hb_handle_t ), 1 );
291     uint64_t      date;
292
293     /* See hb_deep_log() and hb_log() in common.c */
294     global_verbosity_level = verbose;
295     if( verbose )
296         putenv( "HB_DEBUG=1" );
297     
298     h->id = hb_instance_counter++;
299     
300     /* Check for an update on the website if asked to */
301     h->build = -1;
302
303     if( update_check )
304     {
305         hb_log( "hb_init: checking for updates" );
306         date             = hb_get_date();
307         h->update_thread = hb_update_init( &h->build, h->version );
308
309         for( ;; )
310         {
311             if( hb_thread_has_exited( h->update_thread ) )
312             {
313                 /* Immediate success or failure */
314                 hb_thread_close( &h->update_thread );
315                 break;
316             }
317             if( hb_get_date() > date + 1000 )
318             {
319                 /* Still nothing after one second. Connection problem,
320                    let the thread die */
321                 hb_log( "hb_init: connection problem, not waiting for "
322                         "update_thread" );
323                 break;
324             }
325             hb_snooze( 500 );
326         }
327     }
328
329     /*
330      * Initialise buffer pool
331      */
332     hb_buffer_pool_init();
333
334     /* CPU count detection */
335     hb_log( "hb_init: checking cpu count" );
336     h->cpu_count = hb_get_cpu_count();
337
338     h->list_title = hb_list_init();
339     h->jobs       = hb_list_init();
340
341     h->state_lock  = hb_lock_init();
342     h->state.state = HB_STATE_IDLE;
343
344     h->pause_lock = hb_lock_init();
345
346     h->interjob = calloc( sizeof( hb_interjob_t ), 1 );
347
348     /* libavcodec */
349     hb_avcodec_init();
350
351     /* Start library thread */
352     hb_log( "hb_init: starting libhb thread" );
353     h->die         = 0;
354     h->main_thread = hb_thread_init( "libhb", thread_func, h,
355                                      HB_NORMAL_PRIORITY );
356     hb_register( &hb_sync_video );
357     hb_register( &hb_sync_audio );
358         hb_register( &hb_decmpeg2 );
359         hb_register( &hb_decvobsub );
360     hb_register( &hb_encvobsub );
361     hb_register( &hb_deccc608 );
362     hb_register( &hb_decsrtsub );
363     hb_register( &hb_decutf8sub );
364     hb_register( &hb_dectx3gsub );
365     hb_register( &hb_decssasub );
366         hb_register( &hb_render );
367         hb_register( &hb_encavcodec );
368         hb_register( &hb_encx264 );
369     hb_register( &hb_enctheora );
370         hb_register( &hb_deca52 );
371         hb_register( &hb_decdca );
372         hb_register( &hb_decavcodec );
373         hb_register( &hb_decavcodecv );
374         hb_register( &hb_decavcodecvi );
375         hb_register( &hb_decavcodecai );
376         hb_register( &hb_declpcm );
377         hb_register( &hb_encfaac );
378         hb_register( &hb_enclame );
379         hb_register( &hb_encvorbis );
380         hb_register( &hb_muxer );
381 #ifdef __APPLE__
382         hb_register( &hb_encca_aac );
383 #endif
384         hb_register( &hb_encac3 );
385     
386     return h;
387 }
388
389 /**
390  * libhb initialization routine.
391  * This version is to use when calling the dylib, the macro hb_init isn't available from a dylib call!
392  * @param verbose HB_DEBUG_NONE or HB_DEBUG_ALL.
393  * @param update_check signals libhb to check for updated version from HandBrake website.
394  * @return Handle to hb_handle_t for use on all subsequent calls to libhb.
395  */
396 hb_handle_t * hb_init_dl( int verbose, int update_check )
397 {
398     hb_handle_t * h = calloc( sizeof( hb_handle_t ), 1 );
399     uint64_t      date;
400
401     /* See hb_log() in common.c */
402     if( verbose > HB_DEBUG_NONE )
403     {
404         putenv( "HB_DEBUG=1" );
405     }
406
407     h->id = hb_instance_counter++;
408
409     /* Check for an update on the website if asked to */
410     h->build = -1;
411
412     if( update_check )
413     {
414         hb_log( "hb_init: checking for updates" );
415         date             = hb_get_date();
416         h->update_thread = hb_update_init( &h->build, h->version );
417
418         for( ;; )
419         {
420             if( hb_thread_has_exited( h->update_thread ) )
421             {
422                 /* Immediate success or failure */
423                 hb_thread_close( &h->update_thread );
424                 break;
425             }
426             if( hb_get_date() > date + 1000 )
427             {
428                 /* Still nothing after one second. Connection problem,
429                    let the thread die */
430                 hb_log( "hb_init: connection problem, not waiting for "
431                         "update_thread" );
432                 break;
433             }
434             hb_snooze( 500 );
435         }
436     }
437
438     /* CPU count detection */
439     hb_log( "hb_init: checking cpu count" );
440     h->cpu_count = hb_get_cpu_count();
441
442     h->list_title = hb_list_init();
443     h->jobs       = hb_list_init();
444     h->current_job = NULL;
445
446     h->state_lock  = hb_lock_init();
447     h->state.state = HB_STATE_IDLE;
448
449     h->pause_lock = hb_lock_init();
450
451     /* libavcodec */
452     avcodec_init();
453     avcodec_register_all();
454
455     /* Start library thread */
456     hb_log( "hb_init: starting libhb thread" );
457     h->die         = 0;
458     h->main_thread = hb_thread_init( "libhb", thread_func, h,
459                                      HB_NORMAL_PRIORITY );
460
461     hb_register( &hb_sync_video );
462     hb_register( &hb_sync_audio );
463         hb_register( &hb_decmpeg2 );
464         hb_register( &hb_decvobsub );
465     hb_register( &hb_encvobsub );
466     hb_register( &hb_deccc608 );
467     hb_register( &hb_decsrtsub );
468     hb_register( &hb_decutf8sub );
469     hb_register( &hb_dectx3gsub );
470     hb_register( &hb_decssasub );
471         hb_register( &hb_render );
472         hb_register( &hb_encavcodec );
473         hb_register( &hb_encx264 );
474     hb_register( &hb_enctheora );
475         hb_register( &hb_deca52 );
476         hb_register( &hb_decdca );
477         hb_register( &hb_decavcodec );
478         hb_register( &hb_decavcodecv );
479         hb_register( &hb_decavcodecvi );
480         hb_register( &hb_decavcodecai );
481         hb_register( &hb_declpcm );
482         hb_register( &hb_encfaac );
483         hb_register( &hb_enclame );
484         hb_register( &hb_encvorbis );
485         hb_register( &hb_muxer );
486 #ifdef __APPLE__
487         hb_register( &hb_encca_aac );
488 #endif
489         hb_register( &hb_encac3 );
490
491         return h;
492 }
493
494
495 /**
496  * Returns current version of libhb.
497  * @param h Handle to hb_handle_t.
498  * @return character array of version number.
499  */
500 char * hb_get_version( hb_handle_t * h )
501 {
502     return HB_PROJECT_VERSION;
503 }
504
505 /**
506  * Returns current build of libhb.
507  * @param h Handle to hb_handle_t.
508  * @return character array of build number.
509  */
510 int hb_get_build( hb_handle_t * h )
511 {
512     return HB_PROJECT_BUILD;
513 }
514
515 /**
516  * Checks for needed update.
517  * @param h Handle to hb_handle_t.
518  * @param version Pointer to handle where version will be copied.
519  * @return update indicator.
520  */
521 int hb_check_update( hb_handle_t * h, char ** version )
522 {
523     *version = ( h->build < 0 ) ? NULL : h->version;
524     return h->build;
525 }
526
527 /**
528  * Deletes current previews associated with titles
529  * @param h Handle to hb_handle_t
530  */
531 void hb_remove_previews( hb_handle_t * h )
532 {
533     char            filename[1024];
534     char            dirname[1024];
535     hb_title_t    * title;
536     int             i, count, len;
537     DIR           * dir;
538     struct dirent * entry;
539
540     memset( dirname, 0, 1024 );
541     hb_get_temporary_directory( dirname );
542     dir = opendir( dirname );
543     if (dir == NULL) return;
544
545     count = hb_list_count( h->list_title );
546     while( ( entry = readdir( dir ) ) )
547     {
548         if( entry->d_name[0] == '.' )
549         {
550             continue;
551         }
552         for( i = 0; i < count; i++ )
553         {
554             title = hb_list_item( h->list_title, i );
555             len = snprintf( filename, 1024, "%d_%d", h->id, title->index );
556             if (strncmp(entry->d_name, filename, len) == 0)
557             {
558                 snprintf( filename, 1024, "%s/%s", dirname, entry->d_name );
559                 unlink( filename );
560                 break;
561             }
562         }
563     }
564     closedir( dir );
565 }
566
567 /**
568  * Initializes a scan of the by calling hb_scan_init
569  * @param h Handle to hb_handle_t
570  * @param path location of VIDEO_TS folder.
571  * @param title_index Desired title to scan.  0 for all titles.
572  * @param preview_count Number of preview images to generate.
573  * @param store_previews Whether or not to write previews to disk.
574  */
575 void hb_scan( hb_handle_t * h, const char * path, int title_index,
576               int preview_count, int store_previews, uint64_t min_duration )
577 {
578     hb_title_t * title;
579
580     h->scan_die = 0;
581
582     /* Clean up from previous scan */
583     hb_remove_previews( h );
584     while( ( title = hb_list_item( h->list_title, 0 ) ) )
585     {
586         hb_list_rem( h->list_title, title );
587         hb_title_close( &title );
588     }
589
590     hb_log( "hb_scan: path=%s, title_index=%d", path, title_index );
591     h->scan_thread = hb_scan_init( h, &h->scan_die, path, title_index, 
592                                    h->list_title, preview_count, 
593                                    store_previews, min_duration );
594 }
595
596 /**
597  * Returns the list of titles found.
598  * @param h Handle to hb_handle_t
599  * @return Handle to hb_list_t of the title list.
600  */
601 hb_list_t * hb_get_titles( hb_handle_t * h )
602 {
603     return h->list_title;
604 }
605
606 /**
607  * Create preview image of desired title a index of picture.
608  * @param h Handle to hb_handle_t.
609  * @param title_index Index of the title to get the preview for (1-based).
610  * @param picture Index in title.
611  * @param buffer Handle to buffer were image will be drawn.
612  */
613 void hb_get_preview_by_index( hb_handle_t * h, int title_index, int picture, uint8_t * buffer )
614 {
615     hb_title_t * title;
616
617     title = hb_get_title_by_index( h, title_index );
618     if ( title != NULL )
619     {
620         hb_get_preview( h, title, picture, buffer );
621     } 
622 }
623
624 /**
625  * Create preview image of desired title a index of picture.
626  * @param h Handle to hb_handle_t.
627  * @param title Handle to hb_title_t of desired title.
628  * @param picture Index in title.
629  * @param buffer Handle to buffer were image will be drawn.
630  */
631 void hb_get_preview( hb_handle_t * h, hb_title_t * title, int picture,
632                      uint8_t * buffer )
633 {
634     hb_job_t           * job = title->job;
635     char                 filename[1024];
636     FILE               * file;
637     uint8_t            * buf1, * buf2, * buf3, * buf4, * pen;
638     uint32_t             swsflags;
639     AVPicture            pic_in, pic_preview, pic_deint, pic_crop, pic_scale;
640     struct SwsContext  * context;
641     int                  i;
642     int                  deint_width = ((title->width + 7) >> 3) << 3;
643     int                  rgb_width = ((job->width + 7) >> 3) << 3;
644     int                  preview_size;
645
646     swsflags = SWS_LANCZOS | SWS_ACCURATE_RND;
647
648     buf1 = av_malloc( avpicture_get_size( PIX_FMT_YUV420P, title->width, title->height ) );
649     buf2 = av_malloc( avpicture_get_size( PIX_FMT_YUV420P, deint_width, title->height ) );
650     buf3 = av_malloc( avpicture_get_size( PIX_FMT_YUV420P, rgb_width, job->height ) );
651     buf4 = av_malloc( avpicture_get_size( PIX_FMT_RGB32, rgb_width, job->height ) );
652     avpicture_fill( &pic_in, buf1, PIX_FMT_YUV420P,
653                     title->width, title->height );
654     avpicture_fill( &pic_deint, buf2, PIX_FMT_YUV420P,
655                     deint_width, title->height );
656     avpicture_fill( &pic_scale, buf3, PIX_FMT_YUV420P,
657                     rgb_width, job->height );
658     avpicture_fill( &pic_preview, buf4, PIX_FMT_RGB32,
659                     rgb_width, job->height );
660
661     // Allocate the AVPicture frames and fill in
662
663     memset( filename, 0, 1024 );
664
665     hb_get_tempory_filename( h, filename, "%d_%d_%d",
666                              h->id, title->index, picture );
667
668     file = fopen( filename, "rb" );
669     if( !file )
670     {
671         hb_log( "hb_get_preview: fopen failed" );
672         return;
673     }
674
675     fread( buf1, avpicture_get_size( PIX_FMT_YUV420P, title->width, title->height), 1, file );
676     fclose( file );
677
678     if( job->deinterlace )
679     {
680         // Deinterlace and crop
681         avpicture_deinterlace( &pic_deint, &pic_in, PIX_FMT_YUV420P, title->width, title->height );
682         av_picture_crop( &pic_crop, &pic_deint, PIX_FMT_YUV420P, job->crop[0], job->crop[2] );
683     }
684     else
685     {
686         // Crop
687         av_picture_crop( &pic_crop, &pic_in, PIX_FMT_YUV420P, job->crop[0], job->crop[2] );
688     }
689
690     // Get scaling context
691     context = hb_sws_get_context(title->width  - (job->crop[2] + job->crop[3]),
692                              title->height - (job->crop[0] + job->crop[1]),
693                              PIX_FMT_YUV420P,
694                              job->width, job->height, PIX_FMT_YUV420P,
695                              swsflags);
696
697     // Scale
698     sws_scale(context,
699               pic_crop.data, pic_crop.linesize,
700               0, title->height - (job->crop[0] + job->crop[1]),
701               pic_scale.data, pic_scale.linesize);
702
703     // Free context
704     sws_freeContext( context );
705
706     // Get preview context
707     context = hb_sws_get_context(rgb_width, job->height, PIX_FMT_YUV420P,
708                               rgb_width, job->height, PIX_FMT_RGB32,
709                               swsflags);
710
711     // Create preview
712     sws_scale(context,
713               pic_scale.data, pic_scale.linesize,
714               0, job->height,
715               pic_preview.data, pic_preview.linesize);
716
717     // Free context
718     sws_freeContext( context );
719
720     preview_size = pic_preview.linesize[0];
721     pen = buffer;
722     for( i = 0; i < job->height; i++ )
723     {
724         memcpy( pen, buf4 + preview_size * i, 4 * job->width );
725         pen += 4 * job->width;
726     }
727
728     // Clean up
729     avpicture_free( &pic_preview );
730     avpicture_free( &pic_scale );
731     avpicture_free( &pic_deint );
732     avpicture_free( &pic_in );
733 }
734
735  /**
736  * Analyzes a frame to detect interlacing artifacts
737  * and returns true if interlacing (combing) is found.
738  *
739  * Code taken from Thomas Oestreich's 32detect filter
740  * in the Transcode project, with minor formatting changes.
741  *
742  * @param buf         An hb_buffer structure holding valid frame data
743  * @param width       The frame's width in pixels
744  * @param height      The frame's height in pixels
745  * @param color_equal Sensitivity for detecting similar colors
746  * @param color_diff  Sensitivity for detecting different colors
747  * @param threshold   Sensitivity for flagging planes as combed
748  * @param prog_equal  Sensitivity for detecting similar colors on progressive frames
749  * @param prog_diff   Sensitivity for detecting different colors on progressive frames
750  * @param prog_threshold Sensitivity for flagging progressive frames as combed
751  */
752 int hb_detect_comb( hb_buffer_t * buf, int width, int height, int color_equal, int color_diff, int threshold, int prog_equal, int prog_diff, int prog_threshold )
753 {
754     int j, k, n, off, cc_1, cc_2, cc[3];
755         // int flag[3] ; // debugging flag
756     uint16_t s1, s2, s3, s4;
757     cc_1 = 0; cc_2 = 0;
758
759     int offset = 0;
760     
761     if ( buf->flags & 16 )
762     {
763         /* Frame is progressive, be more discerning. */
764         color_diff = prog_diff;
765         color_equal = prog_equal;
766         threshold = prog_threshold;
767     }
768
769     /* One pas for Y, one pass for Cb, one pass for Cr */    
770     for( k = 0; k < 3; k++ )
771     {
772         if( k == 1 )
773         {
774             /* Y has already been checked, now offset by Y's dimensions
775                and divide all the other values by 2, since Cr and Cb
776                are half-size compared to Y.                               */
777             offset = width * height;
778             width >>= 1;
779             height >>= 1;
780         }
781         else if ( k == 2 )
782         {
783             /* Y and Cb are done, so the offset needs to be bumped
784                so it's width*height + (width / 2) * (height / 2)  */
785             offset *= 5/4;
786         }
787
788         for( j = 0; j < width; ++j )
789         {
790             off = 0;
791
792             for( n = 0; n < ( height - 4 ); n = n + 2 )
793             {
794                 /* Look at groups of 4 sequential horizontal lines */
795                 s1 = ( ( buf->data + offset )[ off + j             ] & 0xff );
796                 s2 = ( ( buf->data + offset )[ off + j + width     ] & 0xff );
797                 s3 = ( ( buf->data + offset )[ off + j + 2 * width ] & 0xff );
798                 s4 = ( ( buf->data + offset )[ off + j + 3 * width ] & 0xff );
799
800                 /* Note if the 1st and 2nd lines are more different in
801                    color than the 1st and 3rd lines are similar in color.*/
802                 if ( ( abs( s1 - s3 ) < color_equal ) &&
803                      ( abs( s1 - s2 ) > color_diff ) )
804                         ++cc_1;
805
806                 /* Note if the 2nd and 3rd lines are more different in
807                    color than the 2nd and 4th lines are similar in color.*/
808                 if ( ( abs( s2 - s4 ) < color_equal ) &&
809                      ( abs( s2 - s3 ) > color_diff) )
810                         ++cc_2;
811
812                 /* Now move down 2 horizontal lines before starting over.*/
813                 off += 2 * width;
814             }
815         }
816
817         // compare results
818         /*  The final cc score for a plane is the percentage of combed pixels it contains.
819             Because sensitivity goes down to hundreths of a percent, multiply by 1000
820             so it will be easy to compare against the threhold value which is an integer. */
821         cc[k] = (int)( ( cc_1 + cc_2 ) * 1000.0 / ( width * height ) );
822     }
823
824
825     /* HandBrake is all yuv420, so weight the average percentage of all 3 planes accordingly.*/
826     int average_cc = ( 2 * cc[0] + ( cc[1] / 2 ) + ( cc[2] / 2 ) ) / 3;
827     
828     /* Now see if that average percentage of combed pixels surpasses the threshold percentage given by the user.*/
829     if( average_cc > threshold )
830     {
831 #if 0
832             hb_log("Average %i combed (Threshold %i) %i/%i/%i | PTS: %"PRId64" (%fs) %s", average_cc, threshold, cc[0], cc[1], cc[2], buf->start, (float)buf->start / 90000, (buf->flags & 16) ? "Film" : "Video" );
833 #endif
834         return 1;
835     }
836
837 #if 0
838     hb_log("SKIPPED Average %i combed (Threshold %i) %i/%i/%i | PTS: %"PRId64" (%fs) %s", average_cc, threshold, cc[0], cc[1], cc[2], buf->start, (float)buf->start / 90000, (buf->flags & 16) ? "Film" : "Video" );
839 #endif
840
841     /* Reaching this point means no combing detected. */
842     return 0;
843
844 }
845
846 /**
847  * Calculates job width and height for anamorphic content,
848  *
849  * @param h Instance handle
850  * @param title_index Index of the title/job to inspect (1-based).
851  * @param output_width Pointer to returned storage width
852  * @param output_height Pointer to returned storage height
853  * @param output_par_width Pointer to returned pixel width
854  * @param output_par_height Pointer to returned pixel height
855  */
856 void hb_set_anamorphic_size_by_index( hb_handle_t * h, int title_index,
857         int *output_width, int *output_height,
858         int *output_par_width, int *output_par_height )
859 {
860     hb_title_t * title;
861     title = hb_get_title_by_index( h, title_index );
862     
863     hb_set_anamorphic_size( title->job, output_width, output_height, output_par_width, output_par_height );
864 }
865
866 /**
867  * Calculates job width and height for anamorphic content,
868  *
869  * @param job Handle to hb_job_t
870  * @param output_width Pointer to returned storage width
871  * @param output_height Pointer to returned storage height
872  * @param output_par_width Pointer to returned pixel width
873  * @param output_par_height Pointer to returned pixel height
874  */
875 void hb_set_anamorphic_size( hb_job_t * job,
876         int *output_width, int *output_height,
877         int *output_par_width, int *output_par_height )
878 {
879     /* Set up some variables to make the math easier to follow. */
880     hb_title_t * title = job->title;
881     int cropped_width = title->width - job->crop[2] - job->crop[3] ;
882     int cropped_height = title->height - job->crop[0] - job->crop[1] ;
883     double storage_aspect = (double)cropped_width / (double)cropped_height;
884     int mod = job->modulus ? job->modulus : 16;
885     double aspect = title->aspect;
886     
887     int pixel_aspect_width  = job->anamorphic.par_width;
888     int pixel_aspect_height = job->anamorphic.par_height;
889
890     /* If a source was really NTSC or PAL and the user specified ITU PAR
891        values, replace the standard PAR values with the ITU broadcast ones. */
892     if( title->width == 720 && job->anamorphic.itu_par )
893     {
894         // convert aspect to a scaled integer so we can test for 16:9 & 4:3
895         // aspect ratios ignoring insignificant differences in the LSBs of
896         // the floating point representation.
897         int iaspect = aspect * 9.;
898
899         /* Handle ITU PARs */
900         if (title->height == 480)
901         {
902             /* It's NTSC */
903             if (iaspect == 16)
904             {
905                 /* It's widescreen */
906                 pixel_aspect_width = 40;
907                 pixel_aspect_height = 33;
908             }
909             else if (iaspect == 12)
910             {
911                 /* It's 4:3 */
912                 pixel_aspect_width = 10;
913                 pixel_aspect_height = 11;
914             }
915         }
916         else if (title->height == 576)
917         {
918             /* It's PAL */
919             if(iaspect == 16)
920             {
921                 /* It's widescreen */
922                 pixel_aspect_width = 16;
923                 pixel_aspect_height = 11;
924             }
925             else if (iaspect == 12)
926             {
927                 /* It's 4:3 */
928                 pixel_aspect_width = 12;
929                 pixel_aspect_height = 11;
930             }
931         }
932     }
933
934     /* Figure out what width the source would display at. */
935     int source_display_width = cropped_width * (double)pixel_aspect_width /
936                                (double)pixel_aspect_height ;
937
938     /*
939        3 different ways of deciding output dimensions:
940         - 1: Strict anamorphic, preserve source dimensions
941         - 2: Loose anamorphic, round to mod16 and preserve storage aspect ratio
942         - 3: Power user anamorphic, specify everything
943     */
944     int width, height;
945     int maxWidth, maxHeight;
946
947     maxWidth = MULTIPLE_MOD_DOWN( job->maxWidth, mod );
948     maxHeight = MULTIPLE_MOD_DOWN( job->maxHeight, mod );
949
950     switch( job->anamorphic.mode )
951     {
952         case 1:
953             /* Strict anamorphic */
954             *output_width  = MULTIPLE_MOD( cropped_width, 2 );
955             *output_height = MULTIPLE_MOD( cropped_height, 2 );
956             // adjust the source PAR for new width/height
957             // new PAR = source PAR * ( old width / new_width ) * ( new_height / old_height )
958             pixel_aspect_width = title->pixel_aspect_width * cropped_width * (*output_height);            
959             pixel_aspect_height = title->pixel_aspect_height * (*output_width) * cropped_height;
960         break;
961
962         case 2:
963             /* "Loose" anamorphic.
964                 - Uses mod16-compliant dimensions,
965                 - Allows users to set the width
966             */
967             width = job->width;
968             // height: Gets set later, ignore user job->height value
969
970             /* Gotta handle bounding dimensions.
971                If the width is too big, just reset it with no rescaling.
972                Instead of using the aspect-scaled job height,
973                we need to see if the job width divided by the storage aspect
974                is bigger than the max. If so, set it to the max (this is sloppy).
975                If not, set job height to job width divided by storage aspect.
976             */
977
978             /* Time to get picture width that divide cleanly.*/
979             width  = MULTIPLE_MOD( width, mod);
980
981             if ( maxWidth && (maxWidth < job->width) )
982                 width = maxWidth;
983
984             /* Verify these new dimensions don't violate max height and width settings */
985             height = ((double)width / storage_aspect) + 0.5;
986
987             /* Time to get picture height that divide cleanly.*/
988             height = MULTIPLE_MOD( height, mod);
989             
990             if ( maxHeight && (maxHeight < height) )
991             {
992                 height = maxHeight;
993                 width = ((double)height * storage_aspect) + 0.5;
994                 width  = MULTIPLE_MOD( width, mod);
995             }
996
997             /* The film AR is the source's display width / cropped source height.
998                The output display width is the output height * film AR.
999                The output PAR is the output display width / output storage width. */
1000             pixel_aspect_width = height * cropped_width * pixel_aspect_width;
1001             pixel_aspect_height = width * cropped_height * pixel_aspect_height;
1002
1003             /* Pass the results back to the caller */
1004             *output_width = width;
1005             *output_height = height;
1006         break;
1007             
1008         case 3:
1009             /* Anamorphic 3: Power User Jamboree
1010                - Set everything based on specified values */
1011             
1012             /* Use specified storage dimensions */
1013             storage_aspect = (double)job->width / (double)job->height;
1014             width = job->width;
1015             height = job->height;
1016             
1017             /* Time to get picture dimensions that divide cleanly.*/
1018             width  = MULTIPLE_MOD( width, mod);
1019             height = MULTIPLE_MOD( height, mod);
1020             
1021             /* Bind to max dimensions */
1022             if( maxWidth && width > maxWidth )
1023             {
1024                 width = maxWidth;
1025                 // If we are keeping the display aspect, then we are going
1026                 // to be modifying the PAR anyway.  So it's preferred
1027                 // to let the width/height stray some from the original
1028                 // requested storage aspect.
1029                 //
1030                 // But otherwise, PAR and DAR will change the least
1031                 // if we stay as close as possible to the requested
1032                 // storage aspect.
1033                 if ( !job->anamorphic.keep_display_aspect )
1034                 {
1035                     height = ((double)width / storage_aspect) + 0.5;
1036                     height = MULTIPLE_MOD( height, mod);
1037                 }
1038             }
1039             if( maxHeight && height > maxHeight )
1040             {
1041                 height = maxHeight;
1042                 // Ditto, see comment above
1043                 if ( !job->anamorphic.keep_display_aspect )
1044                 {
1045                     width = ((double)height * storage_aspect) + 0.5;
1046                     width  = MULTIPLE_MOD( width, mod);
1047                 }
1048             }
1049             
1050             /* That finishes the storage dimensions. On to display. */            
1051             if( job->anamorphic.dar_width && job->anamorphic.dar_height )
1052             {
1053                 /* We need to adjust the PAR to produce this aspect. */
1054                 pixel_aspect_width = height * job->anamorphic.dar_width / job->anamorphic.dar_height;
1055                 pixel_aspect_height = width;
1056             }
1057             else
1058             {
1059                 /* If we're doing ana 3 and not specifying a DAR, care needs to be taken.
1060                    This indicates a PAR is potentially being set by the interface. But
1061                    this is an output PAR, to correct a source, and it should not be assumed
1062                    that it properly creates a display aspect ratio when applied to the source,
1063                    which could easily be stored in a different resolution. */
1064                 if( job->anamorphic.keep_display_aspect )
1065                 {
1066                     /* We can ignore the possibility of a PAR change */
1067                     pixel_aspect_width = height * ( (double)source_display_width / (double)cropped_height );
1068                     pixel_aspect_height = width;
1069                 }
1070                 else
1071                 {
1072                     int output_display_width = width * (double)pixel_aspect_width /
1073                         (double)pixel_aspect_height;
1074                     pixel_aspect_width = output_display_width;
1075                     pixel_aspect_height = width;
1076                 }
1077             }
1078             
1079             /* Back to caller */
1080             *output_width = width;
1081             *output_height = height;
1082         break;
1083     }
1084     
1085     /* While x264 is smart enough to reduce fractions on its own, libavcodec
1086        needs some help with the math, so lose superfluous factors.            */
1087     hb_reduce( output_par_width, output_par_height,
1088                pixel_aspect_width, pixel_aspect_height );
1089 }
1090
1091 /**
1092  * Calculates job width, height, and cropping parameters.
1093  * @param job Handle to hb_job_t.
1094  * @param aspect Desired aspect ratio. Value of -1 uses title aspect.
1095  * @param pixels Maximum desired pixel count.
1096  */
1097 void hb_set_size( hb_job_t * job, double aspect, int pixels )
1098 {
1099     hb_title_t * title = job->title;
1100
1101     int croppedWidth  = title->width - title->crop[2] - title->crop[3];
1102     int croppedHeight = title->height - title->crop[0] - title->crop[1];
1103     double croppedAspect = title->aspect * title->height * croppedWidth /
1104                            croppedHeight / title->width;
1105     int addCrop;
1106     int i, w, h;
1107
1108     if( aspect <= 0 )
1109     {
1110         /* Keep the best possible aspect ratio */
1111         aspect = croppedAspect;
1112     }
1113
1114     /* Crop if necessary to obtain the desired ratio */
1115     memcpy( job->crop, title->crop, 4 * sizeof( int ) );
1116     if( aspect < croppedAspect )
1117     {
1118         /* Need to crop on the left and right */
1119         addCrop = croppedWidth - aspect * croppedHeight * title->width /
1120                     title->aspect / title->height;
1121         if( addCrop & 3 )
1122         {
1123             addCrop = ( addCrop + 1 ) / 2;
1124             job->crop[2] += addCrop;
1125             job->crop[3] += addCrop;
1126         }
1127         else if( addCrop & 2 )
1128         {
1129             addCrop /= 2;
1130             job->crop[2] += addCrop - 1;
1131             job->crop[3] += addCrop + 1;
1132         }
1133         else
1134         {
1135             addCrop /= 2;
1136             job->crop[2] += addCrop;
1137             job->crop[3] += addCrop;
1138         }
1139     }
1140     else if( aspect > croppedAspect )
1141     {
1142         /* Need to crop on the top and bottom */
1143         addCrop = croppedHeight - croppedWidth * title->aspect *
1144             title->height / aspect / title->width;
1145         if( addCrop & 3 )
1146         {
1147             addCrop = ( addCrop + 1 ) / 2;
1148             job->crop[0] += addCrop;
1149             job->crop[1] += addCrop;
1150         }
1151         else if( addCrop & 2 )
1152         {
1153             addCrop /= 2;
1154             job->crop[0] += addCrop - 1;
1155             job->crop[1] += addCrop + 1;
1156         }
1157         else
1158         {
1159             addCrop /= 2;
1160             job->crop[0] += addCrop;
1161             job->crop[1] += addCrop;
1162         }
1163     }
1164
1165     /* Compute a resolution from the number of pixels and aspect */
1166     for( i = 0;; i++ )
1167     {
1168         w = 16 * i;
1169         h = MULTIPLE_16( (int)( (double)w / aspect ) );
1170         if( w * h > pixels )
1171         {
1172             break;
1173         }
1174     }
1175     i--;
1176     job->width  = 16 * i;
1177     job->height = MULTIPLE_16( (int)( (double)job->width / aspect ) );
1178 }
1179
1180 /**
1181  * Returns the number of jobs in the queue.
1182  * @param h Handle to hb_handle_t.
1183  * @return Number of jobs.
1184  */
1185 int hb_count( hb_handle_t * h )
1186 {
1187     return hb_list_count( h->jobs );
1188 }
1189
1190 /**
1191  * Returns handle to job at index i within the job list.
1192  * @param h Handle to hb_handle_t.
1193  * @param i Index of job.
1194  * @returns Handle to hb_job_t of desired job.
1195  */
1196 hb_job_t * hb_job( hb_handle_t * h, int i )
1197 {
1198     return hb_list_item( h->jobs, i );
1199 }
1200
1201 hb_job_t * hb_current_job( hb_handle_t * h )
1202 {
1203     return( h->current_job );
1204 }
1205
1206 /**
1207  * Applies information from the given job to the official job instance.
1208  * @param h Handle to hb_handle_t.
1209  * @param title_index Index of the title to apply the chapter name to (1-based).
1210  * @param chapter The chapter to apply the name to (1-based).
1211  * @param job Job information to apply.
1212  */
1213 void hb_set_chapter_name( hb_handle_t * h, int title_index, int chapter_index, const char * chapter_name )
1214 {
1215     hb_title_t * title;
1216     title = hb_get_title_by_index( h, title_index );
1217     
1218     hb_chapter_t * chapter = hb_list_item( title->list_chapter, chapter_index - 1 );
1219     
1220     strncpy(chapter->title, chapter_name, 1023);
1221     chapter->title[1023] = '\0';
1222 }
1223
1224 /**
1225  * Applies information from the given job to the official job instance.
1226  * Currently only applies information needed for anamorphic size calculation and previews.
1227  * @param h Handle to hb_handle_t.
1228  * @param title_index Index of the title to apply the job information to (1-based).
1229  * @param job Job information to apply.
1230  */
1231 void hb_set_job( hb_handle_t * h, int title_index, hb_job_t * job )
1232 {
1233         int i;
1234
1235     hb_title_t * title;
1236     title = hb_get_title_by_index( h, title_index );
1237     
1238     hb_job_t * job_target = title->job;
1239     
1240     job_target->deinterlace = job->deinterlace;
1241     job_target->width = job->width;
1242     job_target->height = job->height;
1243     job_target->maxWidth = job->maxWidth;
1244     job_target->maxHeight = job->maxHeight;
1245     for (i = 0; i < 4; i++)
1246     {
1247         job_target->crop[i] = job->crop[i];
1248     }
1249         
1250     job_target->anamorphic = job->anamorphic;
1251 }
1252
1253 /**
1254  * Adds a job to the job list.
1255  * @param h Handle to hb_handle_t.
1256  * @param job Handle to hb_job_t.
1257  */
1258 void hb_add( hb_handle_t * h, hb_job_t * job )
1259 {
1260     hb_job_t      * job_copy;
1261     hb_title_t    * title,    * title_copy;
1262     hb_chapter_t  * chapter,  * chapter_copy;
1263     hb_audio_t    * audio;
1264     hb_subtitle_t * subtitle, * subtitle_copy;
1265     hb_attachment_t * attachment;
1266     int             i;
1267     char            audio_lang[4];
1268
1269     /* Copy the title */
1270     title      = job->title;
1271     title_copy = malloc( sizeof( hb_title_t ) );
1272     memcpy( title_copy, title, sizeof( hb_title_t ) );
1273
1274     title_copy->list_chapter = hb_list_init();
1275     for( i = 0; i < hb_list_count( title->list_chapter ); i++ )
1276     {
1277         chapter      = hb_list_item( title->list_chapter, i );
1278         chapter_copy = malloc( sizeof( hb_chapter_t ) );
1279         memcpy( chapter_copy, chapter, sizeof( hb_chapter_t ) );
1280         hb_list_add( title_copy->list_chapter, chapter_copy );
1281     }
1282
1283     /*
1284      * Copy the metadata
1285      */
1286     if( title->metadata )
1287     {
1288         title_copy->metadata = malloc( sizeof( hb_metadata_t ) );
1289         
1290         if( title_copy->metadata ) 
1291         {
1292             memcpy( title_copy->metadata, title->metadata, sizeof( hb_metadata_t ) );
1293
1294             /*
1295              * Need to copy the artwork seperatly (TODO).
1296              */
1297             if( title->metadata->coverart )
1298             {
1299                 title_copy->metadata->coverart = malloc( title->metadata->coverart_size );
1300                 if( title_copy->metadata->coverart )
1301                 {
1302                     memcpy( title_copy->metadata->coverart, title->metadata->coverart,
1303                             title->metadata->coverart_size );
1304                 } else {
1305                     title_copy->metadata->coverart_size = 0; 
1306                 }
1307             }
1308         }
1309     }
1310
1311     /* Copy the audio track(s) we want */
1312     title_copy->list_audio = hb_list_init();
1313     for( i = 0; i < hb_list_count(job->list_audio); i++ )
1314     {
1315         if( ( audio = hb_list_item( job->list_audio, i ) ) )
1316         {
1317             hb_list_add( title_copy->list_audio, hb_audio_copy(audio) );
1318         }
1319     }
1320
1321     /* Initialize subtitle list - filled out further below */
1322     title_copy->list_subtitle = hb_list_init();
1323     
1324     /* Copy all the attachments */
1325     title_copy->list_attachment = hb_list_init();
1326     for( i = 0; i < hb_list_count(title->list_attachment); i++ )
1327     {
1328         if( ( attachment = hb_list_item( title->list_attachment, i ) ) )
1329         {
1330             hb_list_add( title_copy->list_attachment, hb_attachment_copy(attachment) );
1331         }
1332     }
1333
1334     /*
1335      * The following code is confusing, there are two ways in which
1336      * we select subtitles and it depends on whether this is single or
1337      * two pass mode.
1338      *
1339      * subtitle_scan may be enabled, in which case the first pass
1340      * scans all subtitles of that language. The second pass does not
1341      * select any because they are set at the end of the first pass.
1342      *
1343      * We may have manually selected a subtitle, in which case that is
1344      * selected in the first pass of a single pass, or the second of a
1345      * two pass.
1346      */
1347     memset( audio_lang, 0, sizeof( audio_lang ) );
1348
1349     if ( job->indepth_scan ) {
1350
1351         /*
1352          * Find the first audio language that is being encoded
1353          */
1354         for( i = 0; i < hb_list_count(job->list_audio); i++ )
1355         {
1356             if( ( audio = hb_list_item( job->list_audio, i ) ) )
1357             {
1358                 strncpy(audio_lang, audio->config.lang.iso639_2, sizeof(audio_lang));
1359                 break;
1360             }
1361         }
1362     }
1363
1364     /*
1365      * If doing a subtitle scan then add all the matching subtitles for this
1366      * language.
1367      */
1368     if ( job->indepth_scan )
1369     {
1370         for( i=0; i < hb_list_count( title->list_subtitle ); i++ )
1371         {
1372             subtitle = hb_list_item( title->list_subtitle, i );
1373             if( strcmp( subtitle->iso639_2, audio_lang ) == 0 &&
1374                 subtitle->source == VOBSUB )
1375             {
1376                 /*
1377                  * Matched subtitle language with audio language, so
1378                  * add this to our list to scan.
1379                  *
1380                  * We will update the subtitle list on the second pass
1381                  * later after the first pass has completed.
1382                  */
1383                 subtitle_copy = malloc( sizeof( hb_subtitle_t ) );
1384                 memcpy( subtitle_copy, subtitle, sizeof( hb_subtitle_t ) );
1385                 hb_list_add( title_copy->list_subtitle, subtitle_copy );
1386             }
1387         }
1388     } else {
1389         /*
1390          * Not doing a subtitle scan in this pass, but maybe we are in the
1391          * first pass?
1392          */
1393         if( job->pass != 1 )
1394         {
1395             /*
1396              * Copy all of them from the input job, to the title_copy/job_copy.
1397              */
1398             for(  i = 0; i < hb_list_count(job->list_subtitle); i++ ) {
1399                 if( ( subtitle = hb_list_item( job->list_subtitle, i ) ) )
1400                 {
1401                     subtitle_copy = malloc( sizeof( hb_subtitle_t ) );
1402                     memcpy( subtitle_copy, subtitle, sizeof( hb_subtitle_t ) );
1403                     hb_list_add( title_copy->list_subtitle, subtitle_copy );
1404                 }
1405             }
1406         }
1407     }
1408
1409     /* Copy the job */
1410     job_copy        = calloc( sizeof( hb_job_t ), 1 );
1411     memcpy( job_copy, job, sizeof( hb_job_t ) );
1412     title_copy->job = job_copy;
1413     job_copy->title = title_copy;
1414     job_copy->list_audio = title_copy->list_audio;
1415     job_copy->list_subtitle = title_copy->list_subtitle;   // sharing list between title and job
1416     job_copy->file  = strdup( job->file );
1417     job_copy->h     = h;
1418     job_copy->pause = h->pause_lock;
1419
1420     /* Copy the job filter list */
1421     if( job->filters )
1422     {
1423         int i;
1424         int filter_count = hb_list_count( job->filters );
1425         job_copy->filters = hb_list_init();
1426         for( i = 0; i < filter_count; i++ )
1427         {
1428             /*
1429              * Copy the filters, since the MacGui reuses the global filter objects
1430              * meaning that queued up jobs overwrite the previous filter settings.
1431              * In reality, settings is probably the only field that needs duplicating
1432              * since it's the only value that is ever changed. But name is duplicated
1433              * as well for completeness. Not copying private_data since it gets
1434              * created for each job in renderInit.
1435              */
1436             hb_filter_object_t * filter = hb_list_item( job->filters, i );
1437             hb_filter_object_t * filter_copy = malloc( sizeof( hb_filter_object_t ) );
1438             memcpy( filter_copy, filter, sizeof( hb_filter_object_t ) );
1439             if( filter->name )
1440                 filter_copy->name = strdup( filter->name );
1441             if( filter->settings )
1442                 filter_copy->settings = strdup( filter->settings );
1443             hb_list_add( job_copy->filters, filter_copy );
1444         }
1445     }
1446
1447     /* Add the job to the list */
1448     hb_list_add( h->jobs, job_copy );
1449     h->job_count = hb_count(h);
1450     h->job_count_permanent++;
1451 }
1452
1453 /**
1454  * Removes a job from the job list.
1455  * @param h Handle to hb_handle_t.
1456  * @param job Handle to hb_job_t.
1457  */
1458 void hb_rem( hb_handle_t * h, hb_job_t * job )
1459 {
1460     hb_list_rem( h->jobs, job );
1461
1462     h->job_count = hb_count(h);
1463     if (h->job_count_permanent)
1464         h->job_count_permanent--;
1465
1466     /* XXX free everything XXX */
1467 }
1468
1469 /**
1470  * Starts the conversion process.
1471  * Sets state to HB_STATE_WORKING.
1472  * calls hb_work_init, to launch work thread. Stores handle to work thread.
1473  * @param h Handle to hb_handle_t.
1474  */
1475 void hb_start( hb_handle_t * h )
1476 {
1477     /* XXX Hack */
1478     h->job_count = hb_list_count( h->jobs );
1479     h->job_count_permanent = h->job_count;
1480
1481     hb_lock( h->state_lock );
1482     h->state.state = HB_STATE_WORKING;
1483 #define p h->state.param.working
1484     p.progress  = 0.0;
1485     p.job_cur   = 1;
1486     p.job_count = h->job_count;
1487     p.rate_cur  = 0.0;
1488     p.rate_avg  = 0.0;
1489     p.hours     = -1;
1490     p.minutes   = -1;
1491     p.seconds   = -1;
1492     p.sequence_id = 0;
1493 #undef p
1494     hb_unlock( h->state_lock );
1495
1496     h->paused = 0;
1497
1498     h->work_die    = 0;
1499     h->work_thread = hb_work_init( h->jobs, h->cpu_count,
1500                                    &h->work_die, &h->work_error, &h->current_job );
1501 }
1502
1503 /**
1504  * Pauses the conversion process.
1505  * @param h Handle to hb_handle_t.
1506  */
1507 void hb_pause( hb_handle_t * h )
1508 {
1509     if( !h->paused )
1510     {
1511         hb_lock( h->pause_lock );
1512         h->paused = 1;
1513
1514         hb_current_job( h )->st_pause_date = hb_get_date();
1515
1516         hb_lock( h->state_lock );
1517         h->state.state = HB_STATE_PAUSED;
1518         hb_unlock( h->state_lock );
1519     }
1520 }
1521
1522 /**
1523  * Resumes the conversion process.
1524  * @param h Handle to hb_handle_t.
1525  */
1526 void hb_resume( hb_handle_t * h )
1527 {
1528     if( h->paused )
1529     {
1530 #define job hb_current_job( h )
1531         if( job->st_pause_date != -1 )
1532         {
1533            job->st_paused += hb_get_date() - job->st_pause_date;
1534         }
1535 #undef job
1536
1537         hb_unlock( h->pause_lock );
1538         h->paused = 0;
1539     }
1540 }
1541
1542 /**
1543  * Stops the conversion process.
1544  * @param h Handle to hb_handle_t.
1545  */
1546 void hb_stop( hb_handle_t * h )
1547 {
1548     h->work_die = 1;
1549
1550     h->job_count = hb_count(h);
1551     h->job_count_permanent = 0;
1552
1553     hb_resume( h );
1554 }
1555
1556 /**
1557  * Stops the conversion process.
1558  * @param h Handle to hb_handle_t.
1559  */
1560 void hb_scan_stop( hb_handle_t * h )
1561 {
1562     h->scan_die = 1;
1563
1564     h->job_count = hb_count(h);
1565     h->job_count_permanent = 0;
1566
1567     hb_resume( h );
1568 }
1569
1570 /**
1571  * Gets a filter object with the given type and settings.
1572  * @param filter_id The type of filter to get.
1573  * @param settings The filter settings to use.
1574  * @returns The requested filter object.
1575  */
1576 hb_filter_object_t * hb_get_filter_object(int filter_id, const char * settings)
1577 {
1578     if (filter_id == HB_FILTER_ROTATE)
1579     {
1580         hb_filter_rotate.settings = (char*)settings;
1581         return &hb_filter_rotate;
1582     }
1583
1584     if (filter_id == HB_FILTER_DETELECINE)
1585     {
1586         hb_filter_detelecine.settings = (char*)settings;
1587         return &hb_filter_detelecine;
1588     }
1589
1590     if (filter_id == HB_FILTER_DECOMB)
1591     {
1592         hb_filter_decomb.settings = (char*)settings;
1593         return &hb_filter_decomb;
1594     }
1595
1596     if (filter_id == HB_FILTER_DEINTERLACE)
1597     {
1598         hb_filter_deinterlace.settings = (char*)settings;
1599         return &hb_filter_deinterlace;
1600     }
1601
1602     if (filter_id == HB_FILTER_DEBLOCK)
1603     {
1604         hb_filter_deblock.settings = (char*)settings;
1605         return &hb_filter_deblock;
1606     }
1607
1608     if (filter_id == HB_FILTER_DENOISE)
1609     {
1610         hb_filter_denoise.settings = (char*)settings;
1611         return &hb_filter_denoise;
1612     }
1613     return NULL;
1614 }
1615
1616 /**
1617  * Returns the state of the conversion process.
1618  * @param h Handle to hb_handle_t.
1619  * @param s Handle to hb_state_t which to copy the state data.
1620  */
1621 void hb_get_state( hb_handle_t * h, hb_state_t * s )
1622 {
1623     hb_lock( h->state_lock );
1624
1625     memcpy( s, &h->state, sizeof( hb_state_t ) );
1626     if ( h->state.state == HB_STATE_SCANDONE || h->state.state == HB_STATE_WORKDONE )
1627         h->state.state = HB_STATE_IDLE;
1628
1629     hb_unlock( h->state_lock );
1630 }
1631
1632 void hb_get_state2( hb_handle_t * h, hb_state_t * s )
1633 {
1634     hb_lock( h->state_lock );
1635
1636     memcpy( s, &h->state, sizeof( hb_state_t ) );
1637
1638     hb_unlock( h->state_lock );
1639 }
1640
1641 /**
1642  * Called in MacGui in UpdateUI to check
1643  *  for a new scan being completed to set a new source
1644  */
1645 int hb_get_scancount( hb_handle_t * h)
1646  {
1647      return h->scanCount;
1648  }
1649
1650 /**
1651  * Closes access to libhb by freeing the hb_handle_t handle ontained in hb_init.
1652  * @param _h Pointer to handle to hb_handle_t.
1653  */
1654 void hb_close( hb_handle_t ** _h )
1655 {
1656     hb_handle_t * h = *_h;
1657     hb_title_t * title;
1658
1659     h->die = 1;
1660     
1661     hb_thread_close( &h->main_thread );
1662
1663     while( ( title = hb_list_item( h->list_title, 0 ) ) )
1664     {
1665         hb_list_rem( h->list_title, title );
1666         if( title->job && title->job->filters )
1667         {
1668             hb_list_close( &title->job->filters );
1669         }
1670         free( title->job );
1671         hb_title_close( &title );
1672     }
1673     hb_list_close( &h->list_title );
1674
1675     hb_list_close( &h->jobs );
1676     hb_lock_close( &h->state_lock );
1677     hb_lock_close( &h->pause_lock );
1678
1679     free( h );
1680     *_h = NULL;
1681 }
1682
1683 /**
1684  * Cleans up libhb at a process level. Call before the app closes. Removes preview directory.
1685  */
1686 void hb_global_close()
1687 {
1688     char dirname[1024];
1689     DIR * dir;
1690     struct dirent * entry;
1691     
1692     /* Find and remove temp folder */
1693     memset( dirname, 0, 1024 );
1694     hb_get_temporary_directory( dirname );
1695
1696     dir = opendir( dirname );
1697     if (dir)
1698     {
1699         while( ( entry = readdir( dir ) ) )
1700         {
1701             char filename[1024];
1702             if( entry->d_name[0] == '.' )
1703             {
1704                 continue;
1705             }
1706             memset( filename, 0, 1024 );
1707             snprintf( filename, 1023, "%s/%s", dirname, entry->d_name );
1708             unlink( filename );
1709         }
1710         closedir( dir );
1711         rmdir( dirname );
1712     }
1713 }
1714
1715 /**
1716  * Monitors the state of the update, scan, and work threads.
1717  * Sets scan done state when scan thread exits.
1718  * Sets work done state when work thread exits.
1719  * @param _h Handle to hb_handle_t
1720  */
1721 static void thread_func( void * _h )
1722 {
1723     hb_handle_t * h = (hb_handle_t *) _h;
1724     char dirname[1024];
1725
1726     h->pid = getpid();
1727
1728     /* Create folder for temporary files */
1729     memset( dirname, 0, 1024 );
1730     hb_get_temporary_directory( dirname );
1731
1732     hb_mkdir( dirname );
1733
1734     while( !h->die )
1735     {
1736         /* In case the check_update thread hangs, it'll die sooner or
1737            later. Then, we join it here */
1738         if( h->update_thread &&
1739             hb_thread_has_exited( h->update_thread ) )
1740         {
1741             hb_thread_close( &h->update_thread );
1742         }
1743
1744         /* Check if the scan thread is done */
1745         if( h->scan_thread &&
1746             hb_thread_has_exited( h->scan_thread ) )
1747         {
1748             hb_thread_close( &h->scan_thread );
1749
1750             if ( h->scan_die )
1751             {
1752                 hb_title_t * title;
1753
1754                 hb_remove_previews( h );
1755                 while( ( title = hb_list_item( h->list_title, 0 ) ) )
1756                 {
1757                     hb_list_rem( h->list_title, title );
1758                     hb_title_close( &title );
1759                 }
1760
1761                 hb_log( "hb_scan: canceled" );
1762             }
1763             else
1764             {
1765                 hb_log( "libhb: scan thread found %d valid title(s)",
1766                         hb_list_count( h->list_title ) );
1767             }
1768             hb_lock( h->state_lock );
1769             h->state.state = HB_STATE_SCANDONE; //originally state.state
1770                         hb_unlock( h->state_lock );
1771                         /*we increment this sessions scan count by one for the MacGui
1772                         to trigger a new source being set */
1773             h->scanCount++;
1774         }
1775
1776         /* Check if the work thread is done */
1777         if( h->work_thread &&
1778             hb_thread_has_exited( h->work_thread ) )
1779         {
1780             hb_thread_close( &h->work_thread );
1781
1782             hb_log( "libhb: work result = %d",
1783                     h->work_error );
1784             hb_lock( h->state_lock );
1785             h->state.state                = HB_STATE_WORKDONE;
1786             h->state.param.workdone.error = h->work_error;
1787
1788             h->job_count = hb_count(h);
1789             if (h->job_count < 1)
1790                 h->job_count_permanent = 0;
1791             hb_unlock( h->state_lock );
1792         }
1793
1794         hb_snooze( 50 );
1795     }
1796
1797     if( h->scan_thread )
1798     {
1799         hb_scan_stop( h );
1800         hb_thread_close( &h->scan_thread );
1801     }
1802     if( h->work_thread )
1803     {
1804         hb_stop( h );
1805         hb_thread_close( &h->work_thread );
1806     }
1807     hb_remove_previews( h );
1808 }
1809
1810 /**
1811  * Redirects stderr to the registered callback
1812  * function.
1813  * @param _data Unused.
1814  */
1815 static void redirect_thread_func(void * _data)
1816 {
1817     int pfd[2];
1818     pipe(pfd);
1819 #if defined( SYS_MINGW )
1820     // dup2 doesn't work on windows for some stupid reason
1821     stderr->_file = pfd[1];
1822 #else
1823     dup2(pfd[1], /*stderr*/ 2);
1824 #endif
1825     FILE * log_f = fdopen(pfd[0], "rb");
1826     
1827     char line_buffer[500];
1828     while(fgets(line_buffer, 500, log_f) != NULL)
1829     {
1830         hb_log_callback(line_buffer);
1831     }
1832 }
1833
1834 /**
1835  * Returns the PID.
1836  * @param h Handle to hb_handle_t
1837  */
1838 int hb_get_pid( hb_handle_t * h )
1839 {
1840     return h->pid;
1841 }
1842
1843 /**
1844  * Returns the id for the given instance.
1845  * @param h Handle to hb_handle_t
1846  * @returns The ID for the given instance
1847  */
1848 int hb_get_instance_id( hb_handle_t * h )
1849 {
1850     return h->id;
1851 }
1852
1853 /**
1854  * Returns the title with the given title index.
1855  * @param h Handle to hb_handle_t
1856  * @param title_index the index of the title to get
1857  * @returns The requested title
1858  */
1859 hb_title_t * hb_get_title_by_index( hb_handle_t * h, int title_index )
1860 {
1861     hb_title_t * title;
1862     int i;
1863         int count = hb_list_count( h->list_title );
1864     for (i = 0; i < count; i++)
1865     {
1866         title = hb_list_item( h->list_title, i );
1867         if (title->index == title_index)
1868         {
1869             return title;
1870         }
1871     }
1872     
1873     return NULL;
1874 }
1875
1876 /**
1877  * Sets the current state.
1878  * @param h Handle to hb_handle_t
1879  * @param s Handle to new hb_state_t
1880  */
1881 void hb_set_state( hb_handle_t * h, hb_state_t * s )
1882 {
1883     hb_lock( h->pause_lock );
1884     hb_lock( h->state_lock );
1885     memcpy( &h->state, s, sizeof( hb_state_t ) );
1886     if( h->state.state == HB_STATE_WORKING ||
1887         h->state.state == HB_STATE_SEARCHING )
1888     {
1889         /* XXX Hack */
1890         if (h->job_count < 1)
1891             h->job_count_permanent = 1;
1892
1893         h->state.param.working.job_cur =
1894             h->job_count_permanent - hb_list_count( h->jobs );
1895         h->state.param.working.job_count = h->job_count_permanent;
1896
1897         // Set which job is being worked on
1898         if (h->current_job)
1899             h->state.param.working.sequence_id = h->current_job->sequence_id;
1900         else
1901             h->state.param.working.sequence_id = 0;
1902     }
1903     hb_unlock( h->state_lock );
1904     hb_unlock( h->pause_lock );
1905 }
1906
1907 /* Passes a pointer to persistent data */
1908 hb_interjob_t * hb_interjob_get( hb_handle_t * h )
1909 {
1910     return h->interjob;
1911 }