From 93e49bf2f20e3d6fde8c466b0a4fabbc189fda1c Mon Sep 17 00:00:00 2001 From: lars Date: Fri, 26 Jan 2007 00:18:22 +0000 Subject: [PATCH] mount tmpfs if no config partition is available (Closes: #117) --- bin/CryptoBoxRootActions | 21 ++++++--- src/cryptobox/core/settings.py | 82 ++++++++++++++++++++++++---------- 2 files changed, 75 insertions(+), 28 deletions(-) diff --git a/bin/CryptoBoxRootActions b/bin/CryptoBoxRootActions index a8d11a5..96faec6 100755 --- a/bin/CryptoBoxRootActions +++ b/bin/CryptoBoxRootActions @@ -54,6 +54,8 @@ OVERRIDE_FILECHECK = False DEV_TYPES = { "pipe":1, "char":2, "dir":4, "block":6, "file":8, "link":10, "socket":12} EVENT_MARKER = '_event_scripts_' +## use this string as device name if you want to mount a ramdisk +MAGIC_TMPFS = "_tmpfs_" def checkIfFileIsSafe(fname): @@ -274,8 +276,10 @@ def run_mount(args): del args[0] destination = args[0] del args[0] + ## shall we mount a ramdisk? + is_tmpfs = (device == MAGIC_TMPFS) # check permissions for the device - if not isWriteable(device, DEV_TYPES["block"]): + if (not is_tmpfs) and (not isWriteable(device, DEV_TYPES["block"])): raise "WrongArguments", "%s is not a writeable block device" % (device, ) ## check permissions for the mountpoint if not isWriteable(destination, DEV_TYPES["dir"]): @@ -296,17 +300,24 @@ def run_mount(args): ## first: get the user/group of the target (trustUserName, trustUID, groupsOfTrustUser) = getUserInfo(savedUID) trustGID = groupsOfTrustUser[0] - fsType = getFSType(device) + if is_tmpfs: + fsType = "tmpfs" + else: + fsType = getFSType(device) ## define arguments if fsType == "vfat": ## add the "uid/gid" arguments to the mount call - mount_args = [allowedProgs["mount"], + mount_args = [ allowedProgs["mount"], "-o", "uid=%d,gid=%d,umask=0000" % (trustUID, trustGID), device, - destination] + destination ] + elif is_tmpfs: + mount_args = [ allowedProgs["mount"], + "-t", "tmpfs", + "cryptobox-tmpfs", destination ] else: ## all other filesystem types will be handled after mount - mount_args = [allowedProgs["mount"], device, destination] + mount_args = [ allowedProgs["mount"], device, destination ] # execute mount proc = subprocess.Popen( shell = False, diff --git a/src/cryptobox/core/settings.py b/src/cryptobox/core/settings.py index 5e2a3af..74eb212 100644 --- a/src/cryptobox/core/settings.py +++ b/src/cryptobox/core/settings.py @@ -46,6 +46,7 @@ class CryptoBoxSettings: """ def __init__(self, config_file=None): + self.__is_initialized = False self.log = logging.getLogger("CryptoBox") config_file = self.__get_config_filename(config_file) self.log.info("loading config file: %s" % config_file) @@ -59,6 +60,7 @@ class CryptoBoxSettings: self.user_db = self.__get_user_db() self.misc_files = [] self.reload_misc_files() + self.__is_initialized = True def reload_misc_files(self): @@ -137,6 +139,10 @@ class CryptoBoxSettings: for line in file("/proc/mounts"): fields = line.split(" ") mount_dir = fields[1] + fs_type = fields[2] + if fs_type == "tmpfs": + ## skip ramdisks - these are not really "active partitions" + continue try: if os.path.samefile(mount_dir, settings_dir): return fields[0] @@ -158,36 +164,67 @@ class CryptoBoxSettings: + "mounted - not mounting again") return False conf_partitions = self.get_available_partitions() + mount_dir = self.prefs["Locations"]["SettingsDir"] if not conf_partitions: + ## return, if tmpfs is already mounted + if os.path.ismount(mount_dir): + self.log.info("A ramdisk seems to be already mounted as a config " \ + + "partition - doing nothing ...") + ## return without any actions + return True self.log.warn("no configuration partition found - you have to create " + "it first") - #TODO: mount tmpfs in settings directory + ## mount tmpfs instead to provide a place for storing stuff + ## "_tmpfs_" as parameter for mount is interpreted as a magic word + ## by CryptoBoxRootActions + proc = subprocess.Popen( + shell = False, + stdout = subprocess.PIPE, + stderr = subprocess.PIPE, + args = [ + self.prefs["Programs"]["super"], + self.prefs["Programs"]["CryptoBoxRootActions"], + "mount", + "_tmpfs_", + mount_dir ]) + (stdout, stderr) = proc.communicate() + if proc.returncode != 0: + self.log.error("Failed to mount a ramdisk for storing settings: %s" \ + % stderr) + return False self.log.info("Ramdisk (tmpfs) mounted as config partition ...") - return False - partition = conf_partitions[0] - proc = subprocess.Popen( - shell = False, - stdout = subprocess.PIPE, - stderr = subprocess.PIPE, - args = [ - self.prefs["Programs"]["super"], - self.prefs["Programs"]["CryptoBoxRootActions"], - "mount", - partition, - self.prefs["Locations"]["SettingsDir"]]) - (stdout, stderr) = proc.communicate() - if proc.returncode != 0: - self.log.error("failed to mount the configuration partition: %s" % partition) - self.log.error("output of mount: %s" % (stderr,)) - return False - self.log.info("configuration partition mounted: %s" % partition) + else: + partition = conf_partitions[0] + ## umount tmpfs in case it is active + if os.path.ismount(mount_dir): + self.umount_partition() + proc = subprocess.Popen( + shell = False, + stdout = subprocess.PIPE, + stderr = subprocess.PIPE, + args = [ + self.prefs["Programs"]["super"], + self.prefs["Programs"]["CryptoBoxRootActions"], + "mount", + partition, + mount_dir ]) + (stdout, stderr) = proc.communicate() + if proc.returncode != 0: + self.log.error("Failed to mount the configuration partition (%s): %s" % \ + (partition, stderr)) + return False + self.log.info("configuration partition mounted: %s" % partition) + ## write config files (not during first initialization of this object) + if self.__is_initialized: + self.write() return True def umount_partition(self): """Umount the currently active configuration partition. """ - if not self.get_active_partition(): + mount_dir = self.prefs["Locations"]["SettingsDir"] + if not os.path.ismount(mount_dir): self.log.warn("umountConfigPartition: no configuration partition mounted") return False self.reload_misc_files() @@ -199,11 +236,10 @@ class CryptoBoxSettings: self.prefs["Programs"]["super"], self.prefs["Programs"]["CryptoBoxRootActions"], "umount", - self.prefs["Locations"]["SettingsDir"]]) + mount_dir ]) (stdout, stderr) = proc.communicate() if proc.returncode != 0: - self.log.error("failed to unmount the configuration partition") - self.log.error("output of mount: %s" % (stderr,)) + self.log.error("Failed to unmount the configuration partition: %s" % stderr) return False self.log.info("configuration partition unmounted") return True