I have some long videos (about 90 minutes) that take a very long time to transcode on my server. I'm using HTML5 with 3 versions of each video - h.264/mp4, vp8/webm, and h.264/mov (lower size/quality) for iphone like devices.

The first preset was run at Tuesday, December 27, 2011 - 5:40pm
nice -n 19 /usr/bin/ffmpeg -y -i '/usr/share/drupal6/files/videos/original/vwfl-2011.mp4' -vcodec copy -acodec copy '/tmp/vwfl-2011.mp4' 2>&1

I prepare the file locally because its faster and then just use -vcodec copy and -acodec copy for a fast transcode

Next comes the webm transcode at Tuesday, December 27, 2011 - 5:41pm
nice -n 19 /usr/bin/ffmpeg -y -i '/usr/share/drupal6/files/videos/original/vwfl-2011.mp4' -pass 1 -passlogfile /tmp/ffmpeg2pass -threads 8 -vcodec libvpx -b 720k -g 120 -level 216 -profile 0 -qmax 42 -qmin 10 -rc_buf_aggressivity 0.95 -vf "scale=min(iw\,640):ow/dar,setsar=1:1" -an -f webm /dev/null 2>&1

and the 2nd pass for webm at Tuesday, December 27, 2011 - 8:07pm
nice -n 19 /usr/bin/ffmpeg -y -i '/usr/share/drupal6/files/videos/original/vwfl-2011.mp4' -pass 2 -passlogfile /tmp/ffmpeg2pass -threads 8 -vcodec libvpx -b 720k -g 120 -level 216 -profile 0 -qmax 42 -qmin 10 -rc_buf_aggressivity 0.95 -vf "scale=min(iw\,640):ow/dar,setsar=1:1" -acodec libvorbis -ac 2 -ab 96k -ar 44100 -f webm '/usr/share/drupal6/files/videos/converted/vwfl-2011.webm' 2>&1

This chugs away for hours and I believe finished at around 4:28am

The last preset never logs an entry and it looks like the log entries are quite different in 6.x-4.7 from the previous release as I only have video_ffmpeg as a category and its not showing me errors when ffmpeg failed.

In 6.x-4.6 what was happening is that it would run ffmpeg -i to get information about the video but when it went to transcode the video, the file original/vwfl-2011.mp4 wouldn't exist. I'm surmising that is the case in this version also.

I checked my filesystem

# cd /usr/share/share/drupal6/files/video
# ls -lhrt
...
drwxrwxr-x. 2 kjh    apache 4.0K Dec 28 04:28 converted
-rw-rw-r--  1 apache apache 628M Dec 28 04:28 vwfl-2011.mp4
drwxrwxr-x. 2 kjh    apache 4.0K Dec 28 04:28 original

Note that the video is now in the video directory not the original directory. I can verify that it was there during the long transcode process. The two versions that were transcoded are have been removed from the converted directory.

The video is in status 5:

mysql> select * from video_files where nid=8343;
+-----+--------+------+------------+--------+---------+-----------+------+
| vid | fid    | nid  | dimensions | status | started | completed | data |
+-----+--------+------+------------+--------+---------+-----------+------+
| 116 | 122039 | 8343 | 640x360    |      5 |       0 |         0 | NULL |
+-----+--------+------+------------+--------+---------+-----------+------+
1 row in set (0.00 sec)

Shorter videos transcode just fine and I've tested this both with transcoding on file save and via cron.

Comments

bkat’s picture

As we can see, the files table thinks the video file is in the files/video/original directory

mysql> select * from files where fid=122039;
+--------+-----+---------------+-------------------------------------+-----------+-----------+--------+------------+
| fid    | uid | filename      | filepath                            | filemime  | filesize  | status | timestamp  |
+--------+-----+---------------+-------------------------------------+-----------+-----------+--------+------------+
| 122039 |   1 | vwfl-2011.mp4 | files/videos/original/vwfl-2011.mp4 | video/mp4 | 658217696 |      1 | 1325028562 |
+--------+-----+---------------+-------------------------------------+-----------+-----------+--------+------------+
Jorrit’s picture

Thanks for your report. Are there any errors in your apache error log, such as errors about a PHP time limit that has been reached?

Jorrit’s picture

Does your server have enough free disk space?

Jorrit’s picture

It is new behaviour in 4.7 that after a failed transcode the outputs are deleted and the file is moved back to the videos/ folder. The database should also have been updated. I can't reproduce the error that the files table still contains the filepath with /original/.

bkat’s picture

There is 49G free on / and 683G free on /home the drupal file system /usr/share/drupal6/files is on /

One thing I'm curious about is that the output from ffmpeg is being captured into memory. It will generate a lot of output since ffmpeg continuously spews out a line for frames that it is processing. I'm doing another test with -nostats command line option in the presets.

It looks like something did go wrong with the last transcode:

sh: line 1: 18177 Segmentation fault nice -n 19 /usr/bin/ffmpeg -y -i '/usr/share/drupal6/files/videos/original/vwfl-2011.mp4' -b 384k -vcodec mpeg4 -acodec libfaac -ac 2 -ar 44100 -ab 64k -vf "scale=gte(dar\,480/320)*480+lt(dar\,480/320)*(320*dar):-1,setsar=1:1,pad=480:320:(ow-iw)/2:(oh-ih)/2" -crf 22 '/tmp/vwfl-2011.mov' 2>&1

