Handbrake Crash

Support for HandBrake on Linux, Solaris, and other Unix-like platforms
Forum rules
An Activity Log is required for support requests. Please read How-to get an activity log? for details on how and why this should be provided.
Post Reply
gnif
Posts: 5
Joined: Thu Apr 04, 2019 1:14 pm

Handbrake Crash

Post by gnif »

Description of problem or question:

When handbrake gets to pass 2 of the encode process, about 8% in it crashes with an 'Abort'.

Steps to reproduce the problem (If Applicable):

Not sure, seems to be specific to the title being ripped, which is "Back to the Future".

HandBrake version (e.g., 1.0.0):

1.2.2

Operating system and version (e.g., Ubuntu 16.04 LTS, macOS 10.13 High Sierra, Windows 10 Creators Update):

Debian Buster

HandBrake Activity Log ***required*** (see How-to get an activity log)

http://paste.debian.net/1076075/

I also created a backtrace

Code: Select all

(gdb) bt
#0  0x00007ffff32528bb in __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:50
#1  0x00007ffff323d535 in __GI_abort () at abort.c:79
#2  0x00007ffff3294778 in __libc_message (action=action@entry=do_abort, fmt=fmt@entry=0x7ffff339f28d "%s\n") at ../sysdeps/posix/libc_fatal.c:181
#3  0x00007ffff329ae6a in malloc_printerr (str=str@entry=0x7ffff33a1018 "double free or corruption (!prev)") at malloc.c:5341
#4  0x00007ffff329c98c in _int_free (av=0x7ffec0000020, p=0x7ffec0020e90, have_lock=<optimized out>) at malloc.c:4309
#5  0x00005555555e2517 in Decode (w=<optimized out>) at ../libhb/decvobsub.c:729
#6  0x00005555555e2517 in decsubWork (w=<optimized out>, buf_in=<optimized out>, buf_out=0x7ffecdffa300) at ../libhb/decvobsub.c:169
#7  0x000055555560c69c in hb_work_loop (_w=0x7fffac0208f0) at ../libhb/work.c:1931
#8  0x00005555555c963b in hb_thread_func (_t=0x7fffac7ba580) at ../libhb/ports.c:867
#9  0x00007ffff558bfa3 in start_thread (arg=<optimized out>) at pthread_create.c:486
#10 0x00007ffff331482f in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:95
I am a developer myself and I can not see how this could happen unless the malloc is failing.
User avatar
JohnAStebbins
HandBrake Team
Posts: 5712
Joined: Sat Feb 09, 2008 7:21 pm

Re: Handbrake Crash

Post by JohnAStebbins »

Even if malloc failed, free would not fail but rather a use of 'raw_buf' would segfault. This is more likely some sort of heap corruption causing free to abort. The activity log indicates possible double free.

Code: Select all

double free or corruption (!prev)
valgrind can find such things, but is very *very* slow. So if this could be reproduced by encoding a smaller segment of the DVD it would be easier to find the cause. Can you try to reproduce by removing subtitle foreign audio search and manually adding subtitle track 2 with forced-only and burn-in checked? Then try using point-to-point encoding to narrow the range (chapters can be changed to seconds and a range in seconds can be set). The error happens after chapter 2 which has a timestamp of 21772800 which is 241 seconds (90khz clock). If you can reproduce with as short a range as possible, that will make a valgrind analysis go much faster.
gnif
Posts: 5
Joined: Thu Apr 04, 2019 1:14 pm

Re: Handbrake Crash

Post by gnif »

Thanks, I did start a run under valgrind but as you mentioned found out how slow it was. I will do what I can and try to narrow it down as you suggested.
gnif
Posts: 5
Joined: Thu Apr 04, 2019 1:14 pm

Re: Handbrake Crash

Post by gnif »

I managed to reproduce it with full debugging and optimisations disabled under valgrind.

Code: Select all

==30664== Conditional jump or move depends on uninitialised value(s)
==30664==    at 0x2F92D9: Decode (decvobsub.c:684)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664== 
==30664== Conditional jump or move depends on uninitialised value(s)
==30664==    at 0x2F9352: Decode (decvobsub.c:687)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664== 
==30664== Use of uninitialised value of size 8
==30664==    at 0x2F94D3: Decode (decvobsub.c:708)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664== 
==30664== Conditional jump or move depends on uninitialised value(s)
==30664==    at 0x483C7EF: memset (vg_replace_strmem.c:1251)
==30664==    by 0x2F9502: Decode (decvobsub.c:707)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664== 
==30664== Conditional jump or move depends on uninitialised value(s)
==30664==    at 0x483C83A: memset (vg_replace_strmem.c:1251)
==30664==    by 0x2F9502: Decode (decvobsub.c:707)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664== 
==30664== Conditional jump or move depends on uninitialised value(s)
==30664==    at 0x483C879: memset (vg_replace_strmem.c:1251)
==30664==    by 0x2F9502: Decode (decvobsub.c:707)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664== 
==30664== Conditional jump or move depends on uninitialised value(s)
==30664==    at 0x483C88A: memset (vg_replace_strmem.c:1251)
==30664==    by 0x2F9502: Decode (decvobsub.c:707)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
This repeats a few hundred times until it finally writes past the end of the buffer

Code: Select all

==30664== Use of uninitialised value of size 8
==30664==    at 0x483C814: memset (vg_replace_strmem.c:1251)
==30664==    by 0x2F9547: Decode (decvobsub.c:709)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664== 
==30664== Use of uninitialised value of size 8
==30664==    at 0x483C814: memset (vg_replace_strmem.c:1251)
==30664==    by 0x2F958C: Decode (decvobsub.c:711)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664== 
==30664== Use of uninitialised value of size 8
==30664==    at 0x483C814: memset (vg_replace_strmem.c:1251)
==30664==    by 0x2F95D1: Decode (decvobsub.c:713)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664== 
==30664== Invalid write of size 8
==30664==    at 0x483C81B: memset (vg_replace_strmem.c:1251)
==30664==    by 0x2F95D1: Decode (decvobsub.c:713)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664==  Address 0x4b13a980 is 0 bytes after a block of size 1,644,480 alloc'd
==30664==    at 0x483577F: malloc (vg_replace_malloc.c:299)
==30664==    by 0x2F920E: Decode (decvobsub.c:664)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664== 
==30664== Invalid write of size 8
==30664==    at 0x483C81F: memset (vg_replace_strmem.c:1251)
==30664==    by 0x2F95D1: Decode (decvobsub.c:713)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
==30664==  Address 0x4b13a988 is 8 bytes after a block of size 1,644,480 alloc'd
==30664==    at 0x483577F: malloc (vg_replace_malloc.c:299)
==30664==    by 0x2F920E: Decode (decvobsub.c:664)
==30664==    by 0x2F82EC: decsubWork (decvobsub.c:169)
==30664==    by 0x339693: hb_work_loop (work.c:1931)
==30664==    by 0x2D79CF: hb_thread_func (ports.c:870)
==30664==    by 0x627FFA2: start_thread (pthread_create.c:486)
==30664==    by 0x78C782E: clone (clone.S:95)
User avatar
JohnAStebbins
HandBrake Team
Posts: 5712
Joined: Sat Feb 09, 2008 7:21 pm

Re: Handbrake Crash

Post by JohnAStebbins »

Thanks. I think there is a malformed vobsub that we are not protecting against. Can you patch with some additional logging and retest so I can verify? It will produce a lot of output to stdout so you should run the abbreviated test again.

Code: Select all

diff --git a/libhb/decvobsub.c b/libhb/decvobsub.c
index a78f7a303..f6f4762cb 100644
--- a/libhb/decvobsub.c
+++ b/libhb/decvobsub.c
@@ -400,6 +400,7 @@ static int ParseControls( hb_work_object_t * w )
                 {
                     pv->offsets[0] = ( buf[i] << 8 ) | buf[i+1]; i += 2;
                     pv->offsets[1] = ( buf[i] << 8 ) | buf[i+1]; i += 2;
+printf("parse offsets %d %d\n", pv->offsets[0], pv->offsets[1]);
                     break;
                 }
             }
@@ -627,6 +628,7 @@ static hb_buffer_t * Decode( hb_work_object_t * w )
     hb_job_t * job = pv->job;
 
     /* Get infos about the subtitle */
+printf("Decode\n");
     if ( ParseControls( w ) )
     {
         /*
@@ -669,6 +671,7 @@ static hb_buffer_t * Decode( hb_work_object_t * w )
 
     offsets[0] = pv->offsets[0] * 2;
     offsets[1] = pv->offsets[1] * 2;
+printf("offsets %d %d\n", offsets[0], offsets[1]);
 
     for( line = 0; line < pv->height; line++ )
     {
@@ -712,6 +715,7 @@ static hb_buffer_t * Decode( hb_work_object_t * w )
                     pv->chromaU[code & 3], code >> 2 );
             memset( chromaV + line * pv->width + col,
                     pv->chromaV[code & 3], code >> 2 );
+printf("width %d height %d line %d col %d code %x\n", pv->width, pv->height, line, col, code);
         }
 
         /* Byte-align */
User avatar
JohnAStebbins
HandBrake Team
Posts: 5712
Joined: Sat Feb 09, 2008 7:21 pm

Re: Handbrake Crash

Post by JohnAStebbins »

Oops, I'm printing *after* it's going to crash. Not very helpful. Corrected patch

Code: Select all

diff --git a/libhb/decvobsub.c b/libhb/decvobsub.c
index a78f7a303..775bd66b1 100644
--- a/libhb/decvobsub.c
+++ b/libhb/decvobsub.c
@@ -400,6 +400,7 @@ static int ParseControls( hb_work_object_t * w )
                 {
                     pv->offsets[0] = ( buf[i] << 8 ) | buf[i+1]; i += 2;
                     pv->offsets[1] = ( buf[i] << 8 ) | buf[i+1]; i += 2;
+printf("parse offsets %d %d\n", pv->offsets[0], pv->offsets[1]);
                     break;
                 }
             }
@@ -626,6 +627,7 @@ static hb_buffer_t * Decode( hb_work_object_t * w )
     uint8_t * buf_raw = NULL;
     hb_job_t * job = pv->job;
 
+printf("Decode\n");
     /* Get infos about the subtitle */
     if ( ParseControls( w ) )
     {
@@ -669,6 +671,7 @@ static hb_buffer_t * Decode( hb_work_object_t * w )
 
     offsets[0] = pv->offsets[0] * 2;
     offsets[1] = pv->offsets[1] * 2;
+printf("offsets %d %d\n", offsets[0], offsets[1]);
 
     for( line = 0; line < pv->height; line++ )
     {
@@ -704,6 +707,7 @@ static hb_buffer_t * Decode( hb_work_object_t * w )
             chromaU = alpha + pv->width * pv->height;
             chromaV = chromaU + pv->width * pv->height;
 
+printf("width %d height %d line %d col %d code %x\n", pv->width, pv->height, line, col, code);
             memset( lum + line * pv->width + col,
                     pv->lum[code & 3], code >> 2 );
             memset( alpha + line * pv->width + col,

gnif
Posts: 5
Joined: Thu Apr 04, 2019 1:14 pm

Re: Handbrake Crash

Post by gnif »

Here is the output from this run, please note that the final line was truncated as the crash occurred before the output had finished flushing.

http://slexy.org/view/s21YJ6PWU7

Edit: added some calls to fflush and re-ran:

http://slexy.org/view/s2HIe0kdlr
User avatar
JohnAStebbins
HandBrake Team
Posts: 5712
Joined: Sat Feb 09, 2008 7:21 pm

Re: Handbrake Crash

Post by JohnAStebbins »

Perfect, that's exactly what I wanted to see. The last runlength is attempting to write a line that is 732 pixels wide when the specified object width is 720. So I just need to add a bounds check. Thanks for all your help!
User avatar
JohnAStebbins
HandBrake Team
Posts: 5712
Joined: Sat Feb 09, 2008 7:21 pm

Re: Handbrake Crash

Post by JohnAStebbins »

gnif
Posts: 5
Joined: Thu Apr 04, 2019 1:14 pm

Re: Handbrake Crash

Post by gnif »

Confirmed, thanks!
Post Reply