Create config files with permissions based on umask rather than the hardcoded ones created by python's tempfile module

This commit is contained in:
Kovid Goyal 2022-03-09 11:01:21 +05:30
parent 65219abb3d
commit 7acaee07d0
No known key found for this signature in database
GPG Key ID: 06BC317B515ACE7C
2 changed files with 26 additions and 4 deletions

View File

@ -1,6 +1,7 @@
#!/usr/bin/env python
# License: GPLv3 Copyright: 2015, Kovid Goyal <kovid at kovidgoyal.net>
from polyglot.builtins import environ_item, hasenv
from functools import lru_cache
import sys, locale, codecs, os, collections, collections.abc
__appname__ = 'calibre'
@ -445,3 +446,16 @@ def get_windows_number_formats():
def trash_name():
return _('Trash') if ismacos else _('Recycle Bin')
@lru_cache(maxsize=2)
def get_umask():
mask = os.umask(0o666)
os.umask(mask)
return mask
# call this at startup as it changed process global state, which doesnt work
# with multi-threading. It's absurd there is no way to safely read the current
# umask of a process.
get_umask()

View File

@ -4,13 +4,19 @@ __license__ = 'GPL v3'
__copyright__ = '2011, Kovid Goyal <kovid@kovidgoyal.net>'
__docformat__ = 'restructuredtext en'
import os, re, traceback, numbers
from contextlib import suppress
from functools import partial
import numbers
import os
import re
import traceback
from collections import defaultdict
from contextlib import suppress
from copy import deepcopy
from functools import partial
from calibre.constants import config_dir, CONFIG_DIR_MODE, preferred_encoding, filesystem_encoding, iswindows
from calibre.constants import (
CONFIG_DIR_MODE, config_dir, filesystem_encoding, get_umask, iswindows,
preferred_encoding
)
from polyglot.builtins import iteritems
plugin_dir = os.path.join(config_dir, 'plugins')
@ -376,6 +382,8 @@ def commit_data(file_path, data):
os.makedirs(bdir, exist_ok=True, mode=CONFIG_DIR_MODE)
try:
with tempfile.NamedTemporaryFile(dir=bdir, prefix=os.path.basename(file_path).split('.')[0] + '-atomic-', delete=False) as f:
if hasattr(os, 'fchmod'):
os.fchmod(f.fileno(), 0o666 & ~get_umask())
f.write(data)
retry_on_fail(os.replace, f.name, file_path)
finally: