BASH скрипты

Пакетная конвертация видеофайлов из формата .wmv в .mp4

Содержание
#!/bin/bash

# Проверка наличия ffmpeg с поддержкой NVENC
if ! ffmpeg -encoders | grep -q h264_nvenc; then
  echo "FFmpeg не поддерживает NVENC. Убедитесь, что установлен ffmpeg с поддержкой NVIDIA."
  exit 1
fi

# Обработка всех .mkv файлов в текущей директории
for INPUT in *.wmv; do
  [ -e "$INPUT" ] || continue

  BASENAME="${INPUT%.*}"
  OUTPUT="${BASENAME}.mp4"

  echo "🎬 Конвертация: $INPUT → $OUTPUT"

  ffmpeg -y -hwaccel cuda -i "$INPUT" \
    -vf format=yuv420p \
    -c:v h264_nvenc -preset fast -cq 23 \
    -c:a aac -b:a 192k \
    "$OUTPUT"

  # Проверка успешности ffmpeg
  if [ $? -eq 0 ]; then
    echo "🗑 Удаление исходного файла: $INPUT"
    rm "$INPUT"
  else
    echo "⚠️ Ошибка при конвертации: $INPUT. Файл не удалён."
  fi

  echo "-----------------------------"
done

echo "✅ Все файлы обработаны."

Этот Bash-скрипт предназначен для пакетной конвертации видеофайлов из формата .wmv в .mp4 с использованием аппаратного ускорения NVENC от NVIDIA. Вот подробный разбор его функционала:


🧠 Общая логика

  • Скрипт проверяет наличие поддержки h264_nvenc в установленном ffmpeg.
  • Обрабатывает все .wmv файлы в текущей директории.
  • Конвертирует каждый файл в .mp4 с использованием NVENC.
  • После успешной конвертации удаляет исходный .wmv файл.

🔍 Подробный анализ

1. Проверка поддержки NVENC

if ! ffmpeg -encoders | grep -q h264_nvenc; then
  • Проверяет, доступен ли энкодер h264_nvenc в ffmpeg.
  • Если не найден — выводит сообщение и завершает работу.

2. Цикл обработки файлов

for INPUT in *.wmv; do
  [ -e "$INPUT" ] || continue
  • Перебирает все .wmv файлы.
  • Пропускает итерацию, если файл не существует (на случай, если шаблон не дал результатов).

3. Формирование имени выходного файла

BASENAME="${INPUT%.*}"
OUTPUT="${BASENAME}.mp4"
  • Удаляет расширение .wmv и добавляет .mp4.

4. Конвертация с ffmpeg

ffmpeg -y -hwaccel cuda -i "$INPUT" \
  -vf format=yuv420p \
  -c:v h264_nvenc -preset fast -cq 23 \
  -c:a aac -b:a 192k \
  "$OUTPUT"
  • -hwaccel cuda: включает аппаратное ускорение CUDA.
  • -vf format=yuv420p: задаёт совместимый формат пикселей.
  • -c:v h264_nvenc: кодирует видео с помощью NVENC.
  • -preset fast: баланс между скоростью и качеством.
  • -cq 23: задаёт уровень качества (чем ниже — тем выше качество).
  • -c:a aac -b:a 192k: кодирует аудио в AAC с битрейтом 192 кбит/с.

5. Проверка результата и удаление исходника

if [ $? -eq 0 ]; then
  rm "$INPUT"
  • Если ffmpeg завершился успешно (exit code 0), удаляет исходный .wmv файл.
  • В противном случае — выводит предупреждение.

✅ Вывод

Скрипт автоматизирует конвертацию .wmv.mp4 с использованием NVENC, обеспечивая:

  • Высокую скорость за счёт GPU.
  • Удаление исходников после успешной обработки.
  • Простую диагностику ошибок.

Если хочешь адаптировать его под .mkv, .avi или другие форматы — просто замени шаблон *.wmv и расширение в OUTPUT.

