From 79e19229af08541ab43c39b57e6da9d6c8a48f94 Mon Sep 17 00:00:00 2001 From: FlintyLemming Date: Sat, 28 Feb 2026 11:19:11 +0800 Subject: [PATCH] =?UTF-8?q?=F0=9F=90=9B=20fix(av1-transfer):=20use=20preex?= =?UTF-8?q?ec=5Ffn+os.execvp=20to=20rename=20ffmpeg=20argv[0]?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit execve with explicit paths fails on this system (linuxbrew symlink issue). os.execvp in preexec_fn uses PATH lookup which works, and since it replaces the child process before subprocess's own exec runs, pipes are inherited correctly. Co-Authored-By: Claude Sonnet 4.6 --- av1-transfer/main.py | 20 +++++++++++--------- 1 file changed, 11 insertions(+), 9 deletions(-) diff --git a/av1-transfer/main.py b/av1-transfer/main.py index 6c021e2..fff68b3 100644 --- a/av1-transfer/main.py +++ b/av1-transfer/main.py @@ -19,8 +19,8 @@ AV1 视频批量转码脚本 import argparse import ctypes import ctypes.util +import os import queue -import shlex import shutil import subprocess import sys @@ -130,21 +130,23 @@ def transcode_one_file(file_info, overall_bar, slot_bars, slot_queue, process_na str(output_path), ] + str_args = [str(a) for a in ffmpeg_args] if process_name: - # 用 bash 的 exec -a 重命名 ffmpeg 进程的 argv[0] - # ffmpeg 通过 PATH 查找,避免 execve 直接调用 symlink 的兼容问题 - shell_args = " ".join(shlex.quote(str(a)) for a in ffmpeg_args) - sh = shutil.which("sh") or shutil.which("bash") or "/usr/bin/sh" + # fork 后、subprocess 执行 exec 之前,用 os.execvp 替换进程: + # - execvp 通过 PATH 查找 ffmpeg(规避 execve 直接调用 symlink 的问题) + # - argv[0] 设为别名,ps/top 显示别名而非 ffmpeg + # - subprocess 设好的 stdout/stderr pipe 已继承,无需额外处理 + _pname = process_name + _args = str_args proc = subprocess.Popen( - f"exec -a {shlex.quote(process_name)} ffmpeg {shell_args}", - shell=True, - executable=sh, + ["ffmpeg"] + str_args, + preexec_fn=lambda: os.execvp("ffmpeg", [_pname] + _args), stdout=subprocess.PIPE, stderr=subprocess.PIPE, ) else: proc = subprocess.Popen( - ["ffmpeg"] + ffmpeg_args, + ["ffmpeg"] + str_args, stdout=subprocess.PIPE, stderr=subprocess.PIPE, )