added gray disc icon for unitialized volumes
simple partitioning interface finished order in navigation bar changed ignore extended partitions (in container list)
This commit is contained in:
parent
665d18bdbd
commit
1c8db28989
16 changed files with 243 additions and 97 deletions
|
@ -113,10 +113,10 @@ class CryptoBoxProps(CryptoBox):
|
||||||
def __init__(self, config_file=None):
|
def __init__(self, config_file=None):
|
||||||
'''read config and fill class variables'''
|
'''read config and fill class variables'''
|
||||||
CryptoBox.__init__(self, config_file)
|
CryptoBox.__init__(self, config_file)
|
||||||
self.__reReadContainerList()
|
self.reReadContainerList()
|
||||||
|
|
||||||
|
|
||||||
def __reReadContainerList(self):
|
def reReadContainerList(self):
|
||||||
self.containers = []
|
self.containers = []
|
||||||
for device in CryptoBoxTools.getAvailablePartitions():
|
for device in CryptoBoxTools.getAvailablePartitions():
|
||||||
if self.isDeviceAllowed(device):
|
if self.isDeviceAllowed(device):
|
||||||
|
|
|
@ -18,7 +18,8 @@ def getAvailablePartitions():
|
||||||
if (len(p_details) == 4):
|
if (len(p_details) == 4):
|
||||||
"the following code prevents double entries like /dev/hda and /dev/hda1"
|
"the following code prevents double entries like /dev/hda and /dev/hda1"
|
||||||
(p_major, p_minor, p_size, p_device) = p_details
|
(p_major, p_minor, p_size, p_device) = p_details
|
||||||
if re.search('^[0-9]*$', p_major) and re.search('^[0-9]*$', p_minor):
|
## ignore lines with: invalid minor/major or extend partitions (size=1)
|
||||||
|
if re.search('^[0-9]*$', p_major) and re.search('^[0-9]*$', p_minor) and (p_size != "1"):
|
||||||
p_parent = re.sub('[1-9]?[0-9]$', '', p_device)
|
p_parent = re.sub('[1-9]?[0-9]$', '', p_device)
|
||||||
if p_parent == p_device:
|
if p_parent == p_device:
|
||||||
if [e for e in ret_list if re.search('^' + p_parent + '[1-9]?[0-9]$', e)]:
|
if [e for e in ret_list if re.search('^' + p_parent + '[1-9]?[0-9]$', e)]:
|
||||||
|
|
|
@ -16,6 +16,7 @@ class WebInterfaceDataset(dict):
|
||||||
self.__setCryptoBoxState()
|
self.__setCryptoBoxState()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def setPluginState(self, plugins):
|
def setPluginState(self, plugins):
|
||||||
for pl in plugins.allPlugins():
|
for pl in plugins.allPlugins():
|
||||||
self["Data.Status.Plugins." + pl] = plugins.getPlugin(pl).getStatus(self.cbox)
|
self["Data.Status.Plugins." + pl] = plugins.getPlugin(pl).getStatus(self.cbox)
|
||||||
|
@ -41,18 +42,7 @@ class WebInterfaceDataset(dict):
|
||||||
self["Data.CurrentDisk.capacity.percent"] = percent
|
self["Data.CurrentDisk.capacity.percent"] = percent
|
||||||
|
|
||||||
|
|
||||||
def __setConfigValues(self):
|
def setContainersState(self):
|
||||||
self["Settings.TemplateDir"] = os.path.abspath(self.prefs["Locations"]["TemplateDir"])
|
|
||||||
self["Settings.LanguageDir"] = os.path.abspath(self.prefs["Locations"]["LangDir"])
|
|
||||||
self["Settings.DocDir"] = os.path.abspath(self.prefs["Locations"]["DocDir"])
|
|
||||||
self["Settings.Stylesheet"] = self.prefs["WebSettings"]["Stylesheet"]
|
|
||||||
self["Settings.Language"] = self.prefs["WebSettings"]["Language"]
|
|
||||||
self["Settings.DocLang"] = self.prefs["WebSettings"]["DocLanguage"]
|
|
||||||
self["Settings.PluginDir"] = self.prefs["Locations"]["PluginDir"]
|
|
||||||
|
|
||||||
|
|
||||||
def __setCryptoBoxState(self):
|
|
||||||
self["Data.Version"] = self.cbox.VERSION
|
|
||||||
avail_counter = 0
|
avail_counter = 0
|
||||||
active_counter = 0
|
active_counter = 0
|
||||||
for container in self.cbox.getContainerList():
|
for container in self.cbox.getContainerList():
|
||||||
|
@ -67,6 +57,20 @@ class WebInterfaceDataset(dict):
|
||||||
if isMounted: active_counter += 1
|
if isMounted: active_counter += 1
|
||||||
avail_counter += 1
|
avail_counter += 1
|
||||||
self["Data.activeDisksCount"] = active_counter
|
self["Data.activeDisksCount"] = active_counter
|
||||||
|
|
||||||
|
|
||||||
|
def __setConfigValues(self):
|
||||||
|
self["Settings.TemplateDir"] = os.path.abspath(self.prefs["Locations"]["TemplateDir"])
|
||||||
|
self["Settings.LanguageDir"] = os.path.abspath(self.prefs["Locations"]["LangDir"])
|
||||||
|
self["Settings.DocDir"] = os.path.abspath(self.prefs["Locations"]["DocDir"])
|
||||||
|
self["Settings.Stylesheet"] = self.prefs["WebSettings"]["Stylesheet"]
|
||||||
|
self["Settings.Language"] = self.prefs["WebSettings"]["Language"]
|
||||||
|
self["Settings.DocLang"] = self.prefs["WebSettings"]["DocLanguage"]
|
||||||
|
self["Settings.PluginDir"] = self.prefs["Locations"]["PluginDir"]
|
||||||
|
|
||||||
|
|
||||||
|
def __setCryptoBoxState(self):
|
||||||
|
self["Data.Version"] = self.cbox.VERSION
|
||||||
for lang in self.cbox.getAvailableLanguages():
|
for lang in self.cbox.getAvailableLanguages():
|
||||||
self["Data.Languages." + lang] = self.__getLanguageName(lang)
|
self["Data.Languages." + lang] = self.__getLanguageName(lang)
|
||||||
## TODO: open issues: Data.Config.AdminPasswordIsSet
|
## TODO: open issues: Data.Config.AdminPasswordIsSet
|
||||||
|
|
|
@ -34,6 +34,10 @@ class WebInterfaceSites:
|
||||||
|
|
||||||
|
|
||||||
def __resetDataset(self):
|
def __resetDataset(self):
|
||||||
|
"""this method has to be called at the beginning of every "site" action
|
||||||
|
important: only at the beginning of an action (to not loose information)
|
||||||
|
important: for _every_ "site" action (cherrypy is stateful)
|
||||||
|
"""
|
||||||
self.dataset = WebInterfaceDataset.WebInterfaceDataset(self.cbox, self.prefs)
|
self.dataset = WebInterfaceDataset.WebInterfaceDataset(self.cbox, self.prefs)
|
||||||
|
|
||||||
|
|
||||||
|
@ -144,8 +148,6 @@ class WebInterfaceSites:
|
||||||
self.dataset["Data.Warning"] = "SetVolumeNameFailed"
|
self.dataset["Data.Warning"] = "SetVolumeNameFailed"
|
||||||
else:
|
else:
|
||||||
self.log.info("successfully renamed volume '%s' to '%s'" % (device, volume_name))
|
self.log.info("successfully renamed volume '%s' to '%s'" % (device, volume_name))
|
||||||
# reread the dataset
|
|
||||||
self.__resetDataset()
|
|
||||||
self.dataset.setCurrentDiskState(device)
|
self.dataset.setCurrentDiskState(device)
|
||||||
else:
|
else:
|
||||||
self.dataset["Data.Warning"] = "InvalidVolumeName"
|
self.dataset["Data.Warning"] = "InvalidVolumeName"
|
||||||
|
@ -188,8 +190,6 @@ class WebInterfaceSites:
|
||||||
self.log.warn("failed to mount the device (%s)" % device)
|
self.log.warn("failed to mount the device (%s)" % device)
|
||||||
else:
|
else:
|
||||||
self.log.info("successfully mounted the container (%s)" % device)
|
self.log.info("successfully mounted the container (%s)" % device)
|
||||||
# reread the dataset
|
|
||||||
self.__resetDataset()
|
|
||||||
self.dataset.setCurrentDiskState(device)
|
self.dataset.setCurrentDiskState(device)
|
||||||
else:
|
else:
|
||||||
if self.cbox.getContainerList():
|
if self.cbox.getContainerList():
|
||||||
|
@ -264,7 +264,6 @@ class WebInterfaceSites:
|
||||||
else:
|
else:
|
||||||
self.log.info("successfully initialized device '%s'" % device)
|
self.log.info("successfully initialized device '%s'" % device)
|
||||||
# reread the dataset
|
# reread the dataset
|
||||||
self.__resetDataset()
|
|
||||||
self.dataset.setCurrentDiskState(device)
|
self.dataset.setCurrentDiskState(device)
|
||||||
return self.__render("show_volume")
|
return self.__render("show_volume")
|
||||||
else:
|
else:
|
||||||
|
@ -274,8 +273,9 @@ class WebInterfaceSites:
|
||||||
return self.__render("show_status")
|
return self.__render("show_status")
|
||||||
|
|
||||||
|
|
||||||
def test(self):
|
def test(self, weblang=""):
|
||||||
self.__resetDataset()
|
self.__resetDataset()
|
||||||
|
self.__setWebLang(weblang)
|
||||||
return "test passed"
|
return "test passed"
|
||||||
|
|
||||||
|
|
||||||
|
@ -306,7 +306,6 @@ class WebInterfaceSites:
|
||||||
else:
|
else:
|
||||||
self.log.info("successfully unmounted the container (%s)" % device)
|
self.log.info("successfully unmounted the container (%s)" % device)
|
||||||
# reread the dataset
|
# reread the dataset
|
||||||
self.__resetDataset()
|
|
||||||
self.dataset.setCurrentDiskState(device)
|
self.dataset.setCurrentDiskState(device)
|
||||||
else:
|
else:
|
||||||
if self.cbox.getContainerList():
|
if self.cbox.getContainerList():
|
||||||
|
@ -455,6 +454,9 @@ class WebInterfaceSites:
|
||||||
## add the current state of the plugins to the hdf dataset
|
## add the current state of the plugins to the hdf dataset
|
||||||
self.dataset.setPluginState(self.pluginList)
|
self.dataset.setPluginState(self.pluginList)
|
||||||
|
|
||||||
|
## update the container information
|
||||||
|
self.dataset.setContainersState()
|
||||||
|
|
||||||
hdf = neo_util.HDF()
|
hdf = neo_util.HDF()
|
||||||
hdf.readFile(hdf_path)
|
hdf.readFile(hdf_path)
|
||||||
self.log.debug(self.dataset)
|
self.log.debug(self.dataset)
|
||||||
|
|
|
@ -8,10 +8,9 @@ Lang {
|
||||||
Top = Die CryptoBox
|
Top = Die CryptoBox
|
||||||
Slogan = ... und 1984 war gestern!
|
Slogan = ... und 1984 war gestern!
|
||||||
Init = Initialisierung der CryptoBox
|
Init = Initialisierung der CryptoBox
|
||||||
Mount = Aktivierung der Crypto-Daten
|
Mount = Aktivierung des Containers
|
||||||
Umount = Deaktivierung der Crypto-Daten
|
Umount = Deaktivierung des Containers
|
||||||
Config = Konfiguration der CryptoBox
|
Config = Konfiguration der CryptoBox
|
||||||
Log = Protokoll der CryptoBox
|
|
||||||
System = System
|
System = System
|
||||||
Status = Status der CryptoBox
|
Status = Status der CryptoBox
|
||||||
Volume = Eigenschaften von
|
Volume = Eigenschaften von
|
||||||
|
@ -31,7 +30,6 @@ Lang {
|
||||||
PartitionInfo = Derzeitige Partitionierung der Festplatte:
|
PartitionInfo = Derzeitige Partitionierung der Festplatte:
|
||||||
IPAddress = Netzwerk-Adresse (IP) der CryptoBox:
|
IPAddress = Netzwerk-Adresse (IP) der CryptoBox:
|
||||||
TimeOut = Zeitabschaltung des Crypto-Dateisystems (in Minuten):
|
TimeOut = Zeitabschaltung des Crypto-Dateisystems (in Minuten):
|
||||||
EmptyLog = Das Logbuch der CryptoBox ist leer.
|
|
||||||
SelectLanguage = Spracheinstellung:
|
SelectLanguage = Spracheinstellung:
|
||||||
RedirectNote = Klicke hier, falls dein Browser die automatische Weiterleitung nicht unterstützt.
|
RedirectNote = Klicke hier, falls dein Browser die automatische Weiterleitung nicht unterstützt.
|
||||||
ProjectHomePage = Projekt-Seite
|
ProjectHomePage = Projekt-Seite
|
||||||
|
@ -54,12 +52,11 @@ Lang {
|
||||||
DoInit = Initialisierung
|
DoInit = Initialisierung
|
||||||
SaveConfig = Speichere Konfiguration
|
SaveConfig = Speichere Konfiguration
|
||||||
Update = Aktualisieren
|
Update = Aktualisieren
|
||||||
Mount = Crypto-Daten aktivieren
|
Mount = Container aktivieren
|
||||||
Umount = Crypto-Daten deaktivieren
|
Umount = Container deaktivieren
|
||||||
Config = Einstellungen
|
Config = Einstellungen
|
||||||
PowerOff = ausschalten
|
PowerOff = ausschalten
|
||||||
ReBoot = neu starten
|
ReBoot = neu starten
|
||||||
Protocol = Protokoll anzeigen
|
|
||||||
Documentation = Hilfe
|
Documentation = Hilfe
|
||||||
Status = Status
|
Status = Status
|
||||||
System = System
|
System = System
|
||||||
|
|
|
@ -6,9 +6,9 @@ Title.Partition = Disk partitions
|
||||||
|
|
||||||
Button {
|
Button {
|
||||||
SelectDevice = Repartition disk
|
SelectDevice = Repartition disk
|
||||||
AddPartition = Add another partition
|
AddPartition = Add
|
||||||
Back = Back
|
DelPartition = Remove
|
||||||
SavePartitions = Save changes
|
SavePartitions = Write new partition table
|
||||||
AbortPartitions = Cancel
|
AbortPartitions = Cancel
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -20,14 +20,33 @@ Text {
|
||||||
Ext3 = Ext3
|
Ext3 = Ext3
|
||||||
Reiser = Reiser
|
Reiser = Reiser
|
||||||
}
|
}
|
||||||
|
PartNum = Id
|
||||||
|
PartType = Type
|
||||||
Size = Size (MB)
|
Size = Size (MB)
|
||||||
SelectDevice = Choose a disk for partitioning
|
SelectDevice = Choose a disk for partitioning
|
||||||
NoDevicesAvailable = No suitable disks found - please check your configuration and hardware setup.
|
WarningMessage = If you continue, you will destroy all data on the choosen disk. Please be careful!
|
||||||
|
}
|
||||||
|
|
||||||
|
SuccessMessage {
|
||||||
WarningMessage {
|
Partitioned {
|
||||||
InvalidInput {
|
Title = Partitioning complete
|
||||||
Title = Invalid input
|
Text = The disk was partitioned successfully.
|
||||||
Text = You entered an invalid value.
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
WarningMessage {
|
||||||
|
NoDisksAvailable {
|
||||||
|
Title = No disks found
|
||||||
|
Text = No suitable disks found - please check your configuration and hardware setup.
|
||||||
|
}
|
||||||
|
|
||||||
|
PartitioningFailed {
|
||||||
|
Title = Partitioning failed
|
||||||
|
Text = The partitioning of the device failed for some reason - sorry!
|
||||||
|
}
|
||||||
|
|
||||||
|
DiskIsBusy {
|
||||||
|
Title = This disk is busy
|
||||||
|
Text = Please deactivate all containers of this disk before partitioning.
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,15 +28,24 @@ def doAction(hdf, cbox, **args):
|
||||||
|
|
||||||
|
|
||||||
def getStatus(cbox):
|
def getStatus(cbox):
|
||||||
#return "%d.%d.%d.%d" % __getCurrentIP(cbox)
|
|
||||||
return "TODO"
|
return "TODO"
|
||||||
|
|
||||||
|
|
||||||
def __isDeviceValid(device, cbox):
|
def __isDeviceValid(device, cbox):
|
||||||
|
## TODO: also check for "is device busy" add output a warning
|
||||||
if not cbox.isDeviceAllowed(device):
|
if not cbox.isDeviceAllowed(device):
|
||||||
return False
|
return False
|
||||||
if not device in CryptoBoxTools.getParentBlockDevices():
|
if not device in CryptoBoxTools.getParentBlockDevices():
|
||||||
return False
|
return False
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
|
def __isDeviceBusy(device, cbox):
|
||||||
|
"""check if the device (or one of its partitions) is mounted"""
|
||||||
|
for c in cbox.getContainerList():
|
||||||
|
if re.match(device + "\d*$", c.getDevice()):
|
||||||
|
if c.isMounted(): return True
|
||||||
|
return False
|
||||||
|
|
||||||
|
|
||||||
def __actionSelectDevice(hdf, cbox, args):
|
def __actionSelectDevice(hdf, cbox, args):
|
||||||
|
@ -48,6 +57,9 @@ def __actionSelectDevice(hdf, cbox, args):
|
||||||
hdf["Data.Plugins.partition.BlockDevices.%d" % counter] = a
|
hdf["Data.Plugins.partition.BlockDevices.%d" % counter] = a
|
||||||
cbox.log.debug("found a suitable block device: %s" % a)
|
cbox.log.debug("found a suitable block device: %s" % a)
|
||||||
counter += 1
|
counter += 1
|
||||||
|
## there is no disk available
|
||||||
|
if not block_devices:
|
||||||
|
hdf["Data.Warning"] = "Plugins.partition.NoDisksAvailable"
|
||||||
return "select_device"
|
return "select_device"
|
||||||
|
|
||||||
|
|
||||||
|
@ -56,8 +68,10 @@ def __actionAddPartition(hdf, cbox, args):
|
||||||
device = args["block_device"]
|
device = args["block_device"]
|
||||||
except KeyError:
|
except KeyError:
|
||||||
return __actionSelectDevice(hdf, cbox, args)
|
return __actionSelectDevice(hdf, cbox, args)
|
||||||
#FIXME: the following check should obviuosly get reversed
|
if not __isDeviceValid(device, cbox): return __actionSelectDevice(hdf, cbox, args)
|
||||||
if __isDeviceValid(device, cbox): return __actionSelectDevice(hdf, cbox, args)
|
if __isDeviceBusy(device, cbox):
|
||||||
|
hdf["Data.Warning"] = "Plugins.partition.DiskIsBusy"
|
||||||
|
return __actionSelectDevice(hdf, cbox, args)
|
||||||
size = __getDeviceSize(device)
|
size = __getDeviceSize(device)
|
||||||
hdf["Data.Plugins.partition.Device"] = device
|
hdf["Data.Plugins.partition.Device"] = device
|
||||||
hdf["Data.Plugins.partition.Device.Size"] = size
|
hdf["Data.Plugins.partition.Device.Size"] = size
|
||||||
|
@ -69,18 +83,49 @@ def __actionAddPartition(hdf, cbox, args):
|
||||||
def __actionDelPartition(hdf, cbox, args):
|
def __actionDelPartition(hdf, cbox, args):
|
||||||
try:
|
try:
|
||||||
device = args["block_device"]
|
device = args["block_device"]
|
||||||
except KeyError:
|
part_num = int(args["del_num"])
|
||||||
|
except (TypeError,KeyError):
|
||||||
|
return __actionSelectDevice(hdf, cbox, args)
|
||||||
|
if not __isDeviceValid(device, cbox): return __actionSelectDevice(hdf, cbox, args)
|
||||||
|
if __isDeviceBusy(device, cbox):
|
||||||
|
hdf["Data.Warning"] = "Plugins.partition.DiskIsBusy"
|
||||||
return __actionSelectDevice(hdf, cbox, args)
|
return __actionSelectDevice(hdf, cbox, args)
|
||||||
#FIXME: the following check should obviuosly get reversed
|
|
||||||
if __isDeviceValid(device, cbox): return __actionSelectDevice(hdf, cbox, args)
|
|
||||||
size = __getDeviceSize(device)
|
size = __getDeviceSize(device)
|
||||||
hdf["Data.Plugins.partition.Device"] = device
|
hdf["Data.Plugins.partition.Device"] = device
|
||||||
hdf["Data.Plugins.partition.Device.Size"] = size
|
hdf["Data.Plugins.partition.Device.Size"] = size
|
||||||
parts = __getPartitionsFromArgs(args, size)
|
parts = __getPartitionsFromArgs(args, size)
|
||||||
__setPartitionData(hdf, parts[:-1], size)
|
## valid partition number to be deleted?
|
||||||
|
if part_num < len(parts):
|
||||||
|
del parts[part_num]
|
||||||
|
else:
|
||||||
|
return __actionSelectDevice(hdf, cbox, args)
|
||||||
|
__setPartitionData(hdf, parts, size)
|
||||||
return "set_partitions"
|
return "set_partitions"
|
||||||
|
|
||||||
|
|
||||||
|
def __actionFinish(hdf, cbox, args):
|
||||||
|
try:
|
||||||
|
device = args["block_device"]
|
||||||
|
except KeyError:
|
||||||
|
return __actionSelectDevice(hdf, cbox, args)
|
||||||
|
if not __isDeviceValid(device, cbox): return __actionSelectDevice(hdf, cbox, args)
|
||||||
|
if __isDeviceBusy(device, cbox):
|
||||||
|
hdf["Data.Warning"] = "Plugins.partition.DiskIsBusy"
|
||||||
|
return __actionSelectDevice(hdf, cbox, args)
|
||||||
|
size = __getDeviceSize(device)
|
||||||
|
parts = __getPartitionsFromArgs(args, size)
|
||||||
|
if parts:
|
||||||
|
if not __runFDisk(cbox, device, parts):
|
||||||
|
hdf["Data.Warning"] = "Plugins.partition.PartitioningFailed"
|
||||||
|
return __actionAddPartition(hdf, cbox, args)
|
||||||
|
else:
|
||||||
|
hdf["Data.Success"] = "Plugins.partition.Partitioned"
|
||||||
|
cbox.reReadContainerList()
|
||||||
|
return "form_system"
|
||||||
|
else:
|
||||||
|
return __actionSelectDevice(hdf, cbox, args)
|
||||||
|
|
||||||
|
|
||||||
def __setPartitionData(hdf, parts, size):
|
def __setPartitionData(hdf, parts, size):
|
||||||
availSize = size
|
availSize = size
|
||||||
i = 0
|
i = 0
|
||||||
|
@ -126,8 +171,41 @@ def __getDeviceSize(device):
|
||||||
elements = f.split()
|
elements = f.split()
|
||||||
if len(elements) != 4: continue
|
if len(elements) != 4: continue
|
||||||
if (int(elements[0]) == major) and (int(elements[1]) == minor):
|
if (int(elements[0]) == major) and (int(elements[1]) == minor):
|
||||||
return int(elements[2])
|
return int(elements[2])/1024
|
||||||
except ValueError:
|
except ValueError:
|
||||||
pass
|
pass
|
||||||
return 0
|
return 0
|
||||||
|
|
||||||
|
|
||||||
|
def __runFDisk(cbox, device, parts):
|
||||||
|
proc = subprocess.Popen(
|
||||||
|
shell = False,
|
||||||
|
stdin = subprocess.PIPE,
|
||||||
|
stderr = subprocess.PIPE,
|
||||||
|
args = [
|
||||||
|
cbox.prefs["Programs"]["super"],
|
||||||
|
cbox.prefs["Programs"]["CryptoBoxRootActions"],
|
||||||
|
"plugin",
|
||||||
|
os.path.join(os.path.dirname(__file__), "root_action.py"),
|
||||||
|
"partition",
|
||||||
|
device])
|
||||||
|
import logging
|
||||||
|
logger = logging.getLogger("CryptoBox")
|
||||||
|
for line in __getSFDiskLayout(parts): proc.stdin.write(line + "\n")
|
||||||
|
(output, error) = proc.communicate()
|
||||||
|
if error: logger.debug("partitioning failed: %s" % error)
|
||||||
|
return proc.returncode == 0
|
||||||
|
|
||||||
|
|
||||||
|
def __getSFDiskLayout(paramParts):
|
||||||
|
parts = paramParts[:]
|
||||||
|
## first a primary partition
|
||||||
|
yield ",%d,%s,*" % (parts[0]["size"], PartTypes[parts[0]["type"]])
|
||||||
|
del parts[0]
|
||||||
|
if not parts: return
|
||||||
|
yield ",,E" # extended container for the rest
|
||||||
|
yield ";" # empty partition in main table
|
||||||
|
yield ";" # another empty partition in main table
|
||||||
|
while parts:
|
||||||
|
yield ",%d,%s" % (parts[0]["size"], PartTypes[parts[0]["type"]])
|
||||||
|
del parts[0]
|
||||||
|
|
|
@ -1,10 +1,9 @@
|
||||||
#!/usr/bin/env python2.4
|
#!/usr/bin/env python2.4
|
||||||
|
|
||||||
#TODO: add netmask and gateway
|
|
||||||
|
|
||||||
## necessary: otherwise CryptoBoxRootActions.py will refuse to execute this script
|
## necessary: otherwise CryptoBoxRootActions.py will refuse to execute this script
|
||||||
PLUGIN_TYPE = "cryptobox"
|
PLUGIN_TYPE = "cryptobox"
|
||||||
|
|
||||||
|
SFDISK_BIN = "/sbin/sfdisk"
|
||||||
|
|
||||||
import subprocess
|
import subprocess
|
||||||
import re
|
import re
|
||||||
|
@ -12,12 +11,24 @@ import sys
|
||||||
import os
|
import os
|
||||||
|
|
||||||
|
|
||||||
|
def __partitionDevice(device):
|
||||||
|
## do not use the "-q" flag, as this spoils the exit code of sfdisk (seems to be a bug)
|
||||||
|
proc = subprocess.Popen(
|
||||||
|
shell = False,
|
||||||
|
args = [
|
||||||
|
SFDISK_BIN,
|
||||||
|
"-uM",
|
||||||
|
device])
|
||||||
|
proc.communicate()
|
||||||
|
return proc.returncode == 0
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
args = sys.argv[1:]
|
args = sys.argv[1:]
|
||||||
|
|
||||||
self_bin =sys.argv[0]
|
self_bin =sys.argv[0]
|
||||||
|
|
||||||
if len(args) > 1:
|
if len(args) > 2:
|
||||||
sys.stderr.write("%s: too many arguments (%s)\n" % (self_bin, args))
|
sys.stderr.write("%s: too many arguments (%s)\n" % (self_bin, args))
|
||||||
sys.exit(1)
|
sys.exit(1)
|
||||||
|
|
||||||
|
@ -25,9 +36,14 @@ if __name__ == "__main__":
|
||||||
sys.stderr.write("%s: no argument supplied\n" % self_bin)
|
sys.stderr.write("%s: no argument supplied\n" % self_bin)
|
||||||
sys.exit(1)
|
sys.exit(1)
|
||||||
|
|
||||||
proc = subprocess.Popen(
|
if args[0] == "partition":
|
||||||
shell = False,
|
if len(args) < 2:
|
||||||
args = [IFCONFIG_BIN, IFACE, args[0]])
|
sys.stderr.write("%s: not enough arguments (%s)\n" % (self_bin, args))
|
||||||
proc.communicate()
|
sys.exit(1)
|
||||||
sys.exit(proc.returncode)
|
if __partitionDevice(args[1]):
|
||||||
|
sys.exit(0)
|
||||||
|
else:
|
||||||
|
sys.exit(1)
|
||||||
|
else:
|
||||||
|
sys.exit(1)
|
||||||
|
|
||||||
|
|
|
@ -13,15 +13,17 @@
|
||||||
<?cs /each ?>
|
<?cs /each ?>
|
||||||
</select></p>
|
</select></p>
|
||||||
|
|
||||||
|
<p class="note">
|
||||||
|
<?cs var:html_escape(Lang.Plugins.partition.Text.WarningMessage) ?>
|
||||||
|
</p>
|
||||||
|
|
||||||
<input type="hidden" name="step" value="add_partition" />
|
<input type="hidden" name="step" value="add_partition" />
|
||||||
|
|
||||||
<button type="submit"><?cs var:html_escape(Lang.Plugins.partition.Button.SelectDevice) ?></button>
|
<button type="submit"><?cs var:html_escape(Lang.Plugins.partition.Button.SelectDevice) ?></button>
|
||||||
|
|
||||||
</form>
|
</form>
|
||||||
|
|
||||||
<?cs else ?>
|
|
||||||
|
|
||||||
<p><?cs var:html_escape(Lang.Plugins.partition.Text.NoDevicesAvailable) ?></p>
|
|
||||||
|
|
||||||
<?cs /if ?>
|
<?cs /if ?>
|
||||||
|
|
||||||
|
<?cs # a warning will be displayed if there are no disks available ?>
|
||||||
|
|
||||||
|
|
|
@ -2,32 +2,56 @@
|
||||||
|
|
||||||
<h1><?cs var:html_escape(Lang.Plugins.partition.Title.Partition) ?></h1>
|
<h1><?cs var:html_escape(Lang.Plugins.partition.Title.Partition) ?></h1>
|
||||||
|
|
||||||
<p> <?cs loop: x = #0, subcount(Data.Plugins.partition.Parts)-1, #1 ?>
|
<div align="center">
|
||||||
<p><?cs var:x ?> - <?cs var:Data.Plugins.partition.Parts[x].Size ?> - <?cs var:Data.Plugins.partition.Parts[x].Type ?></p><?cs
|
<table class="partition">
|
||||||
/loop ?></p>
|
<tr>
|
||||||
|
<th><?cs var:html_escape(Lang.Plugins.partition.Text.PartNum) ?></th>
|
||||||
|
<th><?cs var:html_escape(Lang.Plugins.partition.Text.Size) ?></th>
|
||||||
|
<th><?cs var:html_escape(Lang.Plugins.partition.Text.PartType) ?></th>
|
||||||
|
<th></th>
|
||||||
|
</tr>
|
||||||
|
|
||||||
<?cs if:Data.Plugins.partition.availSize ?>
|
<?cs loop: x = #0, subcount(Data.Plugins.partition.Parts)-1, #1 ?>
|
||||||
<?cs call:print_form_header("plugins/partition") ?>
|
<tr>
|
||||||
<?cs include:Settings.PluginDir + "/partition/current_partition_info.cs" ?><?cs
|
<td><?cs var:x ?></td>
|
||||||
|
<td><?cs var:Data.Plugins.partition.Parts[x].Size ?></td>
|
||||||
# new partition input if space is available ?><?cs
|
<td><?cs var:Data.Plugins.partition.Parts[x].Type ?></td>
|
||||||
set: x = subcount(Data.Plugins.partition.Parts) ?>
|
<td>
|
||||||
<p><?cs var:x ?> - <input type="text" name="part<?cs var:x ?>_size" value="<?cs var:Data.Plugins.partition.availSize ?>" /> - <select name="part<?cs var:x ?>_type" size="0"><?cs each: t = Data.Plugins.partition.Types ?><option><?cs var:t ?></option><?cs /each ?></select></p>
|
<?cs call:print_form_header("plugins/partition") ?>
|
||||||
|
|
||||||
<input type="hidden" name="step" value="add_partition" />
|
|
||||||
<button type="submit"><?cs var:html_escape(Lang.Plugins.partition.Button.AddPartition) ?></button>
|
|
||||||
</form>
|
|
||||||
<?cs /if ?>
|
|
||||||
|
|
||||||
<?cs if:subcount(Data.Plugins.partition.Parts) > 0 ?>
|
|
||||||
<?cs call:print_form_header("plugins/partition") ?>
|
|
||||||
<?cs include:Settings.PluginDir + "/partition/current_partition_info.cs" ?>
|
<?cs include:Settings.PluginDir + "/partition/current_partition_info.cs" ?>
|
||||||
<input type="hidden" name="step" value="del_partition" />
|
<input type="hidden" name="step" value="del_partition" />
|
||||||
<button type="submit"><?cs var:html_escape(Lang.Plugins.partition.Button.Back) ?></button>
|
<input type="hidden" name="del_num" value="<?cs var:x ?>" />
|
||||||
|
<button type="submit"><?cs var:html_escape(Lang.Plugins.partition.Button.DelPartition) ?></button>
|
||||||
|
</form>
|
||||||
|
</td>
|
||||||
|
</tr>
|
||||||
|
<?cs /loop ?></p>
|
||||||
|
|
||||||
|
<?cs # new partition input if space is available ?>
|
||||||
|
<?cs if:Data.Plugins.partition.availSize > 0 ?>
|
||||||
|
<tr>
|
||||||
|
<?cs call:print_form_header("plugins/partition") ?>
|
||||||
|
<?cs include:Settings.PluginDir + "/partition/current_partition_info.cs" ?>
|
||||||
|
<input type="hidden" name="step" value="add_partition" />
|
||||||
|
<?cs set: x = subcount(Data.Plugins.partition.Parts) ?>
|
||||||
|
<td><?cs var:x ?></td>
|
||||||
|
<td><input type="text" name="part<?cs var:x ?>_size" size="8" value="<?cs var:Data.Plugins.partition.availSize ?>" /></td>
|
||||||
|
<td><select name="part<?cs var:x ?>_type" size="0"><?cs each: t = Data.Plugins.partition.Types ?><option><?cs var:t ?></option><?cs /each ?></select></td>
|
||||||
|
<td>
|
||||||
|
<button type="submit"><?cs var:html_escape(Lang.Plugins.partition.Button.AddPartition) ?></button>
|
||||||
|
</td>
|
||||||
</form>
|
</form>
|
||||||
|
</tr>
|
||||||
<?cs /if ?>
|
<?cs /if ?>
|
||||||
|
</table>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
|
||||||
<?cs if:subcount(Data.Plugins.partition.Parts) > 0 ?>
|
<?cs if:subcount(Data.Plugins.partition.Parts) > 0 ?>
|
||||||
|
<p class="note">
|
||||||
|
<?cs var:html_escape(Lang.Plugins.partition.Text.WarningMessage) ?>
|
||||||
|
</p>
|
||||||
|
|
||||||
<?cs call:print_form_header("plugins/partition") ?>
|
<?cs call:print_form_header("plugins/partition") ?>
|
||||||
<?cs include:Settings.PluginDir + "/partition/current_partition_info.cs" ?>
|
<?cs include:Settings.PluginDir + "/partition/current_partition_info.cs" ?>
|
||||||
<input type="hidden" name="step" value="finish" />
|
<input type="hidden" name="step" value="finish" />
|
||||||
|
|
|
@ -1,25 +1,11 @@
|
||||||
<?cs # $Id$ ?>
|
<?cs # $Id$ ?>
|
||||||
|
|
||||||
<?cs # mounting possible? ?>
|
<?cs # status ?>
|
||||||
<?cs if:((Data.Status.Config == 1) && (Data.Status.InitRunning == 0)) ?>
|
<a href="<?cs call:link('status','','','','') ?>" title="<?cs var:html_escape(Lang.Button.Status) ?>"><?cs var:html_escape(Lang.Button.Status) ?></a>
|
||||||
|
|
||||||
<!-- TODO: remove the following lines, as soon as we completely switched to the volume-based user interface
|
<?cs # system ?>
|
||||||
<?cs if:subcount(Data.Disks.passive) > 0 ?>
|
<a href="<?cs call:link('system','','','','') ?>" title="<?cs var:html_escape(Lang.Button.System) ?>"><?cs var:html_escape(Lang.Button.System) ?></a>
|
||||||
<a href="<?cs call:link('mount_ask','','','','') ?>" title="<?cs var:html_escape(Lang.Text.DoMount) ?>"><?cs var:html_escape(Lang.Button.Mount) ?></a><?cs /if ?>
|
|
||||||
<?cs if:Data.activeDisksCount > 0 ?>
|
|
||||||
<a href="<?cs call:link('umount_ask','','','','') ?>" title="<?cs var:html_escape(Lang.Text.DoUmount) ?>"><?cs var:html_escape(Lang.Button.Umount) ?></a><?cs /if ?>
|
|
||||||
-->
|
|
||||||
|
|
||||||
<a href="<?cs if:subcount(Data.Disks) > 1
|
|
||||||
?><?cs call:link('show_status','','','','')
|
|
||||||
?><?cs else
|
|
||||||
?><?cs call:link('show_volume','device',Data.Disks.0.device,'','')
|
|
||||||
?><?cs /if
|
|
||||||
?>" title="<?cs var:html_escape(Lang.Button.Status) ?>"><?cs var:html_escape(Lang.Button.Status) ?></a>
|
|
||||||
<?cs /if ?>
|
|
||||||
|
|
||||||
<?cs # manual ?>
|
<?cs # manual ?>
|
||||||
<a href="<?cs call:link('doc','','','','') ?>" title="<?cs var:html_escape(Lang.Button.Documentation) ?>"><?cs var:html_escape(Lang.Button.Documentation) ?></a>
|
<a href="<?cs call:link('doc','','','','') ?>" title="<?cs var:html_escape(Lang.Button.Documentation) ?>"><?cs var:html_escape(Lang.Button.Documentation) ?></a>
|
||||||
<a href="<?cs call:link('status','','','','') ?>" title="<?cs var:html_escape(Lang.Button.Status) ?>"><?cs var:html_escape(Lang.Button.Status) ?></a>
|
|
||||||
<a href="<?cs call:link('system','','','','') ?>" title="<?cs var:html_escape(Lang.Button.System) ?>"><?cs var:html_escape(Lang.Button.System) ?></a>
|
|
||||||
|
|
||||||
|
|
|
@ -6,7 +6,9 @@
|
||||||
<a href="<?cs call:link('show_volume','device',Data.Disks[index].device,'','') ?>" title="<?cs
|
<a href="<?cs call:link('show_volume','device',Data.Disks[index].device,'','') ?>" title="<?cs
|
||||||
var:Data.Disks[index].name ?>">
|
var:Data.Disks[index].name ?>">
|
||||||
<?cs # the "div" is the container for the background image ?>
|
<?cs # the "div" is the container for the background image ?>
|
||||||
<div class="<?cs if:Data.Disks[index].active ?>active<?cs else ?>passive<?cs /if ?><?cs
|
<div class="<?cs if:Data.Disks[index].active ?>active<?cs
|
||||||
|
elif:Data.Disks[index].encryption || Data.Disks[index].plaintext ?>passive<?cs
|
||||||
|
else ?>void<?cs /if ?><?cs
|
||||||
if:Data.Disks[index].device == Data.CurrentDisk.device ?> current<?cs /if ?>">
|
if:Data.Disks[index].device == Data.CurrentDisk.device ?> current<?cs /if ?>">
|
||||||
<p><?cs var:Data.Disks[index].name ?></p>
|
<p><?cs var:Data.Disks[index].name ?></p>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -319,6 +319,10 @@ button:hover {
|
||||||
background-image: url(disc_green.png);
|
background-image: url(disc_green.png);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#volumes div.void {
|
||||||
|
background-image: url(disc_gray.png);
|
||||||
|
}
|
||||||
|
|
||||||
#volumes div.current {
|
#volumes div.current {
|
||||||
border-style: dashed;
|
border-style: dashed;
|
||||||
border-width: 2px;
|
border-width: 2px;
|
||||||
|
@ -422,3 +426,14 @@ button:hover {
|
||||||
color: #909090;
|
color: #909090;
|
||||||
margin-top: 0px;
|
margin-top: 0px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// TODO: move this to the plugin "partition" (inline include with cs)
|
||||||
|
#words div.partition {
|
||||||
|
text-align: center;
|
||||||
|
align: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
table.partition tr td{
|
||||||
|
text-align: center
|
||||||
|
}
|
||||||
|
|
BIN
pythonrewrite/www-data/disc_gray.png
Normal file
BIN
pythonrewrite/www-data/disc_gray.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 4.4 KiB |
Binary file not shown.
Before Width: | Height: | Size: 4.6 KiB After Width: | Height: | Size: 4.8 KiB |
Binary file not shown.
Before Width: | Height: | Size: 4.7 KiB After Width: | Height: | Size: 4.9 KiB |
Loading…
Reference in a new issue