Вот улучшенная версия вашего скрипта с добавлением:

  • ✅ Удаления временных файлов (если они создаются)
  • 🎧 Поддержки нескольких аудиодорожек и субтитров
  • 🎚 Возможности выбора качества через переменные PRESET, CRF, AUDIO_BITRATE

Улучшенный скрипт
#!/bin/bash
set -e
set -u
set -o pipefail

# Настройки качества (можно переопределить при запуске)
PRESET="${PRESET:-fast}"         # fast, medium, slow
CRF="${CRF:-23}"                 # 0 (макс. качество) – 51 (минимум)
AUDIO_BITRATE="${AUDIO_BITRATE:-192k}"

# Определение кодека: NVENC или libx264
if ffmpeg -hide_banner -encoders | grep -q h264_nvenc; then
  echo "✅ NVENC доступен, используем h264_nvenc"
  VIDEO_CODEC="h264_nvenc"
  QUALITY_PARAM="-cq $CRF"
  HWACCEL="-hwaccel cuda -hwaccel_output_format cuda"
else
  echo "⚠️ NVENC недоступен, переключаемся на libx264"
  VIDEO_CODEC="libx264"
  QUALITY_PARAM="-crf $CRF"
  HWACCEL=""
fi

# Обработка всех .wmv и .mkv файлов
for INPUT in *.wmv *.mkv *.avi; do
  [ -e "$INPUT" ] || continue

  BASENAME="${INPUT%.*}"
  OUTPUT="${BASENAME}.mp4"
  TEMP_FILE="/tmp/${BASENAME}_temp.mp4"

  echo "🎬 Конвертация: $INPUT → $OUTPUT"

  ffmpeg -y $HWACCEL -i "$INPUT" \
    -map 0:v -map 0:a? \
    -vf format=yuv420p \
    -c:v "$VIDEO_CODEC" -preset "$PRESET" $QUALITY_PARAM \
    -c:a aac -b:a "$AUDIO_BITRATE" \
    "$TEMP_FILE"

  if [ -f "$TEMP_FILE" ]; then
    mv "$TEMP_FILE" "$OUTPUT"
    echo "🗑 Удаление исходного файла: $INPUT"
    rm "$INPUT"
  else
    echo "❌ Ошибка при конвертации: $INPUT. Файл не удалён."
    rm -f "$TEMP_FILE"
  fi

  echo "-----------------------------"
done

echo "✅ Все файлы обработаны."

🧪 Примеры запуска

  • Стандартный запуск: ./convert.sh
  • С выбором качества: PRESET=slow CRF=18 AUDIO_BITRATE=256k ./convert.sh

🧠 Объяснение изменений

  • -map 0 — захватывает все потоки: видео, аудио, субтитры.
  • PRESET, CRF, AUDIO_BITRATE — позволяют гибко управлять качеством.
  • TEMP_FILE — используется для безопасной конвертации, чтобы не перезаписать выходной файл при ошибке.
  • rm -f "$TEMP_FILE" — удаляет временный файл при ошибке.

Если хочешь добавить выбор конкретной аудиодорожки по языку, автоматическое извлечение субтитров или логирование — могу доработать дальше.

Конвертация DVD-структур (каталогов VIDEO_TS) в .mp4

Содержание
#!/bin/bash
set -e
set -u
set -o pipefail

SOURCE_ROOT="."
DEST_ROOT="."
mkdir -p "$DEST_ROOT"

# Лог-файл с таймстемпом
exec > >(tee -a "$DEST_ROOT/convert_$(date +%F_%T).log") 2>&1

find "$SOURCE_ROOT" -type d -name "VIDEO_TS" | while IFS= read -r VIDEO_TS_DIR; do
    DVD_NAME=$(basename "$(realpath "$VIDEO_TS_DIR"/..)")
    OUTPUT="$(realpath "$DEST_ROOT")/${DVD_NAME}.mp4"
    VOB_TEMP="/tmp/${DVD_NAME}_combined.vob"
    LOGFILE="$DEST_ROOT/${DVD_NAME}_ffmpeg.log"

    echo "📀 Обработка DVD: $DVD_NAME"
    echo "📁 VIDEO_TS: $VIDEO_TS_DIR"
    echo "🎯 Целевой файл: $OUTPUT"

    # Автоопределение самой длинной цепочки VTS
    MAIN_VTS=$(find "$VIDEO_TS_DIR" -name "VTS_*_*.VOB" -printf "%s %p\n" | sort -nr | head -1 | awk '{print $2}' | sed 's/_1\.VOB//')
    if [ -z "$MAIN_VTS" ]; then
        echo "⚠️ Не удалось определить основную цепочку VOB, пропускаем $DVD_NAME"
        continue
    fi

    echo "🔗 Объединение VOB-файлов: $(basename "$MAIN_VTS")_*"
    CHAIN_PREFIX=$(basename "$MAIN_VTS" | sed 's/_.*//')
    cat "$VIDEO_TS_DIR"/${CHAIN_PREFIX}_*.VOB > "$VOB_TEMP"


    # Проверка, что файл не пустой
    if [ ! -s "$VOB_TEMP" ]; then
        echo "⚠️ VOB-файл пустой, пропускаем $DVD_NAME"
        rm -f "$VOB_TEMP"
        continue
    fi

    echo "🔍 Проверка аудиопотока в $VOB_TEMP..."
    HAS_AUDIO=$(ffprobe -v error -select_streams a -show_entries stream=codec_name -of default=noprint_wrappers=1:nokey=1 "$VOB_TEMP")

    if [ -z "$HAS_AUDIO" ]; then
        echo "⚠️ Аудио не обнаружено, конвертация без аудио..."
        ffmpeg -y -hwaccel cuda -i "$VOB_TEMP" -c:v h264_nvenc -preset fast -an "$OUTPUT" 2>> "$LOGFILE"
    else
        echo "✅ Аудио найдено: $HAS_AUDIO"
        echo "🎬 Конвертация с видео и аудио..."
        ffmpeg -y -hwaccel cuda -i "$VOB_TEMP" -c:v h264_nvenc -preset fast -c:a aac -b:a 192k "$OUTPUT" 2>&1 | tee -a "$LOGFILE"
    fi

    # Проверка результата
    if [ -f "$OUTPUT" ]; then
        echo "📦 Готово: $OUTPUT"
        ls -lh "$OUTPUT"
    else
        echo "❌ Ошибка: MP4 не создан"
    fi

    rm -f "$VOB_TEMP"
    echo "-----------------------------"
done

Этот Bash-скрипт предназначен для автоматизированной пакетной конвертации DVD-структур (каталогов VIDEO_TS) в .mp4 файлы с использованием аппаратного ускорения NVENC. Он включает в себя обработку ошибок, логирование, проверку аудио и очистку временных файлов. Ниже — подробный анализ:


🧠 Общая задача

  • Найти все каталоги VIDEO_TS в текущем дереве.
  • Определить основную видеодорожку DVD.
  • Объединить .VOB файлы в один временный.
  • Проверить наличие аудио.
  • Конвертировать в .mp4 с использованием ffmpeg и NVENC.
  • Вести логирование и удалять временные файлы.

🔍 Подробный разбор

1. Безопасные настройки

set -e          # Прерывает выполнение при любой ошибке
set -u          # Ошибка при обращении к необъявленной переменной
set -o pipefail # Ошибка при сбое в любом этапе пайпа

2. Инициализация путей и логирования

SOURCE_ROOT="."
DEST_ROOT="."
mkdir -p "$DEST_ROOT"
exec > >(tee -a "$DEST_ROOT/convert_$(date +%F_%T).log") 2>&1
  • Работает в текущем каталоге.
  • Создаёт лог-файл с таймстемпом, перенаправляя stdout и stderr.

3. Поиск DVD-структур

find "$SOURCE_ROOT" -type d -name "VIDEO_TS"
  • Ищет каталоги VIDEO_TS, характерные для DVD.

4. Определение имени DVD и путей

DVD_NAME=$(basename "$(realpath "$VIDEO_TS_DIR"/..)")
OUTPUT="$(realpath "$DEST_ROOT")/${DVD_NAME}.mp4"
VOB_TEMP="/tmp/${DVD_NAME}_combined.vob"
LOGFILE="$DEST_ROOT/${DVD_NAME}_ffmpeg.log"
  • Имя DVD берётся из родительского каталога.
  • Формируются пути к выходному .mp4, временному .vob и лог-файлу.

5. Определение основной цепочки VOB

MAIN_VTS=$(find "$VIDEO_TS_DIR" -name "VTS_*_*.VOB" -printf "%s %p\n" | sort -nr | head -1 | awk '{print $2}' | sed 's/_1\.VOB//')
  • Ищет самый крупный .VOB файл, предполагая, что он часть основной видеодорожки.
  • Удаляет суффикс _1.VOB для получения префикса цепочки.

6. Объединение VOB-файлов

CHAIN_PREFIX=$(basename "$MAIN_VTS" | sed 's/_.*//')
cat "$VIDEO_TS_DIR"/${CHAIN_PREFIX}_*.VOB > "$VOB_TEMP"
  • Объединяет все .VOB файлы с общим префиксом в один временный файл.

7. Проверка на пустоту

if [ ! -s "$VOB_TEMP" ]; then
  • Пропускает обработку, если файл пустой.

8. Проверка наличия аудио

HAS_AUDIO=$(ffprobe ...)
  • Использует ffprobe для определения наличия аудиопотока.

9. Конвертация с ffmpeg

ffmpeg -y -hwaccel cuda -i "$VOB_TEMP" ...
  • Если аудио отсутствует: -an (без аудио).
  • Если аудио есть: кодирует в aac с битрейтом 192k.
  • Видео кодируется через h264_nvenc с пресетом fast.

10. Проверка результата

if [ -f "$OUTPUT" ]; then
  ls -lh "$OUTPUT"
else
  echo "❌ Ошибка: MP4 не создан" fi
  • Проверяет, был ли создан .mp4.
  • ⚠️ Здесь синтаксическая ошибка: fi стоит внутри else, должно быть: else echo "❌ Ошибка: MP4 не создан" fi

11. Очистка временного файла

rm -f "$VOB_TEMP"
  • Удаляет временный .vob файл после обработки.

✅ Вывод

Скрипт — мощный инструмент для пакетной обработки DVD:

  • Автоматически определяет основную видеодорожку.
  • Объединяет .VOB файлы.
  • Конвертирует с GPU-ускорением.
  • Ведёт подробный лог для каждой операции.
  • Удаляет временные файлы.

🛠 Рекомендации по улучшению

  • Добавить проверку на наличие ffmpeg и ffprobe.
  • Добавить опцию для выбора качества или кодека.
  • Возможность обработки нескольких аудиодорожек или субтитров.
Улучшенный скрипт
#!/bin/bash
set -e
set -u
set -o pipefail

# Проверка наличия ffmpeg и ffprobe
command -v ffmpeg >/dev/null 2>&1 || { echo "❌ ffmpeg не найден. Установите ffmpeg."; exit 1; }
command -v ffprobe >/dev/null 2>&1 || { echo "❌ ffprobe не найден. Установите ffprobe."; exit 1; }

# Настройки
SOURCE_ROOT="."
DEST_ROOT="."
mkdir -p "$DEST_ROOT"

# Параметры кодирования (можно переопределить при запуске)
VIDEO_CODEC="${VIDEO_CODEC:-h264_nvenc}"
PRESET="${PRESET:-fast}"
CRF="${CRF:-23}"

# Лог-файл с таймстемпом
exec > >(tee -a "$DEST_ROOT/convert_$(date +%F_%T).log") 2>&1

