Fix atexit handlers being called in forked children
In particular the atexit handler for random_unix_socket()
This commit is contained in:
parent
92bbf08343
commit
806ca2b224
@ -29,7 +29,7 @@ from kitty.fast_data_types import (
|
|||||||
from kitty.options.types import Options
|
from kitty.options.types import Options
|
||||||
from kitty.shm import SharedMemory
|
from kitty.shm import SharedMemory
|
||||||
from kitty.types import SignalInfo
|
from kitty.types import SignalInfo
|
||||||
from kitty.utils import log_error, random_unix_socket
|
from kitty.utils import log_error, random_unix_socket, safer_fork
|
||||||
|
|
||||||
if TYPE_CHECKING:
|
if TYPE_CHECKING:
|
||||||
from _typeshed import ReadableBuffer, WriteableBuffer
|
from _typeshed import ReadableBuffer, WriteableBuffer
|
||||||
@ -53,11 +53,6 @@ class Child:
|
|||||||
child_process_pid: int
|
child_process_pid: int
|
||||||
|
|
||||||
|
|
||||||
def reinit_openssl_prng() -> None:
|
|
||||||
import ssl
|
|
||||||
ssl.RAND_add(os.urandom(64), 0.0)
|
|
||||||
|
|
||||||
|
|
||||||
def wait_for_child_death(child_pid: int, timeout: float = 1) -> Optional[int]:
|
def wait_for_child_death(child_pid: int, timeout: float = 1) -> Optional[int]:
|
||||||
st = time.monotonic()
|
st = time.monotonic()
|
||||||
while time.monotonic() - st < timeout:
|
while time.monotonic() - st < timeout:
|
||||||
@ -317,7 +312,7 @@ def fork(shm_address: str, free_non_child_resources: Callable[[], None]) -> Tupl
|
|||||||
r, w = safe_pipe()
|
r, w = safe_pipe()
|
||||||
ready_fd_read, ready_fd_write = safe_pipe()
|
ready_fd_read, ready_fd_write = safe_pipe()
|
||||||
try:
|
try:
|
||||||
child_pid = os.fork()
|
child_pid = safer_fork()
|
||||||
except OSError:
|
except OSError:
|
||||||
os.close(r)
|
os.close(r)
|
||||||
os.close(w)
|
os.close(w)
|
||||||
@ -331,7 +326,6 @@ def fork(shm_address: str, free_non_child_resources: Callable[[], None]) -> Tupl
|
|||||||
# master process
|
# master process
|
||||||
os.close(w)
|
os.close(w)
|
||||||
os.close(ready_fd_read)
|
os.close(ready_fd_read)
|
||||||
reinit_openssl_prng()
|
|
||||||
poll = select.poll()
|
poll = select.poll()
|
||||||
poll.register(r, select.POLLIN)
|
poll.register(r, select.POLLIN)
|
||||||
tuple(poll.poll())
|
tuple(poll.poll())
|
||||||
@ -445,11 +439,10 @@ class SocketChild:
|
|||||||
def fork(self, free_non_child_resources: Callable[[], None]) -> None:
|
def fork(self, free_non_child_resources: Callable[[], None]) -> None:
|
||||||
global is_zygote
|
global is_zygote
|
||||||
r, w = safe_pipe()
|
r, w = safe_pipe()
|
||||||
self.pid = os.fork()
|
self.pid = safer_fork()
|
||||||
if self.pid > 0:
|
if self.pid > 0:
|
||||||
# master process
|
# master process
|
||||||
os.close(w)
|
os.close(w)
|
||||||
reinit_openssl_prng()
|
|
||||||
if self.stdin > -1:
|
if self.stdin > -1:
|
||||||
os.close(self.stdin)
|
os.close(self.stdin)
|
||||||
self.stdin = -1
|
self.stdin = -1
|
||||||
@ -803,10 +796,9 @@ def fork_prewarm_process(opts: Options, use_exec: bool = False) -> Optional[Prew
|
|||||||
else:
|
else:
|
||||||
unix_socket = random_unix_socket()
|
unix_socket = random_unix_socket()
|
||||||
socket_name = get_socket_name(unix_socket)
|
socket_name = get_socket_name(unix_socket)
|
||||||
child_pid = os.fork()
|
child_pid = safer_fork()
|
||||||
if child_pid:
|
if child_pid:
|
||||||
# master
|
# master
|
||||||
reinit_openssl_prng()
|
|
||||||
if not use_exec:
|
if not use_exec:
|
||||||
unix_socket.close()
|
unix_socket.close()
|
||||||
os.close(stdin_read)
|
os.close(stdin_read)
|
||||||
|
|||||||
@ -1056,3 +1056,16 @@ def is_pid_alive(pid: int) -> bool:
|
|||||||
except Exception:
|
except Exception:
|
||||||
pass
|
pass
|
||||||
return True
|
return True
|
||||||
|
|
||||||
|
|
||||||
|
def safer_fork() -> int:
|
||||||
|
pid = os.fork()
|
||||||
|
if pid:
|
||||||
|
# master
|
||||||
|
import ssl
|
||||||
|
ssl.RAND_add(os.urandom(32), 0.0)
|
||||||
|
else:
|
||||||
|
# child
|
||||||
|
import atexit
|
||||||
|
atexit._clear()
|
||||||
|
return pid
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user