
Я пытаюсь записать видео с помощью USB-камеры, но у меня возникают некоторые проблемы при использовании ffmpeg
.
Если я запускаю ffmpeg -f video4linux2 -t 00:00:10 -i /dev/video0 out.mpg
, программа пытается записать с разрешением 640x480 и ffmpeg
зависает.
Однако если я добавлю -s
и ffmpeg
начну запись с разрешением ниже 640x480 (например, 320x240), видео запишется успешно.
После зависания, если я нажимаю CTRL+C
, ffmpeg возобновляет работу, выдавая файл размером 0 кБ. Используя strace
я могу видеть, что ioctl
вызов устройства сохраняет возвраты -EINVAL
и последующие ioctl
s возвращают -EAGAIN
.
ioctl(3, VIDIOC_G_STD, 0xbe84dfb0) = -1 EINVAL (Invalid argument)
ioctl(3, VIDIOC_DQBUF, {type=V4L2_BUF_TYPE_VIDEO_CAPTURE}) = -1 EAGAIN (Resource temporarily unavailable)
Есть идеи, почему это происходит?
Я использую ffmpeg
версию 2.8.7, построенную через busybox
1.25. Архитектура хоста — процессор ARM с ядром 3.2.
Я также попробовал скомпилировать последнюю версию из исходного кода, но проблема осталась...
решение1
Разобрался в причине: перекодировка и объем необработанных данных.
Используя командную строку, упомянутую в моем вопросе, я считывал из формата raw (yuv422) и перекодировал его в mpeg-1, который был кодировкой по умолчанию для моей версии ffmpeg
. Объем данных, передаваемых с камеры, был просто слишком большим для процессора, что приводило к зависанию. Камера, которую я использовал, могла также транслировать в сжатом формате (mjpeg). Переключившись на этот формат, ffmpeg
зависания больше не было, и я мог записывать со скоростью 15 кадров в секунду.
Однако был шаг перекодирования, из mjpeg в mpeg-1. Мне удалось достичь более высокого количества кадров в секунду, указав ffmpeg
копировать поток, удалив последний шаг перекодирования.