find "$SOURCE_ROOT" -type d -name "VIDEO_TS" | while IFS= read -r VIDEO_TS_DIR; do
    DVD_NAME=$(basename "$(realpath "$VIDEO_TS_DIR"/..)")
    OUTPUT="$(realpath "$DEST_ROOT")/${DVD_NAME}.mp4"
    VOB_TEMP="/tmp/${DVD_NAME}_combined.vob"
    LOGFILE="$DEST_ROOT/${DVD_NAME}_ffmpeg.log"

    echo "📀 Обработка DVD: $DVD_NAME"
    echo "📁 VIDEO_TS: $VIDEO_TS_DIR"
    echo "🎯 Целевой файл: $OUTPUT"

    MAIN_VTS=$(find "$VIDEO_TS_DIR" -name "VTS_*_*.VOB" -printf "%s %p\n" | sort -nr | head -1 | awk '{print $2}' | sed 's/_1\.VOB//')
    if [ -z "$MAIN_VTS" ]; then
        echo "⚠️ Не удалось определить основную цепочку VOB, пропускаем $DVD_NAME"
        continue
    fi

    CHAIN_PREFIX=$(basename "$MAIN_VTS" | sed 's/_.*//')
    cat "$VIDEO_TS_DIR"/${CHAIN_PREFIX}_*.VOB > "$VOB_TEMP"

    if [ ! -s "$VOB_TEMP" ]; then
        echo "⚠️ VOB-файл пустой, пропускаем $DVD_NAME"
        rm -f "$VOB_TEMP"
        continue
    fi

    echo "🔍 Проверка аудиопотока в $VOB_TEMP..."
    HAS_AUDIO=$(ffprobe -v error -select_streams a -show_entries stream=codec_name -of default=noprint_wrappers=1:nokey=1 "$VOB_TEMP")

    echo "🎬 Конвертация с параметрами: codec=$VIDEO_CODEC, preset=$PRESET, crf=$CRF"
    if [ -z "$HAS_AUDIO" ]; then
        echo "⚠️ Аудио не обнаружено, конвертация без аудио..."
        ffmpeg -y -hwaccel cuda -i "$VOB_TEMP" -map 0 -dn -c:v "$VIDEO_CODEC" -preset "$PRESET" -cq "$CRF" -an "$OUTPUT" 2>> "$LOGFILE"
    else
        echo "✅ Аудио найдено: $HAS_AUDIO"
        ffmpeg -y -hwaccel cuda -i "$VOB_TEMP" -map 0 -dn -c:v "$VIDEO_CODEC" -preset "$PRESET" -cq "$CRF" -c:a aac -b:a 192k "$OUTPUT" 2>&1 | tee -a "$LOGFILE"
    fi

    if [ -f "$OUTPUT" ]; then
        echo "📦 Готово: $OUTPUT"
        ls -lh "$OUTPUT"
    else
        echo "❌ Ошибка: MP4 не создан"
    fi

    rm -f "$VOB_TEMP"
    echo "-----------------------------"
done

✅ Решение: обновить драйвер NVIDIA

🔧 1. Проверка текущей версии драйвера

nvidia-smi

Посмотри строку Driver Version. Если ниже 570.0 — нужно обновить.


📦 2. Установка актуального драйвера

На Debian 12 проще всего использовать официальный .run-инсталлятор от NVIDIA:

Шаги:

  1. Перейди на официальную страницу драйверов NVIDIA
  2. Выбери:
    • Product Series: GeForce 10 Series
    • Product: GeForce GTX 1070
    • OS: Linux 64-bit
    • Download Type: Production Branch
  3. Скачай .run-файл (например, NVIDIA-Linux-x86_64-###.run)
  4. Перейди в tty (Ctrl+Alt+F3), останови X-сервер: sudo systemctl stop gdm
  5. Установи: sudo bash NVIDIA-Linux-x86_64-*.run
  6. Перезагрузи: sudo reboot

💡 Альтернатива: временно переключиться на libx264

Если обновление драйвера невозможно прямо сейчас — можно временно использовать CPU-кодек:

В скрипте замени:

VIDEO_CODEC="h264_nvenc"

на:

VIDEO_CODEC="libx264"

Или добавь проверку версии драйвера в скрипт — я могу помочь встроить это.

Алексей, сообщение Received signal SIGTERM; aborting. означает, что процесс установки драйвера NVIDIA был принудительно прерван — кто-то или что-то отправило сигнал SIGTERM, заставив инсталлятор завершиться досрочно.


🔍 Возможные причины

1. ❌ Активный графический интерфейс (X-сервер)

Инсталлятор .run требует, чтобы X-сервер был остановлен, иначе он может сам завершиться или быть прерван системой.

💡 Решение:

  • Перейди в текстовую консоль (Ctrl+Alt+F3)
  • Останови дисплей-менеджер: sudo systemctl stop gdm или, если используешь lightdm, sddm, xdm: sudo systemctl stop lightdm

2. 🔒 Запущен другой процесс, блокирующий установку

Например, apt, dpkg, или другой инсталлятор.

💡 Решение:

sudo fuser -v /var/lib/dpkg/lock
sudo fuser -v /var/lib/apt/lists/lock

Если есть процессы — завершить их:

sudo kill -9 <PID>

3. 🧱 Установлен драйвер из репозиториев Debian

Если уже установлен nvidia-driver через apt, он может конфликтовать с .run-инсталлятором.

💡 Решение:

sudo apt purge nvidia-driver
sudo apt autoremove

4. 🛡️ SELinux или AppArmor вмешиваются

Иногда системы безопасности могут прервать установку.

💡 Решение: временно отключить AppArmor:

sudo systemctl stop apparmor

✅ Рекомендованный порядок действий

  1. Перейти в tty: Ctrl+Alt+F3
  2. Войти как root
  3. Остановить графику: sudo systemctl stop gdm
  4. Убедиться, что X не работает: ps aux | grep X
  5. Запустить установку: bash NVIDIA-Linux-x86_64-580.82.09.run

Алексей, это сообщение от инсталлятора NVIDIA .run означает, что драйвер уже установлен — но не через этот установщик, а, скорее всего, через:

  • apt install nvidia-driver (репозиторий Debian)
  • dkms или module-assistant
  • другой .run-файл

Чтобы избежать конфликтов, NVIDIA рекомендует:


✅ Вариант 1: Обновить драйвер через тот же механизм

Если драйвер был установлен через apt, обнови его так:

sudo apt update
sudo apt install --only-upgrade nvidia-driver

Проверь версию:

nvidia-smi

Если она ≥ 570.0 — можно использовать NVENC API 13.0.


🧨 Вариант 2: Удалить текущий драйвер и установить вручную

Если хочешь перейти на .run-инсталлятор:

🔧 1. Удалить текущий драйвер

sudo apt purge '^nvidia-.*'
sudo apt autoremove

🔧 2. Перезагрузиться в текстовую консоль

sudo reboot

Затем войти в tty (Ctrl+Alt+F3), остановить графику:

sudo systemctl stop gdm

🔧 3. Установить .run-драйвер

sudo bash NVIDIA-Linux-x86_64-580.82.09.run

💡 Совет

Если ты не уверен, как драйвер был установлен — можешь показать вывод:

dpkg -l | grep nvidia

Алексей, ошибка:

ffprobe: error while loading shared libraries: libnppig.so.11: cannot open shared object file: No such file or directory

означает, что FFmpeg или ffprobe пытается использовать библиотеку NVIDIA Performance Primitives (NPP), но она не найдена в системе.


🔍 Что такое libnppig.so.11

  • Это часть CUDA Toolkit, конкретно — библиотеки libnpp* из libnpp-dev.
  • FFmpeg использует её, если был собран с флагом --enable-libnpp (что у тебя есть).
  • Версия .so.11 соответствует CUDA 11.x.

✅ Решения

🔧 Вариант 1: Установить libnpp из CUDA Toolkit

Если ты уже установил CUDA Toolkit, но не все компоненты:

sudo apt install libnpp-dev

Или, если ставил CUDA вручную — проверь наличие:

ls /usr/local/cuda/lib64/libnppig.so.11

Если файл есть — добавь путь в LD_LIBRARY_PATH:

export LD_LIBRARY_PATH=/usr/local/cuda/lib64:$LD_LIBRARY_PATH

Можно добавить в ~/.bashrc:

echo 'export LD_LIBRARY_PATH=/usr/local/cuda/lib64:$LD_LIBRARY_PATH' >> ~/.bashrc
source ~/.bashrc

🔧 Вариант 2: Установить нужную версию CUDA

Если libnppig.so.11 отсутствует — возможно, у тебя CUDA 12.x, а FFmpeg был собран с заголовками от CUDA 11.

💡 Решение:

  • Установи CUDA 11.8: wget https://developer.download.nvidia.com/compute/cuda/11.8.0/local_installers/cuda_11.8.0_520.61.05_linux.run sudo bash cuda_11.8.0_520.61.05_linux.run
  • Убедись, что libnppig.so.11 находится в /usr/local/cuda/lib64

🔧 Вариант 3: Пересобрать FFmpeg без --enable-libnpp

Если ты не используешь libnpp (например, для масштабирования), можно пересобрать FFmpeg без этой опции:

./configure ... --disable-libnpp
make -j$(nproc)
sudo make install

🧪 Проверка после исправления

ffprobe -version
ffmpeg -encoders | grep nvenc

Если всё работает — проблема решена.

Алексей, пакет libnpp-dev действительно отсутствует в репозиториях Debian — он не поставляется отдельно. Библиотеки libnppig.so.11 и другие libnpp* входят в состав CUDA Toolkit, и их нужно устанавливать вручную из официального .run-инсталлятора NVIDIA.


✅ Решение: установить CUDA Toolkit вручную

🔧 Шаг 1: Скачать CUDA 11.8 (совместим с libnppig.so.11)

wget https://developer.download.nvidia.com/compute/cuda/11.8.0/local_installers/cuda_11.8.0_520.61.05_linux.run

🔧 Шаг 2: Установить CUDA Toolkit

  1. Перейди в текстовую консоль (Ctrl+Alt+F3)
  2. Останови графику: sudo systemctl stop gdm
  3. Запусти установку: sudo bash cuda_11.8.0_520.61.05_linux.run

Во время установки выбери только Toolkit, без драйвера (если он уже установлен).


🔧 Шаг 3: Добавить библиотеки в LD_LIBRARY_PATH

echo 'export LD_LIBRARY_PATH=/usr/local/cuda/lib64:$LD_LIBRARY_PATH' >> ~/.bashrc
source ~/.bashrc

Или временно:

export LD_LIBRARY_PATH=/usr/local/cuda/lib64:$LD_LIBRARY_PATH

🔍 Шаг 4: Проверить наличие libnppig.so.11

ls /usr/local/cuda/lib64/libnppig.so.11

Если файл найден — FFmpeg и ffprobe должны работать.


💡 Альтернатива: пересобрать FFmpeg без --enable-libnpp

Если ты не используешь libnpp (например, для масштабирования на GPU), можно пересобрать FFmpeg без этой опции:

./configure ... --disable-libnpp
make -j$(nproc)
sudo make install

Алексей, ошибка вызвана тем, что FFmpeg пытается сохранить служебный поток DVD (dvd_nav_packet) в выходной .mp4 файл, но формат MP4 не поддерживает такие потоки. Вот ключевая строка:

Could not find tag for codec dvd_nav_packet in stream #0, codec not currently supported in container

✅ Решение: исключить служебный поток из конвертации

🔧 Что происходит

  • Stream #0:0 — это dvd_nav_packet, служебные данные навигации DVD.
  • В скрипте используется: -map 0:v -map 0:a — что захватывает все видео и аудио, но не исключает служебные потоки.

🛠 Исправление: изменить -map в скрипте

Замените строку:

-map 0:v -map 0:a

на:

-map 0:1 -map 0:2

Это явно указывает:

  • 0:1 — видео MPEG2
  • 0:2 — аудио MP2

И пропускает 0:0, который содержит dvd_nav_packet.


💡 Альтернатива: использовать -map 0 с -dn

Если структура потоков может меняться, можно использовать:

-map 0 -dn

Флаг -dn отключает data streams, включая служебные DVD-пакеты.


🔁 Пример исправленной команды

ffmpeg -y $HWACCEL -i "$INPUT" \
  -map 0:1 -map 0:2 \
  -vf format=yuv420p \
  -c:v "$VIDEO_CODEC" -preset "$PRESET" $QUALITY_PARAM \
  -c:a aac -b:a "$AUDIO_BITRATE" \
  "$TEMP_FILE"

или универсально:

ffmpeg -y $HWACCEL -i "$INPUT" \
  -map 0 -dn \
  -vf format=yuv420p \
  -c:v "$VIDEO_CODEC" -preset "$PRESET" $QUALITY_PARAM \
  -c:a aac -b:a "$AUDIO_BITRATE" \
  "$TEMP_FILE"

Алексей, чтобы устранить ошибку с dvd_nav_packet, нужно заменить -map 0 на -map 0 -dn в обеих командах ffmpeg. Это исключит служебные потоки (data streams), которые не поддерживаются в формате MP4.


✏️ Вот как нужно изменить фрагмент скрипта:

echo "🎬 Конвертация с параметрами: codec=$VIDEO_CODEC, preset=$PRESET, crf=$CRF"
if [ -z "$HAS_AUDIO" ]; then
    echo "⚠️ Аудио не обнаружено, конвертация без аудио..."
    ffmpeg -y -hwaccel cuda -i "$VOB_TEMP" -map 0 -dn \
        -c:v "$VIDEO_CODEC" -preset "$PRESET" -cq "$CRF" -an "$OUTPUT" 2>> "$LOGFILE"
else
    echo "✅ Аудио найдено: $HAS_AUDIO"
    ffmpeg -y -hwaccel cuda -i "$VOB_TEMP" -map 0 -dn \
        -c:v "$VIDEO_CODEC" -preset "$PRESET" -cq "$CRF" \
        -c:a aac -b:a 192k "$OUTPUT" 2>&1 | tee -a "$LOGFILE"
fi

🔍 Что делает -dn

  • -dn = disable data streams
  • Это исключает потоки типа Data: dvd_nav_packet, которые не поддерживаются в MP4 и вызывают ошибку.

Если структура входных файлов всегда одинакова (например, 0:1 — видео, 0:2 — аудио), можно вместо -map 0 -dn использовать явное указание:

-map 0:1 -map 0:2

Но -map 0 -dn более универсален и безопасен для разных DVD-структур.

Да, Алексей — ты всё сделал правильно 💯

Вот что ты уже учёл:


✅ Что работает в твоём фрагменте

  • -map 0 -dn — исключает служебные потоки типа dvd_nav_packet, которые мешали сохранению в MP4.
  • Условие if [ -z "$HAS_AUDIO" ] — корректно определяет наличие аудио.
  • Использование -an при отсутствии аудио — верно.
  • Логирование через tee -a "$LOGFILE" — удобно для отладки.
  • Очистка временного файла rm -f "$VOB_TEMP" — аккуратно.

💡 Мелкие улучшения (по желанию)

Если хочешь чуть больше надёжности:

1. Проверка успешности ffmpeg

Можно добавить проверку $? после ffmpeg:

if [ $? -eq 0 ] && [ -f "$OUTPUT" ]; then
    echo "📦 Готово: $OUTPUT"
    ls -lh "$OUTPUT"
else
    echo "❌ Ошибка: MP4 не создан"
fi

2. Логировать структуру входного файла (для отладки)

Добавь перед конвертацией:

ffprobe -hide_banner "$VOB_TEMP" >> "$LOGFILE"