and the following file was left behind

# ls -lhrt /tmp/vwfl-2011.mov 
-rw-r--r-- 1 apache apache 189M Dec 28 04:28 /tmp/vwfl-2011.mov

The file should be about 334M when transcoded with this preset. I'll do some investigating on the transcode failure.

However, my system seems to be in an inconsistent state:
1. The status is set to 5 and not to the error state
2. The files table has the wrong file name
3. No watchdog entries were written for this preset

Also it looks like video_ffmpeg.inc checks to see if the output file exists with a filesize != 0 to determine if ffmpeg was successful. This doesn't seem safe if either ffmpeg or qt-faststart fail after partially writing their output files.

Jorrit’s picture

The strange thing is that the video has been moved back to the /videos dir. The command to update the database is right after that move.

What's the command that you use to run the cron job?

bkat’s picture

The video being moved back is weird but there are no errors logged by drupal and not even the debug letting us know that we're running the ffmpeg for the preset that is failing.

Cron is invoked via
/usr/bin/wget -O - -q http://mydomain.com/cron.php

I tried using drush video-scheduler but as I pointed out in a different bug, that isn't working.

I ran the exact ffmpeg from the command line on the same machine and it completed without segfaulting.

bkat’s picture

I ran the test with "-nostats" on my ffmpeg commands and it transcoded all three presets. The files were left in the original and converted directory but the database was not updated. I wonder if the database connection is getting disconnected after such a long period (10+ hours) without any activity?

Jorrit’s picture

When you run the cron command, is the output sent somewhere? I always put the following at the top of my crontab, so the output gets sent to my e-mailaddress. If there is no output I don't get an e-mail.

MAILTO=my@email.com

x x x x x /usr/bin/wget -O - -q http://mydomain.com/cron.php
....

I assume you are using MySQL. Could you run the following command and report what the timeout values are?

drush sql-query "SHOW VARIABLES LIKE '%timeout%'"

bkat’s picture

I ran the wget by hand and it returned long before the transcode failed.

I'm using mysql with the default timeouts which are 8 hours for wait_timeout and interactive_timeout

Variable_name	Value
connect_timeout	10
delayed_insert_timeout	300
innodb_lock_wait_timeout	50
innodb_rollback_on_timeout	OFF
interactive_timeout	28800
lock_wait_timeout	31536000
net_read_timeout	30
net_write_timeout	60
slave_net_timeout	3600
wait_timeout	28800
Jorrit’s picture

Could you please post your ffmpeg version and the command lines that you are using? I am going to try to reproduce this problem.

If you want, you can try to increase the MySQL timeouts and see if the database is updated.

bkat’s picture

ffmpeg 0.9.2

I'm uploading mp4's that are in the format I want so I'm avoiding lengthy transcode by just doing
'!cmd_path -y -nostats -i !videofile -vcodec copy -acodec copy !convertfile'

Next up is webm

        '!cmd_path -y -nostats -i !videofile -pass 1 -passlogfile /tmp/ffmpeg2pass -threads 8 -vcodec libvpx -b 720k -g 120 -level 216 -profile 0 -qmax 42 -qmin 10 -rc_buf_aggressivity 0.95 -vf "scale=min(iw\,!width):ow/dar,setsar=1:1" -an -f webm /dev/null',
         '!cmd_path -y -nostats -i !videofile -pass 2 -passlogfile /tmp/ffmpeg2pass -threads 8 -vcodec libvpx -b 720k -g 120 -level 216 -profile 0 -qmax 42 -qmin 10 -rc_buf_aggressivity 0.95 -vf "scale=min(iw\,!width):ow/dar,setsar=1:1" -acodec libvorbis -ac 2 -ab 96k -ar 44100 -f webm !convertfile'

And finally mov
'!cmd_path -y -nostats -i !videofile -b:v 384k -vcodec mpeg4 -acodec libfaac -ac 2 -ar 44100 -ab 64k -vf "scale=gte(dar\,480/320)*480+lt(dar\,480/320)*(320*dar):-1,setsar=1:1,pad=480:320:(ow-iw)/2:(oh-ih)/2" -crf 22 !convertfile'

The mp4 of course is fast because its just doing a copy. The webm is where the time is spent. My server is really old and is running on an AMD Athlon XP 3200+.

Jorrit’s picture

Status: Active » Postponed (maintainer needs more info)

I have run some MySQL tests and it does indeed kill the connection if the PHP script runs for longer than the timeout period. To check if there are no other issues when transcoding large files except this MySQL timeout, could you increase the interactive_timeout and wait_timeout values?

If this is indeed the problem preventing you from transcoding large files, I will try to change the code so it uses coprocessing to execute a simple MySQL query at a regular interval or to retry the connection after the transcoding has taken place.

Jorrit’s picture

Status: Postponed (maintainer needs more info) » Closed (works as designed)

Closed because of lack of activity.