From dc8e621d7c3dab6e75c428d3e9f4f5ba84d2ae1b Mon Sep 17 00:00:00 2001 From: ed Date: Sun, 7 Jan 2024 17:52:10 +0000 Subject: [PATCH] increase OOM kill-score for FFmpeg and mtp's; discourage Linux from killing innocent processes when FFmpeg decides to allocate 1 TiB of RAM --- copyparty/mtag.py | 3 ++- copyparty/th_srv.py | 10 +++++----- copyparty/util.py | 10 ++++++++++ 3 files changed, 17 insertions(+), 6 deletions(-) diff --git a/copyparty/mtag.py b/copyparty/mtag.py index c71e45d6..e32d0ece 100644 --- a/copyparty/mtag.py +++ b/copyparty/mtag.py @@ -118,7 +118,7 @@ def ffprobe( b"--", fsenc(abspath), ] - rc, so, se = runcmd(cmd, timeout=timeout, nice=True) + rc, so, se = runcmd(cmd, timeout=timeout, nice=True, oom=200) retchk(rc, cmd, se) return parse_ffprobe(so) @@ -564,6 +564,7 @@ class MTag(object): args = { "env": env, "nice": True, + "oom": 300, "timeout": parser.timeout, "kill": parser.kill, "capture": parser.capture, diff --git a/copyparty/th_srv.py b/copyparty/th_srv.py index 129e3251..64f24f0e 100644 --- a/copyparty/th_srv.py +++ b/copyparty/th_srv.py @@ -467,9 +467,9 @@ class ThumbSrv(object): cmd += [fsenc(tpath)] self._run_ff(cmd, vn) - def _run_ff(self, cmd: list[bytes], vn: VFS) -> None: + def _run_ff(self, cmd: list[bytes], vn: VFS, oom: int = 400) -> None: # self.log((b" ".join(cmd)).decode("utf-8")) - ret, _, serr = runcmd(cmd, timeout=vn.flags["convt"], nice=True) + ret, _, serr = runcmd(cmd, timeout=vn.flags["convt"], nice=True, oom=oom) if not ret: return @@ -623,7 +623,7 @@ class ThumbSrv(object): fsenc(tmp_opus) ] # fmt: on - self._run_ff(cmd, vn) + self._run_ff(cmd, vn, oom=300) # iOS fails to play some "insufficiently complex" files # (average file shorter than 8 seconds), so of course we @@ -647,7 +647,7 @@ class ThumbSrv(object): fsenc(tpath) ] # fmt: on - self._run_ff(cmd, vn) + self._run_ff(cmd, vn, oom=300) elif want_caf: # simple remux should be safe @@ -665,7 +665,7 @@ class ThumbSrv(object): fsenc(tpath) ] # fmt: on - self._run_ff(cmd, vn) + self._run_ff(cmd, vn, oom=300) if tmp_opus != tpath: try: diff --git a/copyparty/util.py b/copyparty/util.py index 6bfe0b34..b97f514c 100644 --- a/copyparty/util.py +++ b/copyparty/util.py @@ -2557,6 +2557,7 @@ def runcmd( argv: Union[list[bytes], list[str]], timeout: Optional[float] = None, **ka: Any ) -> tuple[int, str, str]: isbytes = isinstance(argv[0], (bytes, bytearray)) + oom = ka.pop("oom", 0) # 0..1000 kill = ka.pop("kill", "t") # [t]ree [m]ain [n]one capture = ka.pop("capture", 3) # 0=none 1=stdout 2=stderr 3=both @@ -2587,6 +2588,14 @@ def runcmd( argv = [NICES] + argv p = sp.Popen(argv, stdout=cout, stderr=cerr, **ka) + + if oom and not ANYWIN and not MACOS: + try: + with open("/proc/%d/oom_score_adj" % (p.pid,), "wb") as f: + f.write(("%d\n" % (oom,)).encode("utf-8")) + except: + pass + if not timeout or PY2: bout, berr = p.communicate(sin) else: @@ -2734,6 +2743,7 @@ def _parsehook( sp_ka = { "env": env, "nice": True, + "oom": 300, "timeout": tout, "kill": kill, "capture": cap,