fixed wrong redirection after reboot (causing reboot loop)
clarified interpretation of blkid output added missing success message to volume_format_fs execute formatting in the background mark busy devices as such fixed a small bug in CryptoBoxRootActions
|
@ -74,6 +74,7 @@ def checkIfPluginIsValid(plugin):
|
||||||
import imp
|
import imp
|
||||||
try:
|
try:
|
||||||
x = imp.load_source("cbox_plugin",plugin)
|
x = imp.load_source("cbox_plugin",plugin)
|
||||||
|
#TODO: no wildcard catches, please!
|
||||||
except Exception:
|
except Exception:
|
||||||
return False
|
return False
|
||||||
try:
|
try:
|
||||||
|
@ -87,7 +88,7 @@ def checkIfPluginIsValid(plugin):
|
||||||
|
|
||||||
def checkIfEventScriptIsValid(plugin):
|
def checkIfEventScriptIsValid(plugin):
|
||||||
event_dir = os.path.dirname(plugin)
|
event_dir = os.path.dirname(plugin)
|
||||||
if os.path.exists(os.path.join(event_dir,EVENT_MARKER)):
|
if os.path.exists(os.path.join(event_dir, EVENT_MARKER)):
|
||||||
return True
|
return True
|
||||||
else:
|
else:
|
||||||
return False
|
return False
|
||||||
|
@ -106,7 +107,7 @@ def call_plugin(args):
|
||||||
## check if the plugin is a python program, that is marked as a cryptobox plugin
|
## check if the plugin is a python program, that is marked as a cryptobox plugin
|
||||||
if not checkIfPluginIsValid(plugin):
|
if not checkIfPluginIsValid(plugin):
|
||||||
raise Exception, "the plugin (%s) is not a correctly marked python script" % plugin
|
raise Exception, "the plugin (%s) is not a correctly marked python script" % plugin
|
||||||
args.insert(0,plugin)
|
args.insert(0, plugin)
|
||||||
proc = subprocess.Popen(
|
proc = subprocess.Popen(
|
||||||
shell = False,
|
shell = False,
|
||||||
args = args)
|
args = args)
|
||||||
|
@ -122,12 +123,12 @@ def call_event(args):
|
||||||
if not os.access(event, os.X_OK):
|
if not os.access(event, os.X_OK):
|
||||||
raise Exception, "could not find executable event script (%s)" % event
|
raise Exception, "could not find executable event script (%s)" % event
|
||||||
## check if the script is valid (the marker file must be in the same directory)
|
## check if the script is valid (the marker file must be in the same directory)
|
||||||
if not checkIfEventScriptIsValid(plugin):
|
if not checkIfEventScriptIsValid(event):
|
||||||
raise Exception, "the event script (%s) does not reside in a directory with the marker file (%s) - this is not allowed due to abuse prevention" % (plugin,EVENT_MARKER)
|
raise Exception, "the event script (%s) does not reside in a directory with the marker file (%s) - this is not allowed due to abuse prevention" % (event, EVENT_MARKER)
|
||||||
## check if the event (and its parents) are only writeable for root
|
## check if the event (and its parents) are only writeable for root
|
||||||
if not checkIfFileIsSafe(event):
|
if not checkIfFileIsSafe(event):
|
||||||
raise Exception, "the event (%s) is not safe - check its (and its parents') permissions" % event
|
raise Exception, "the event (%s) is not safe - check its (and its parents') permissions" % event
|
||||||
args.insert(0,event)
|
args.insert(0, event)
|
||||||
proc = subprocess.Popen(
|
proc = subprocess.Popen(
|
||||||
shell = False,
|
shell = False,
|
||||||
args = args)
|
args = args)
|
||||||
|
@ -201,7 +202,7 @@ def run_cryptsetup(args):
|
||||||
cmd_args.append(action)
|
cmd_args.append(action)
|
||||||
cmd_args.append(device)
|
cmd_args.append(device)
|
||||||
elif action == "luksDelKey":
|
elif action == "luksDelKey":
|
||||||
if len(cs_args) < 2: raise "WrongArguments", "missing arguments"
|
if len(args) < 2: raise "WrongArguments", "missing arguments"
|
||||||
device = args[0]; del args[0]
|
device = args[0]; del args[0]
|
||||||
cmd_args.insert(-1, action)
|
cmd_args.insert(-1, action)
|
||||||
cmd_args.insert(-1, device)
|
cmd_args.insert(-1, device)
|
||||||
|
@ -361,7 +362,7 @@ def getUserInfo(user):
|
||||||
except TypeError:
|
except TypeError:
|
||||||
# if a KeyError is raised again, then the supplied user was invalid
|
# if a KeyError is raised again, then the supplied user was invalid
|
||||||
userinfo = pwd.getpwnam(user)
|
userinfo = pwd.getpwnam(user)
|
||||||
u_groups =[one_group.gr_gid
|
u_groups = [one_group.gr_gid
|
||||||
for one_group in grp.getgrall()
|
for one_group in grp.getgrall()
|
||||||
if userinfo.pw_name in one_group.gr_mem]
|
if userinfo.pw_name in one_group.gr_mem]
|
||||||
if not userinfo.pw_gid in u_groups: u_groups.append(userinfo.pw_gid)
|
if not userinfo.pw_gid in u_groups: u_groups.append(userinfo.pw_gid)
|
||||||
|
|
|
@ -76,11 +76,12 @@ Languages = en, de, sl, fr
|
||||||
|
|
||||||
[Programs]
|
[Programs]
|
||||||
cryptsetup = /sbin/cryptsetup
|
cryptsetup = /sbin/cryptsetup
|
||||||
mkfs-data = /sbin/mkfs.ext3
|
mkfs = /sbin/mkfs
|
||||||
blkid = /sbin/blkid
|
blkid = /sbin/blkid
|
||||||
blockdev = /sbin/blockdev
|
blockdev = /sbin/blockdev
|
||||||
mount = /bin/mount
|
mount = /bin/mount
|
||||||
umount = /bin/umount
|
umount = /bin/umount
|
||||||
|
nice = /usr/bin/nice
|
||||||
super = /usr/bin/super
|
super = /usr/bin/super
|
||||||
# this is the "program" name as defined in /etc/super.tab
|
# this is the "program" name as defined in /etc/super.tab
|
||||||
CryptoBoxRootActions = CryptoBoxRootActions
|
CryptoBoxRootActions = CryptoBoxRootActions
|
||||||
|
|
|
@ -1,17 +0,0 @@
|
||||||
[global]
|
|
||||||
server.socketPort = 8080
|
|
||||||
#server.environment = "production"
|
|
||||||
server.environment = "development"
|
|
||||||
server.logToScreen = True
|
|
||||||
server.log_tracebacks = True
|
|
||||||
server.threadPool = 1
|
|
||||||
server.reverseDNS = False
|
|
||||||
server.logFile = "cryptoboxwebserver.log"
|
|
||||||
|
|
||||||
[/favicon.ico]
|
|
||||||
static_filter.on = True
|
|
||||||
# TODO: use live-cd/live-cd-tree.d/var/www/favicon.ico
|
|
||||||
static_filter.file = "/usr/share/doc/python-cherrypy/cherrypy/favicon.ico"
|
|
||||||
|
|
||||||
[/test_stream]
|
|
||||||
stream_response = True
|
|
|
@ -75,11 +75,12 @@ Languages = de, en, fr
|
||||||
|
|
||||||
[Programs]
|
[Programs]
|
||||||
cryptsetup = /sbin/cryptsetup
|
cryptsetup = /sbin/cryptsetup
|
||||||
mkfs-data = /sbin/mkfs.ext3
|
mkfs = /sbin/mkfs
|
||||||
blkid = /sbin/blkid
|
blkid = /sbin/blkid
|
||||||
blockdev = /sbin/blockdev
|
blockdev = /sbin/blockdev
|
||||||
mount = /bin/mount
|
mount = /bin/mount
|
||||||
umount = /bin/umount
|
umount = /bin/umount
|
||||||
|
nice = /usr/bin/nice
|
||||||
super = /usr/bin/super
|
super = /usr/bin/super
|
||||||
# this is the "program" name as defined in /etc/super.tab
|
# this is the "program" name as defined in /etc/super.tab
|
||||||
CryptoBoxRootActions = CryptoBoxRootActions
|
CryptoBoxRootActions = CryptoBoxRootActions
|
||||||
|
|
|
@ -1,3 +1,10 @@
|
||||||
|
cryptobox (0.2.52-1) unstable; urgency=low
|
||||||
|
|
||||||
|
* format partitions in background
|
||||||
|
* mark busy partitions
|
||||||
|
|
||||||
|
-- Lars Kruse <devel@sumpfralle.de> Wed, 6 Dec 2006 14:57:43 +0100
|
||||||
|
|
||||||
cryptobox (0.2.51-1) unstable; urgency=low
|
cryptobox (0.2.51-1) unstable; urgency=low
|
||||||
|
|
||||||
* favicon included
|
* favicon included
|
||||||
|
|
|
@ -28,6 +28,7 @@ import os
|
||||||
import logging
|
import logging
|
||||||
import cryptobox.core.tools as cbxTools
|
import cryptobox.core.tools as cbxTools
|
||||||
import cryptobox.plugins.base
|
import cryptobox.plugins.base
|
||||||
|
from cryptobox.core.exceptions import *
|
||||||
|
|
||||||
|
|
||||||
PARTTYPES = {
|
PARTTYPES = {
|
||||||
|
@ -228,7 +229,7 @@ class partition(cryptobox.plugins.base.CryptoBoxPlugin):
|
||||||
## breaks the flow (hanging process)
|
## breaks the flow (hanging process)
|
||||||
#self.cbox.reReadContainerList()
|
#self.cbox.reReadContainerList()
|
||||||
## write config data
|
## write config data
|
||||||
self.cbox.prefs.mountPartition()
|
self.cbox.prefs.mount_partition()
|
||||||
self.cbox.prefs.write()
|
self.cbox.prefs.write()
|
||||||
self.cbox.log.info("settings stored on config partition")
|
self.cbox.log.info("settings stored on config partition")
|
||||||
## return the result
|
## return the result
|
||||||
|
@ -456,6 +457,26 @@ class partition(cryptobox.plugins.base.CryptoBoxPlugin):
|
||||||
|
|
||||||
|
|
||||||
def __format_one_partition(self, dev_name, fs_type):
|
def __format_one_partition(self, dev_name, fs_type):
|
||||||
|
"""Format a single partition
|
||||||
|
"""
|
||||||
|
import cryptobox.core.container
|
||||||
|
## first: retrieve UUID - it can be removed from the database afterwards
|
||||||
|
prev_name = [e.get_name() for e in self.cbox.get_container_list()
|
||||||
|
if e.get_device() == dev_name]
|
||||||
|
## call "mkfs"
|
||||||
|
try:
|
||||||
|
cont = cryptobox.core.container.CryptoBoxContainer(dev_name, self.cbox)
|
||||||
|
cont.create(cryptobox.core.container.CONTAINERTYPES["plain"], fs_type=fs_type)
|
||||||
|
except (CBInvalidType, CBCreateError, CBVolumeIsActive), err_msg:
|
||||||
|
self.cbox.log.warn(err_msg)
|
||||||
|
return False
|
||||||
|
## remove unused volume entry
|
||||||
|
if prev_name:
|
||||||
|
del self.cbox.prefs.volumes_db[prev_name[0]]
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
|
def __old_format_one_partition(self, dev_name, fs_type):
|
||||||
"""Format a single partition
|
"""Format a single partition
|
||||||
"""
|
"""
|
||||||
## first: retrieve UUID - it can be removed from the database afterwards
|
## first: retrieve UUID - it can be removed from the database afterwards
|
||||||
|
|
|
@ -22,7 +22,7 @@ __revision__ = "$Id"
|
||||||
|
|
||||||
import cryptobox.plugins.base
|
import cryptobox.plugins.base
|
||||||
|
|
||||||
REDIRECT_DELAY = 180
|
REDIRECT_DELAY = 120
|
||||||
|
|
||||||
class shutdown(cryptobox.plugins.base.CryptoBoxPlugin):
|
class shutdown(cryptobox.plugins.base.CryptoBoxPlugin):
|
||||||
|
|
||||||
|
@ -44,7 +44,7 @@ class shutdown(cryptobox.plugins.base.CryptoBoxPlugin):
|
||||||
elif type == "reboot":
|
elif type == "reboot":
|
||||||
if self.__do_shutdown("reboot"):
|
if self.__do_shutdown("reboot"):
|
||||||
self.hdf["Data.Success"] = "Plugins.shutdown.Reboot"
|
self.hdf["Data.Success"] = "Plugins.shutdown.Reboot"
|
||||||
self.hdf["Data.Redirect.URL"] = ""
|
self.hdf["Data.Redirect.URL"] = "/"
|
||||||
self.hdf["Data.Redirect.Delay"] = REDIRECT_DELAY
|
self.hdf["Data.Redirect.Delay"] = REDIRECT_DELAY
|
||||||
return "progress_reboot"
|
return "progress_reboot"
|
||||||
else:
|
else:
|
||||||
|
|
|
@ -31,8 +31,8 @@ AdviceMessage {
|
||||||
|
|
||||||
SuccessMessage {
|
SuccessMessage {
|
||||||
FormatSuccess {
|
FormatSuccess {
|
||||||
Title = Formatting successful
|
Title = Formatting is running
|
||||||
Text = The selected filesystem was successfully formatted.
|
Text = The selected filesystem is being formatted in the background. This may take some time (depending on the size of your disk).
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -40,7 +40,7 @@ class volume_format_fs(cryptobox.plugins.base.CryptoBoxPlugin):
|
||||||
|
|
||||||
def do_action(self, store=None, fs_type="windows", container_type="luks", crypto_password=None, crypto_password2=None, confirm=None):
|
def do_action(self, store=None, fs_type="windows", container_type="luks", crypto_password=None, crypto_password2=None, confirm=None):
|
||||||
if not fs_type in FSTYPES.keys():
|
if not fs_type in FSTYPES.keys():
|
||||||
self.cbox.info
|
self.cbox.log.info("invalid filesystem type choosen: %s" % str(fs_type))
|
||||||
return "format_volume"
|
return "format_volume"
|
||||||
self.hdf[self.hdf_prefix + "fs_type"] = fs_type
|
self.hdf[self.hdf_prefix + "fs_type"] = fs_type
|
||||||
self.hdf[self.hdf_prefix + "container_type"] = container_type
|
self.hdf[self.hdf_prefix + "container_type"] = container_type
|
||||||
|
@ -54,10 +54,10 @@ class volume_format_fs(cryptobox.plugins.base.CryptoBoxPlugin):
|
||||||
if container_type == "luks":
|
if container_type == "luks":
|
||||||
return "volume_format_luks"
|
return "volume_format_luks"
|
||||||
elif container_type == "plain":
|
elif container_type == "plain":
|
||||||
return self.__format_plain(fs_type)
|
return self.__format_plain(FSTYPES[fs_type])
|
||||||
elif store == "step2":
|
elif store == "step2":
|
||||||
if container_type == "luks":
|
if container_type == "luks":
|
||||||
return self.__format_luks(fs_type, crypto_password, crypto_password2)
|
return self.__format_luks(FSTYPES[fs_type], crypto_password, crypto_password2)
|
||||||
else:
|
else:
|
||||||
self.cbox.log.info("invalid input value for 'container_type': %s" % container_type)
|
self.cbox.log.info("invalid input value for 'container_type': %s" % container_type)
|
||||||
return "volume_format"
|
return "volume_format"
|
||||||
|
@ -72,36 +72,10 @@ class volume_format_fs(cryptobox.plugins.base.CryptoBoxPlugin):
|
||||||
return "no status"
|
return "no status"
|
||||||
|
|
||||||
|
|
||||||
def __format_plain(self, fsType):
|
def __format_plain(self, fs_type):
|
||||||
try:
|
try:
|
||||||
container = self.cbox.get_container(self.device)
|
container = self.cbox.get_container(self.device)
|
||||||
container.create(cbx_container.CONTAINERTYPES["plain"])
|
container.create(cbx_container.CONTAINERTYPES["plain"], fs_type=fs_type)
|
||||||
except CBVolumeIsActive:
|
|
||||||
self.hdf["Data.Warning"] = "VolumeMayNotBeMounted"
|
|
||||||
self.cbox.log.info("initialization is not possible as long as the device (%s) is mounted" % self.device)
|
|
||||||
return None
|
|
||||||
except CBContainerError, errMsg:
|
|
||||||
self.hdf["Data.Warning"] = "Plugins.volume_format_fs.FormatFailed"
|
|
||||||
self.cbox.log.warn("initialization of device '%s' failed" % self.device)
|
|
||||||
self.cbox.log.warn("reason: %s" % errMsg)
|
|
||||||
return "volume_format"
|
|
||||||
else:
|
|
||||||
self.cbox.log.info("successfully initialized device '%s'" % self.device)
|
|
||||||
return None
|
|
||||||
|
|
||||||
|
|
||||||
def __format_luks(self, fsType, pw, pw2):
|
|
||||||
if not pw:
|
|
||||||
self.hdf["Data.Warning"] = "EmptyPassword"
|
|
||||||
self.cbox.log.warn("no crypto password was supplied for initialization of device '%s'" % self.device)
|
|
||||||
return "volume_format"
|
|
||||||
if pw != pw2:
|
|
||||||
self.hdf["Data.Warning"] = "DifferentPasswords"
|
|
||||||
self.cbox.log.warn("the crypto password was not repeated correctly for initialization of device '%s'" % self.device)
|
|
||||||
return "volume_format"
|
|
||||||
container = self.cbox.get_container(self.device)
|
|
||||||
try:
|
|
||||||
container.create(cbx_container.CONTAINERTYPES["luks"], pw)
|
|
||||||
except CBVolumeIsActive:
|
except CBVolumeIsActive:
|
||||||
self.hdf["Data.Warning"] = "VolumeMayNotBeMounted"
|
self.hdf["Data.Warning"] = "VolumeMayNotBeMounted"
|
||||||
self.cbox.log.info("initialization is not possible as long as the device (%s) is mounted" % self.device)
|
self.cbox.log.info("initialization is not possible as long as the device (%s) is mounted" % self.device)
|
||||||
|
@ -114,5 +88,33 @@ class volume_format_fs(cryptobox.plugins.base.CryptoBoxPlugin):
|
||||||
else:
|
else:
|
||||||
self.hdf["Data.Success"] = "Plugins.volume_format_fs.FormatSuccess"
|
self.hdf["Data.Success"] = "Plugins.volume_format_fs.FormatSuccess"
|
||||||
self.cbox.log.info("successfully initialized device '%s'" % self.device)
|
self.cbox.log.info("successfully initialized device '%s'" % self.device)
|
||||||
return None
|
return { "plugin":"disks", "values":{} }
|
||||||
|
|
||||||
|
|
||||||
|
def __format_luks(self, fs_type, pw, pw2):
|
||||||
|
if not pw:
|
||||||
|
self.hdf["Data.Warning"] = "EmptyPassword"
|
||||||
|
self.cbox.log.warn("no crypto password was supplied for initialization of device '%s'" % self.device)
|
||||||
|
return "volume_format"
|
||||||
|
if pw != pw2:
|
||||||
|
self.hdf["Data.Warning"] = "DifferentPasswords"
|
||||||
|
self.cbox.log.warn("the crypto password was not repeated correctly for initialization of device '%s'" % self.device)
|
||||||
|
return "volume_format"
|
||||||
|
container = self.cbox.get_container(self.device)
|
||||||
|
try:
|
||||||
|
container.create(cbx_container.CONTAINERTYPES["luks"],
|
||||||
|
fs_type=fs_type, password=pw)
|
||||||
|
except CBVolumeIsActive:
|
||||||
|
self.hdf["Data.Warning"] = "VolumeMayNotBeMounted"
|
||||||
|
self.cbox.log.info("initialization is not possible as long as the device (%s) is mounted" % self.device)
|
||||||
|
return None
|
||||||
|
except CBContainerError, errMsg:
|
||||||
|
self.hdf["Data.Warning"] = "Plugins.volume_format_fs.FormatFailed"
|
||||||
|
self.cbox.log.warn("initialization of device '%s' failed" % self.device)
|
||||||
|
self.cbox.log.warn("reason: %s" % errMsg)
|
||||||
|
return "volume_format"
|
||||||
|
else:
|
||||||
|
self.hdf["Data.Success"] = "Plugins.volume_format_fs.FormatSuccess"
|
||||||
|
self.cbox.log.info("successfully initialized device '%s'" % self.device)
|
||||||
|
return { "plugin":"disks", "values":{} }
|
||||||
|
|
||||||
|
|
|
@ -26,6 +26,7 @@ __revision__ = "$Id"
|
||||||
import subprocess
|
import subprocess
|
||||||
import os
|
import os
|
||||||
import re
|
import re
|
||||||
|
import time
|
||||||
from cryptobox.core.exceptions import *
|
from cryptobox.core.exceptions import *
|
||||||
|
|
||||||
|
|
||||||
|
@ -36,6 +37,10 @@ CONTAINERTYPES = {
|
||||||
"swap":3,
|
"swap":3,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
FSTYPES = {
|
||||||
|
"plain":["ext3", "ext2", "vfat", "reiserfs"],
|
||||||
|
"swap":["swap"]}
|
||||||
|
|
||||||
|
|
||||||
## we use this marker to make sure, that we do not remove a non-cryptobox directory
|
## we use this marker to make sure, that we do not remove a non-cryptobox directory
|
||||||
## below the mount directory
|
## below the mount directory
|
||||||
|
@ -46,10 +51,6 @@ class CryptoBoxContainer:
|
||||||
"""Manage a container of the CryptoBox
|
"""Manage a container of the CryptoBox
|
||||||
"""
|
"""
|
||||||
|
|
||||||
__fsTypes = {
|
|
||||||
"plain":["ext3", "ext2", "vfat", "reiserfs"],
|
|
||||||
"swap":["swap"]}
|
|
||||||
|
|
||||||
__dmDir = "/dev/mapper"
|
__dmDir = "/dev/mapper"
|
||||||
|
|
||||||
|
|
||||||
|
@ -101,10 +102,10 @@ class CryptoBoxContainer:
|
||||||
raise CBVolumeIsActive("the container must not be active during renaming")
|
raise CBVolumeIsActive("the container must not be active during renaming")
|
||||||
if not re.search(r'^[a-zA-Z0-9_\.\- ]+$', new_name):
|
if not re.search(r'^[a-zA-Z0-9_\.\- ]+$', new_name):
|
||||||
raise CBInvalidName("the supplied new name contains illegal characters")
|
raise CBInvalidName("the supplied new name contains illegal characters")
|
||||||
## check for another partitions with the same name
|
## check for another partition with the same name
|
||||||
if self.cbox.get_container_list(filter_name=new_name):
|
if self.cbox.get_container_list(filter_name=new_name):
|
||||||
raise CBNameIsInUse("the supplied new name is already in use for anonther partition")
|
raise CBNameIsInUse("the supplied new name is already in use for anonther partition")
|
||||||
## maybe there a is an entry in the volumes database (but the partition is not active
|
## maybe there a is an entry in the volumes database (but the partition is not active)
|
||||||
try:
|
try:
|
||||||
## remove possibly existing inactive database item
|
## remove possibly existing inactive database item
|
||||||
del self.cbox.prefs.volumes_db[new_name]
|
del self.cbox.prefs.volumes_db[new_name]
|
||||||
|
@ -182,23 +183,64 @@ class CryptoBoxContainer:
|
||||||
self.umount = self.__umount_plain
|
self.umount = self.__umount_plain
|
||||||
|
|
||||||
|
|
||||||
def create(self, cont_type, password=None):
|
def create(self, cont_type, password=None, fs_type="ext3"):
|
||||||
"""Format a container.
|
"""Format a container.
|
||||||
|
|
||||||
Also set a password for encrypted container.
|
Also set a password for encrypted container.
|
||||||
"""
|
"""
|
||||||
|
if not fs_type in FSTYPES["plain"]:
|
||||||
|
raise CBInvalidType("invalid filesystem type supplied: %s" % str(fs_type))
|
||||||
old_name = self.get_name()
|
old_name = self.get_name()
|
||||||
if cont_type == CONTAINERTYPES["luks"]:
|
if cont_type == CONTAINERTYPES["luks"]:
|
||||||
self.__create_luks(password)
|
self.__create_luks(password, fs_type)
|
||||||
elif cont_type == CONTAINERTYPES["plain"]:
|
elif cont_type == CONTAINERTYPES["plain"]:
|
||||||
self.__create_plain()
|
self.__create_plain(fs_type)
|
||||||
else:
|
else:
|
||||||
raise CBInvalidType("invalid container type (%d) supplied" % (cont_type, ))
|
raise CBInvalidType("invalid container type (%d) supplied" % (cont_type, ))
|
||||||
## no exception was raised during creation -> we can continue
|
## no exception was raised during creation -> we can continue
|
||||||
## reset the properties (encryption state, ...) of the device
|
## reset the properties (encryption state, ...) of the device
|
||||||
self.reset_object()
|
self.reset_object()
|
||||||
## restore the old name (must be after reset_object)
|
## restore the old name (must be after reset_object)
|
||||||
self.set_name(old_name)
|
try:
|
||||||
|
self.set_name(old_name)
|
||||||
|
except CBNameIsInUse:
|
||||||
|
## failure is okay
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
def set_busy(self, new_state, time_limit=300):
|
||||||
|
"""Set the current busy state.
|
||||||
|
|
||||||
|
The timelimit is specified in seconds.
|
||||||
|
"""
|
||||||
|
if new_state:
|
||||||
|
self.cbox.busy_devices[self.device] = int(time.time() + time_limit)
|
||||||
|
else:
|
||||||
|
try:
|
||||||
|
if self.cbox.busy_devices[self.device]:
|
||||||
|
del self.cbox.busy_devices[self.device]
|
||||||
|
except KeyError:
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
def is_busy(self):
|
||||||
|
"""Check the busy state of the container.
|
||||||
|
"""
|
||||||
|
if not self.cbox.busy_devices.has_key(self.device):
|
||||||
|
self.cbox.log.debug("no 'busy' attribute for '%s'" % self.get_name())
|
||||||
|
return False
|
||||||
|
## invalid value - can happen after saving and loading the database
|
||||||
|
if not isinstance(self.cbox.busy_devices[self.device], int):
|
||||||
|
self.cbox.log.debug("invalid 'busy' attribute for '%s'" % self.get_name())
|
||||||
|
del db_entry["busy"]
|
||||||
|
return False
|
||||||
|
if time.time() >= self.cbox.busy_devices[self.device]:
|
||||||
|
self.cbox.log.debug("expired 'busy' attribute for '%s'" % self.get_name())
|
||||||
|
del db_entry["busy"]
|
||||||
|
return False
|
||||||
|
## lock is still active
|
||||||
|
self.cbox.log.debug("active 'busy' attribute for '%s'" % self.get_name())
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
def change_password(self, oldpw, newpw):
|
def change_password(self, oldpw, newpw):
|
||||||
|
@ -362,9 +404,9 @@ class CryptoBoxContainer:
|
||||||
if self.__is_luks_partition():
|
if self.__is_luks_partition():
|
||||||
return CONTAINERTYPES["luks"]
|
return CONTAINERTYPES["luks"]
|
||||||
type_of_partition = self.__get_type_id_of_partition()
|
type_of_partition = self.__get_type_id_of_partition()
|
||||||
if type_of_partition in self.__fsTypes["plain"]:
|
if type_of_partition in FSTYPES["plain"]:
|
||||||
return CONTAINERTYPES["plain"]
|
return CONTAINERTYPES["plain"]
|
||||||
if type_of_partition in self.__fsTypes["swap"]:
|
if type_of_partition in FSTYPES["swap"]:
|
||||||
return CONTAINERTYPES["swap"]
|
return CONTAINERTYPES["swap"]
|
||||||
return CONTAINERTYPES["unused"]
|
return CONTAINERTYPES["unused"]
|
||||||
|
|
||||||
|
@ -372,29 +414,28 @@ class CryptoBoxContainer:
|
||||||
def __get_type_id_of_partition(self):
|
def __get_type_id_of_partition(self):
|
||||||
"returns the type of the partition (see 'man blkid')"
|
"returns the type of the partition (see 'man blkid')"
|
||||||
devnull = None
|
devnull = None
|
||||||
try:
|
|
||||||
devnull = open(os.devnull, "w")
|
|
||||||
except IOError:
|
|
||||||
self.cbox.log.warn("Could not open %s" % (os.devnull, ))
|
|
||||||
proc = subprocess.Popen(
|
proc = subprocess.Popen(
|
||||||
shell=False,
|
shell = False,
|
||||||
stdin=None,
|
stdout = subprocess.PIPE,
|
||||||
stdout=subprocess.PIPE,
|
stderr = subprocess.PIPE,
|
||||||
stderr=subprocess.PIPE,
|
args = [ self.cbox.prefs["Programs"]["blkid"],
|
||||||
args=[self.cbox.prefs["Programs"]["blkid"],
|
|
||||||
"-s", "TYPE",
|
"-s", "TYPE",
|
||||||
"-o", "value",
|
"-o", "value",
|
||||||
"-c", os.devnull,
|
"-c", os.devnull,
|
||||||
"-w", os.devnull,
|
"-w", os.devnull,
|
||||||
self.device])
|
self.device ])
|
||||||
proc.wait()
|
(stdout, stder) = proc.communicate()
|
||||||
output = proc.stdout.read().strip()
|
if proc.returncode == 0:
|
||||||
if proc.returncode != 0:
|
## we found a uuid
|
||||||
self.cbox.log.warn("retrieving of partition type via 'blkid' failed: %s" % \
|
return stdout.strip()
|
||||||
(proc.stderr.read().strip(), ))
|
elif proc.returncode == 2:
|
||||||
|
## failed to find the attribute - no problem
|
||||||
|
return None
|
||||||
|
else:
|
||||||
|
## something strange happened
|
||||||
|
self.cbox.log.warn("retrieving of partition type via 'blkid' failed: %s" % \
|
||||||
|
(stderr.strip(), ))
|
||||||
return None
|
return None
|
||||||
devnull.close()
|
|
||||||
return output
|
|
||||||
|
|
||||||
|
|
||||||
def __is_luks_partition(self):
|
def __is_luks_partition(self):
|
||||||
|
@ -596,50 +637,63 @@ class CryptoBoxContainer:
|
||||||
self.cbox.send_event_notification("postumount", self.__get_event_args())
|
self.cbox.send_event_notification("postumount", self.__get_event_args())
|
||||||
|
|
||||||
|
|
||||||
def __create_plain(self):
|
def __create_plain(self, fs_type="ext3"):
|
||||||
"make a plaintext partition"
|
"make a plaintext partition"
|
||||||
|
import threading
|
||||||
if self.is_mounted():
|
if self.is_mounted():
|
||||||
raise CBVolumeIsActive("deactivate the partition before filesystem initialization")
|
raise CBVolumeIsActive(
|
||||||
devnull = None
|
"deactivate the partition before filesystem initialization")
|
||||||
try:
|
def format():
|
||||||
devnull = open(os.devnull, "w")
|
import os
|
||||||
except IOError:
|
old_name = self.get_name()
|
||||||
self.cbox.log.warn("Could not open %s" % (os.devnull, ))
|
self.set_busy(True, 600)
|
||||||
proc = subprocess.Popen(
|
self.cbox.log.debug("Turn the busy flag on: %s" % self.device)
|
||||||
shell = False,
|
## give the main thread a chance to continue
|
||||||
stdin = None,
|
child_pid = os.fork()
|
||||||
stdout = devnull,
|
if child_pid == 0:
|
||||||
stderr = subprocess.PIPE,
|
proc = subprocess.Popen(
|
||||||
args = [
|
shell = False,
|
||||||
self.cbox.prefs["Programs"]["mkfs-data"],
|
stdin = None,
|
||||||
self.device])
|
stdout = subprocess.PIPE,
|
||||||
proc.wait()
|
stderr = subprocess.PIPE,
|
||||||
if proc.returncode != 0:
|
args = [
|
||||||
err_msg = "Could not create the filesystem: %s" % (proc.stderr.read().strip(), )
|
self.cbox.prefs["Programs"]["nice"],
|
||||||
self.cbox.log.error(err_msg)
|
self.cbox.prefs["Programs"]["mkfs"],
|
||||||
raise CBCreateError(err_msg)
|
"-t", fs_type, self.device])
|
||||||
devnull.close()
|
(stdout, sterr) = proc.communicate()
|
||||||
|
## for to allow error detection
|
||||||
|
if proc.returncode == 0:
|
||||||
|
time.sleep(5)
|
||||||
|
## skip cleanup stuff (as common for sys.exit)
|
||||||
|
os._exit(0)
|
||||||
|
else:
|
||||||
|
os.waitpid(child_pid, 0)
|
||||||
|
self.set_name(old_name)
|
||||||
|
self.set_busy(False)
|
||||||
|
self.cbox.log.debug("Turn the busy flag off: %s" % self.device)
|
||||||
|
bg_task = threading.Thread(target=format)
|
||||||
|
bg_task.start()
|
||||||
|
time.sleep(3)
|
||||||
|
## if the thread exited very fast, then it failed
|
||||||
|
if not bg_task.isAlive():
|
||||||
|
raise CBCreateError("Failed to initilize device: %s" % self.device)
|
||||||
|
|
||||||
|
|
||||||
def __create_luks(self, password):
|
def __create_luks(self, password, fs_type="ext3"):
|
||||||
"""Create a luks partition.
|
"""Create a luks partition.
|
||||||
"""
|
"""
|
||||||
|
import threading
|
||||||
if not password:
|
if not password:
|
||||||
raise CBInvalidPassword("no password supplied for new luks mapping")
|
raise CBInvalidPassword("no password supplied for new luks mapping")
|
||||||
if self.is_mounted():
|
if self.is_mounted():
|
||||||
raise CBVolumeIsActive("deactivate the partition before filesystem initialization")
|
raise CBVolumeIsActive("deactivate the partition before filesystem initialization")
|
||||||
devnull = None
|
|
||||||
try:
|
|
||||||
devnull = open(os.devnull, "w")
|
|
||||||
except IOError:
|
|
||||||
self.cbox.log.warn("Could not open %s" % (os.devnull, ))
|
|
||||||
## remove any potential open luks mapping
|
## remove any potential open luks mapping
|
||||||
self.__umount_luks()
|
self.__umount_luks()
|
||||||
## create the luks header
|
## create the luks header
|
||||||
proc = subprocess.Popen(
|
proc = subprocess.Popen(
|
||||||
shell = False,
|
shell = False,
|
||||||
stdin = subprocess.PIPE,
|
stdin = subprocess.PIPE,
|
||||||
stdout = devnull,
|
stdout = subprocess.PIPE,
|
||||||
stderr = subprocess.PIPE,
|
stderr = subprocess.PIPE,
|
||||||
args = [
|
args = [
|
||||||
self.cbox.prefs["Programs"]["super"],
|
self.cbox.prefs["Programs"]["super"],
|
||||||
|
@ -660,7 +714,7 @@ class CryptoBoxContainer:
|
||||||
proc = subprocess.Popen(
|
proc = subprocess.Popen(
|
||||||
shell = False,
|
shell = False,
|
||||||
stdin = subprocess.PIPE,
|
stdin = subprocess.PIPE,
|
||||||
stdout = devnull,
|
stdout = subprocess.PIPE,
|
||||||
stderr = subprocess.PIPE,
|
stderr = subprocess.PIPE,
|
||||||
args = [
|
args = [
|
||||||
self.cbox.prefs["Programs"]["super"],
|
self.cbox.prefs["Programs"]["super"],
|
||||||
|
@ -676,24 +730,44 @@ class CryptoBoxContainer:
|
||||||
err_msg = "Could not open the new luks mapping: %s" % (errout.strip(), )
|
err_msg = "Could not open the new luks mapping: %s" % (errout.strip(), )
|
||||||
self.cbox.log.error(err_msg)
|
self.cbox.log.error(err_msg)
|
||||||
raise CBCreateError(err_msg)
|
raise CBCreateError(err_msg)
|
||||||
## make the filesystem
|
def format_luks():
|
||||||
proc = subprocess.Popen(
|
import os
|
||||||
shell = False,
|
old_name = self.get_name()
|
||||||
stdin = None,
|
self.set_busy(True, 600)
|
||||||
stdout = devnull,
|
self.cbox.log.debug("Turn the busy flag on: %s" % self.device)
|
||||||
stderr = subprocess.PIPE,
|
child_pid = os.fork()
|
||||||
args = [
|
if child_pid == 0:
|
||||||
self.cbox.prefs["Programs"]["mkfs-data"],
|
## make the filesystem
|
||||||
os.path.join(self.__dmDir, self.name)])
|
proc = subprocess.Popen(
|
||||||
proc.wait()
|
shell = False,
|
||||||
## remove the mapping - for every exit status
|
stdin = None,
|
||||||
self.__umount_luks()
|
stdout = subprocess.PIPE,
|
||||||
if proc.returncode != 0:
|
stderr = subprocess.PIPE,
|
||||||
err_msg = "Could not create the filesystem: %s" % (proc.stderr.read().strip(), )
|
args = [
|
||||||
self.cbox.log.error(err_msg)
|
self.cbox.prefs["Programs"]["nice"],
|
||||||
## remove the luks mapping
|
self.cbox.prefs["Programs"]["mkfs"],
|
||||||
raise CBCreateError(err_msg)
|
"-t", fs_type,
|
||||||
devnull.close()
|
os.path.join(self.__dmDir, self.name)])
|
||||||
|
(stdou, stderr) = proc.communicate()
|
||||||
|
## wait to allow error detection
|
||||||
|
if proc.returncode == 0:
|
||||||
|
time.sleep(5)
|
||||||
|
## skip cleanup stuff (as common for sys.exit)
|
||||||
|
os._exit(0)
|
||||||
|
else:
|
||||||
|
os.waitpid(child_pid, 0)
|
||||||
|
self.set_name(old_name)
|
||||||
|
self.set_busy(False)
|
||||||
|
self.cbox.log.debug("Turn the busy flag off: %s" % self.device)
|
||||||
|
## remove the mapping - for every exit status
|
||||||
|
self.__umount_luks()
|
||||||
|
bg_task = threading.Thread(target=format_luks)
|
||||||
|
bg_task.setDaemon(True)
|
||||||
|
bg_task.start()
|
||||||
|
time.sleep(3)
|
||||||
|
## if the thread exited very fast, then it failed
|
||||||
|
if not bg_task.isAlive():
|
||||||
|
raise CBCreateError("Failed to initilize device: %s" % self.device)
|
||||||
|
|
||||||
|
|
||||||
def __clean_mount_dirs(self):
|
def __clean_mount_dirs(self):
|
||||||
|
|
|
@ -46,6 +46,7 @@ class CryptoBox:
|
||||||
self.prefs = cbxSettings.CryptoBoxSettings(config_file)
|
self.prefs = cbxSettings.CryptoBoxSettings(config_file)
|
||||||
self.__run_tests()
|
self.__run_tests()
|
||||||
self.__containers = []
|
self.__containers = []
|
||||||
|
self.busy_devices = {}
|
||||||
self.reread_container_list()
|
self.reread_container_list()
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -455,7 +455,8 @@ Languages = list(min=1,default=list("en"))
|
||||||
|
|
||||||
[Programs]
|
[Programs]
|
||||||
cryptsetup = fileExecutable(default="/sbin/cryptsetup")
|
cryptsetup = fileExecutable(default="/sbin/cryptsetup")
|
||||||
mkfs-data = fileExecutable(default="/sbin/mkfs.ext3")
|
mkfs = fileExecutable(default="/sbin/mkfs")
|
||||||
|
nice = fileExecutable(default="/usr/bin/nice")
|
||||||
blkid = fileExecutable(default="/sbin/blkid")
|
blkid = fileExecutable(default="/sbin/blkid")
|
||||||
blockdev = fileExecutable(default="/sbin/blockdev")
|
blockdev = fileExecutable(default="/sbin/blockdev")
|
||||||
mount = fileExecutable(default="/bin/mount")
|
mount = fileExecutable(default="/bin/mount")
|
||||||
|
|
|
@ -191,6 +191,14 @@ class CryptoBoxPlugin:
|
||||||
return self.plugin_visibility
|
return self.plugin_visibility
|
||||||
|
|
||||||
|
|
||||||
|
def reset(self):
|
||||||
|
"""Reinitialize the plugin.
|
||||||
|
|
||||||
|
This function should be called before every run
|
||||||
|
"""
|
||||||
|
self.hdf = {}
|
||||||
|
|
||||||
|
|
||||||
def get_test_class(self):
|
def get_test_class(self):
|
||||||
"""Return the unittest class of the feature.
|
"""Return the unittest class of the feature.
|
||||||
"""
|
"""
|
||||||
|
|
|
@ -103,11 +103,13 @@ class WebInterfaceDataset(dict):
|
||||||
is_plain = (container.get_type() == \
|
is_plain = (container.get_type() == \
|
||||||
cbxContainer.CONTAINERTYPES["plain"]) and 1 or 0
|
cbxContainer.CONTAINERTYPES["plain"]) and 1 or 0
|
||||||
is_mounted = container.is_mounted() and 1 or 0
|
is_mounted = container.is_mounted() and 1 or 0
|
||||||
|
is_busy = container.is_busy() and 1 or 0
|
||||||
self["Data.CurrentDisk.device"] = container.get_device()
|
self["Data.CurrentDisk.device"] = container.get_device()
|
||||||
self["Data.CurrentDisk.name"] = container.get_name()
|
self["Data.CurrentDisk.name"] = container.get_name()
|
||||||
self["Data.CurrentDisk.encryption"] = is_encrypted
|
self["Data.CurrentDisk.encryption"] = is_encrypted
|
||||||
self["Data.CurrentDisk.plaintext"] = is_plain
|
self["Data.CurrentDisk.plaintext"] = is_plain
|
||||||
self["Data.CurrentDisk.active"] = is_mounted
|
self["Data.CurrentDisk.active"] = is_mounted
|
||||||
|
self["Data.CurrentDisk.busy"] = is_busy
|
||||||
self["Data.CurrentDisk.size"] = cbxTools.get_blockdevice_size_humanly(
|
self["Data.CurrentDisk.size"] = cbxTools.get_blockdevice_size_humanly(
|
||||||
container.get_device())
|
container.get_device())
|
||||||
if is_mounted:
|
if is_mounted:
|
||||||
|
@ -133,10 +135,12 @@ class WebInterfaceDataset(dict):
|
||||||
is_plain = (container.get_type() == \
|
is_plain = (container.get_type() == \
|
||||||
cbxContainer.CONTAINERTYPES["plain"]) and 1 or 0
|
cbxContainer.CONTAINERTYPES["plain"]) and 1 or 0
|
||||||
is_mounted = container.is_mounted() and 1 or 0
|
is_mounted = container.is_mounted() and 1 or 0
|
||||||
|
is_busy = container.is_busy() and 1 or 0
|
||||||
self["Data.Disks.%d.device" % avail_counter] = container.get_device()
|
self["Data.Disks.%d.device" % avail_counter] = container.get_device()
|
||||||
self["Data.Disks.%d.name" % avail_counter] = container.get_name()
|
self["Data.Disks.%d.name" % avail_counter] = container.get_name()
|
||||||
self["Data.Disks.%d.encryption" % avail_counter] = is_encrypted
|
self["Data.Disks.%d.encryption" % avail_counter] = is_encrypted
|
||||||
self["Data.Disks.%d.plaintext" % avail_counter] = is_plain
|
self["Data.Disks.%d.plaintext" % avail_counter] = is_plain
|
||||||
|
self["Data.Disks.%d.busy" % avail_counter] = is_busy
|
||||||
self["Data.Disks.%d.active" % avail_counter] = is_mounted
|
self["Data.Disks.%d.active" % avail_counter] = is_mounted
|
||||||
self["Data.Disks.%d.size" % avail_counter] = \
|
self["Data.Disks.%d.size" % avail_counter] = \
|
||||||
cbxTools.get_blockdevice_size_humanly(container.get_device())
|
cbxTools.get_blockdevice_size_humanly(container.get_device())
|
||||||
|
|
|
@ -252,28 +252,20 @@ class WebInterfaceSites:
|
||||||
""" returns a function that is suitable for handling a cherrypy
|
""" returns a function that is suitable for handling a cherrypy
|
||||||
page request
|
page request
|
||||||
"""
|
"""
|
||||||
def handler(self, **args):
|
def handler(self, weblang="", device=None, redirect=None, message_keep=None, **args):
|
||||||
"""this function handles a cherrypy page request
|
"""this function handles a cherrypy page request
|
||||||
"""
|
"""
|
||||||
|
plugin.reset()
|
||||||
self.__reset_dataset()
|
self.__reset_dataset()
|
||||||
self.__check_environment()
|
self.__check_environment()
|
||||||
## set web interface language
|
self.__set_web_lang(weblang)
|
||||||
try:
|
|
||||||
self.__set_web_lang(args["weblang"])
|
|
||||||
del args["weblang"]
|
|
||||||
except KeyError:
|
|
||||||
self.__set_web_lang("")
|
|
||||||
## we always read the "device" setting - otherwise volume-plugin
|
## we always read the "device" setting - otherwise volume-plugin
|
||||||
## links would not work easily
|
## links would not work easily
|
||||||
## (see "volume_props" linking to "volume_format_fs")
|
## (see "volume_props" linking to "volume_format_fs")
|
||||||
## it will get ignored for non-volume plugins
|
## it will get ignored for non-volume plugins
|
||||||
try:
|
plugin.device = None
|
||||||
plugin.device = None
|
if device and self.__set_device(device):
|
||||||
if self.__set_device(args["device"]):
|
plugin.device = device
|
||||||
plugin.device = args["device"]
|
|
||||||
del args["device"]
|
|
||||||
except KeyError:
|
|
||||||
plugin.device = None
|
|
||||||
## check the device argument of volume plugins
|
## check the device argument of volume plugins
|
||||||
if "volume" in plugin.plugin_capabilities:
|
if "volume" in plugin.plugin_capabilities:
|
||||||
## initialize the dataset of the selected device if necessary
|
## initialize the dataset of the selected device if necessary
|
||||||
|
@ -285,22 +277,18 @@ class WebInterfaceSites:
|
||||||
## check if there is a "redirect" setting - this will override
|
## check if there is a "redirect" setting - this will override
|
||||||
## the return value of the do_action function
|
## the return value of the do_action function
|
||||||
## (e.g. useful for umount-before-format)
|
## (e.g. useful for umount-before-format)
|
||||||
try:
|
override_next_template = None
|
||||||
if args["redirect"]:
|
if redirect:
|
||||||
override_next_template = { "plugin":args["redirect"] }
|
override_next_template = { "plugin": redirect }
|
||||||
if "volume" in plugin.plugin_capabilities:
|
if "volume" in plugin.plugin_capabilities:
|
||||||
override_next_template["values"] = {"device":plugin.device}
|
override_next_template["values"] = {"device":plugin.device}
|
||||||
del args["redirect"]
|
|
||||||
except KeyError:
|
|
||||||
override_next_template = None
|
|
||||||
## check for information to be kept after the last call
|
## check for information to be kept after the last call
|
||||||
try:
|
if message_keep:
|
||||||
keep_values = args["message_keep"]
|
for (key, value) in message_keep["dataset"].items():
|
||||||
del args["message_keep"]
|
|
||||||
for key, value in keep_values["dataset"].items():
|
|
||||||
self.__dataset[key] = value
|
self.__dataset[key] = value
|
||||||
except KeyError:
|
## check if the device is busy
|
||||||
keep_values = None
|
if plugin.device and self.cbox.get_container(plugin.device).is_busy():
|
||||||
|
return self.__render("volume_busy")
|
||||||
## call the plugin handler
|
## call the plugin handler
|
||||||
next_template = plugin.do_action(**args)
|
next_template = plugin.do_action(**args)
|
||||||
## for 'volume' plugins: reread the dataset of the current disk
|
## for 'volume' plugins: reread the dataset of the current disk
|
||||||
|
@ -330,7 +318,7 @@ class WebInterfaceSites:
|
||||||
and self.__plugin_manager.get_plugin(next_template["plugin"]):
|
and self.__plugin_manager.get_plugin(next_template["plugin"]):
|
||||||
value_dict = dict(next_template["values"])
|
value_dict = dict(next_template["values"])
|
||||||
## force the current weblang attribute - otherwise it gets lost
|
## force the current weblang attribute - otherwise it gets lost
|
||||||
value_dict["weblang"] = self.__dataset["Settings.Language"]
|
value_dict["weblang"] = self.lang_order[0]
|
||||||
## check for warnings/success messages, that should be kept
|
## check for warnings/success messages, that should be kept
|
||||||
if "Data.Success" in plugin.hdf.keys() \
|
if "Data.Success" in plugin.hdf.keys() \
|
||||||
or "Data.Warning" in plugin.hdf.keys():
|
or "Data.Warning" in plugin.hdf.keys():
|
||||||
|
@ -354,7 +342,6 @@ class WebInterfaceSites:
|
||||||
|
|
||||||
|
|
||||||
@cherrypy.expose
|
@cherrypy.expose
|
||||||
@__request_auth
|
|
||||||
def test(self, weblang=""):
|
def test(self, weblang=""):
|
||||||
"""test authentication - this function may be safely removed
|
"""test authentication - this function may be safely removed
|
||||||
"""
|
"""
|
||||||
|
@ -509,7 +496,10 @@ class WebInterfaceSites:
|
||||||
if key == "LINK":
|
if key == "LINK":
|
||||||
return
|
return
|
||||||
try:
|
try:
|
||||||
node.setValue("", translator.ugettext(node.value()))
|
#TODO: we should use unicode - or not?
|
||||||
|
#node.setValue("", translator.ugettext(node.value()))
|
||||||
|
## quite obscure: ugettext can handle None - gettext breaks instead
|
||||||
|
node.setValue("", str(translator.gettext(node.value())))
|
||||||
except UnicodeEncodeError, err_msg:
|
except UnicodeEncodeError, err_msg:
|
||||||
self.cbox.log.info(
|
self.cbox.log.info(
|
||||||
"Failed unicode encoding for gettext: %s - %s" \
|
"Failed unicode encoding for gettext: %s - %s" \
|
||||||
|
|
|
@ -22,6 +22,17 @@ Button {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
AdviceMessage {
|
||||||
|
|
||||||
|
VolumeIsBusy {
|
||||||
|
Title = Disk is busy
|
||||||
|
Text = This disk is currently busy. Please wait for a moment.
|
||||||
|
Link.Rel = /
|
||||||
|
Link.Text = Show all disks
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
WarningMessage {
|
WarningMessage {
|
||||||
|
|
||||||
AccessDenied {
|
AccessDenied {
|
||||||
|
|
|
@ -119,15 +119,31 @@ def:show_volume_icon(volume) ?><?cs
|
||||||
# show the appropriate icon for the current state of the volume ?><?cs
|
# show the appropriate icon for the current state of the volume ?><?cs
|
||||||
if:volume.active ?><?cs
|
if:volume.active ?><?cs
|
||||||
if:volume.encryption ?><?cs
|
if:volume.encryption ?><?cs
|
||||||
set:filename='volume_active_crypto.gif' ?><?cs
|
if:volume.busy ?><?cs
|
||||||
|
set:filename='volume_active_crypto_busy.gif' ?><?cs
|
||||||
|
else ?><?cs
|
||||||
|
set:filename='volume_active_crypto.gif' ?><?cs
|
||||||
|
/if ?><?cs
|
||||||
else ?><?cs
|
else ?><?cs
|
||||||
set:filename='volume_active_plain.gif' ?><?cs
|
if:volume.busy ?><?cs
|
||||||
|
set:filename='volume_active_plain_busy.gif' ?><?cs
|
||||||
|
else ?><?cs
|
||||||
|
set:filename='volume_active_plain.gif' ?><?cs
|
||||||
|
/if ?><?cs
|
||||||
/if ?><?cs
|
/if ?><?cs
|
||||||
else ?><?cs
|
else ?><?cs
|
||||||
if:volume.encryption ?><?cs
|
if:volume.encryption ?><?cs
|
||||||
set:filename='volume_passive_crypto.gif' ?><?cs
|
if:volume.busy ?><?cs
|
||||||
|
set:filename='volume_passive_crypto_busy.gif' ?><?cs
|
||||||
|
else ?><?cs
|
||||||
|
set:filename='volume_passive_crypto.gif' ?><?cs
|
||||||
|
/if ?><?cs
|
||||||
else ?><?cs
|
else ?><?cs
|
||||||
set:filename='volume_passive_plain.gif' ?><?cs
|
if:volume.busy ?><?cs
|
||||||
|
set:filename='volume_passive_plain_busy.gif' ?><?cs
|
||||||
|
else ?><?cs
|
||||||
|
set:filename='volume_passive_plain.gif' ?><?cs
|
||||||
|
/if ?><?cs
|
||||||
/if ?><?cs
|
/if ?><?cs
|
||||||
/if ?><img src="<?cs call:link('cryptobox-misc/' + filename,'','','','') ?>" alt="icon: volume" /><?cs
|
/if ?><img src="<?cs call:link('cryptobox-misc/' + filename,'','','','') ?>" alt="icon: volume" /><?cs
|
||||||
/def ?><?cs
|
/def ?><?cs
|
||||||
|
|
|
@ -0,0 +1,8 @@
|
||||||
|
<?cs # $Id$ ?>
|
||||||
|
|
||||||
|
<?cs # display a warning because of a busy volume ?>
|
||||||
|
|
||||||
|
<?cs call:handle_messages() ?>
|
||||||
|
|
||||||
|
<?cs call:hint('VolumeIsBusy') ?>
|
||||||
|
|
After Width: | Height: | Size: 5.5 KiB |
After Width: | Height: | Size: 5.9 KiB |
After Width: | Height: | Size: 4.9 KiB |
After Width: | Height: | Size: 5.2 KiB |
After Width: | Height: | Size: 7.8 KiB |
After Width: | Height: | Size: 7.4 KiB |
After Width: | Height: | Size: 6.9 KiB |
After Width: | Height: | Size: 6.9 KiB |