diff options
author | Igor Pashev <pashev.igor@gmail.com> | 2012-06-24 17:06:39 +0000 |
---|---|---|
committer | Igor Pashev <pashev.igor@gmail.com> | 2012-06-24 17:06:39 +0000 |
commit | fb71d4fb8584b77db037d836652617d635f6bb2a (patch) | |
tree | 0db40b2cfa6099f03cb446a2c22a30d48f2ec1a5 | |
parent | 66531f95525651ec9bb15b368d2dfc355805c9c4 (diff) | |
download | live-fb71d4fb8584b77db037d836652617d635f6bb2a.tar.gz |
Use class Disk to represent disks
-rw-r--r-- | lib/__init__.py | 0 | ||||
-rw-r--r-- | lib/hdd/__init__.py | 116 | ||||
-rwxr-xr-x | setup | 117 |
3 files changed, 132 insertions, 101 deletions
diff --git a/lib/__init__.py b/lib/__init__.py new file mode 100644 index 0000000..e69de29 --- /dev/null +++ b/lib/__init__.py diff --git a/lib/hdd/__init__.py b/lib/hdd/__init__.py new file mode 100644 index 0000000..8c63933 --- /dev/null +++ b/lib/hdd/__init__.py @@ -0,0 +1,116 @@ +#!/usr/bin/python + +import subprocess +import sys +import re +import pprint + +def humanCapasity(b): + b = float(b) + G = ['%.0f B', '%.2f KB', '%.2f MB', '%.2f GB', '%.2f TB'] + for p in G: + if b < 1024: + return p % b + else: + b /= 1024 + raise 'Too large hard drive ;-)' + + +class Disk(object): + # fdisk -G /dev/rdsk/c0t0d0p0 + # * Physical geometry for device /dev/rdsk/c0t0d0p0 + # * PCYL NCYL ACYL BCYL NHEAD NSECT SECSIZ + # 2088 2088 0 0 255 63 512 + _fdiskG = re.compile('\s*(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s*') + + # fdisk -W - /dev/rdsk/c0t0d0p0 + #* Id Act Bhead Bsect Bcyl Ehead Esect Ecyl Rsect Numsect + # 191 128 65 2 0 168 44 380 4096 6111232 + # 0 0 0 0 0 0 0 0 0 0 + # 0 0 0 0 0 0 0 0 0 0 + # 0 0 0 0 0 0 0 0 0 0 + _fdiskW = re.compile('\s*(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s*') + + _name = None + _desc = None + _geometry = {} + _capacity = 0 + _capacity_human = None + _partitions = [] + _raw_device = None + + @property + def name(self): + return self._name + + @property + def desc(self): + return self._desc + + @desc.setter + def desc(self, desc): + self._desc = desc + + def read_partitions(): + self._partitions = {} + out = subprocess.Popen(['fdisk', '-W', '-', self._raw_device], + stdout=subprocess.PIPE).stdout + for line in out: + m = self._fdiskW.match(line) + if m: + self._partitions.append({ + 'id' : int(m.group(1)), + 'rsect' : int(m.group(9)), + 'numsect' : int(m.group(10)), + 'cap' : humanCapasity(int(m.group(10))*self._geometry['secsiz']), + }) + + @name.setter + def name(self, name): + """ Set disk name and update disk's info: capacity, geometry etc.""" + if name != self._name: + self._raw_device = '/dev/rdsk/{}p0'.format(name) + self._name = name + out = subprocess.Popen(['fdisk', '-G', self._raw_device], + stdout=subprocess.PIPE).stdout + for line in out: + m = self._fdiskG.match(line) + if m: + self._geometry = { + 'pcyl' : int(m.group(1)), + 'ncyl' : int(m.group(2)), + 'acyl' : int(m.group(3)), + 'bcyl' : int(m.group(4)), + 'nhead' : int(m.group(5)), + 'nsect' : int(m.group(6)), + 'secsiz' : int(m.group(7)), + } + self._capacity = ( self._geometry['ncyl'] * self._geometry['nhead'] * + self._geometry['nsect'] * self._geometry['secsiz'] ) + assert self._capacity != 0 + self._capacity_human = humanCapasity(self._capacity) + + @property + def geometry(self): + return self._geometry + + @property + def partitions(self): + return self._partitions + + @property + def capacity(self): + """ Capacity in bytes """ + return self._capacity + + @property + def cap(self): + """ Human readable capacity string, e. g. 30 GB """ + return self._capacity_human + + def __init__(self, name, desc=None): + self.name = name + self.desc = desc + pass + + @@ -6,128 +6,43 @@ import sys import re import pprint -d = dialog.Dialog() +from lib.hdd import Disk + +d = dialog.Dialog(dialog='whiptail') d.setBackgroundTitle('Dyson Installer') HDD = {} -POOLS = {} RPOOL = 'rpool' - -def bytes_for_human(b): - b = float(b) - G = ['%.0f B', '%.2f KB', '%.2f MB', '%.2f GB', '%.2f TB'] - for p in G: - if b < 1024: - return p % b - else: - b /= 1024 - raise 'Too large hard drive ;-)' - -# fdisk -G /dev/rdsk/c0t0d0p0 -# * Physical geometry for device /dev/rdsk/c0t0d0p0 -# * PCYL NCYL ACYL BCYL NHEAD NSECT SECSIZ -# 2088 2088 0 0 255 63 512 -re_fdiskG = re.compile('\s*(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s*') - -def get_hdd_geometry(dsk): - out = subprocess.Popen(['fdisk', '-G', '/dev/rdsk/' + dsk + 'p0'], - stdout=subprocess.PIPE).stdout - for line in out: - m = re_fdiskG.match(line) - if m: - cap = int(m.group(2)) * int(m.group(5)) * int(m.group(6)) * int(m.group(7)) - return { - 'pcyl' : int(m.group(1)), - 'ncyl' : int(m.group(2)), - 'acyl' : int(m.group(3)), - 'bcyl' : int(m.group(4)), - 'nhead' : int(m.group(5)), - 'nsect' : int(m.group(6)), - 'secsiz' : int(m.group(7)), - } - - -# fdisk -W - /dev/rdsk/c0t0d0p0 -#* Id Act Bhead Bsect Bcyl Ehead Esect Ecyl Rsect Numsect -# 191 128 65 2 0 168 44 380 4096 6111232 -# 0 0 0 0 0 0 0 0 0 0 -# 0 0 0 0 0 0 0 0 0 0 -# 0 0 0 0 0 0 0 0 0 0 -re_fdiskW = re.compile('\s*(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s+(\d+)\s*') -def get_fdisk_partitions(dsk): - res = [] - out = subprocess.Popen(['fdisk', '-W', '-', '/dev/rdsk/' + dsk + 'p0'], - stdout=subprocess.PIPE).stdout - for line in out: - m = re_fdiskW.match(line) - if m: - res.append({ - 'id' : int(m.group(1)), - 'act' : int(m.group(2)), - 'bhead' : int(m.group(3)), - 'bsect' : int(m.group(4)), - 'bcyl' : int(m.group(5)), - 'ehead' : int(m.group(6)), - 'esect' : int(m.group(7)), - 'ecyl' : int(m.group(8)), - 'rsect' : int(m.group(9)), - 'numsect' : int(m.group(10)), - }) - return res - - - -def get_hdd(): +def read_hdd(): + global HDD pat = re.compile('\d+\.\s+(\S+)\s+<(\S+)\s*.+>') out = subprocess.Popen('format </dev/null', shell=True, stdout=subprocess.PIPE).stdout + HDD = {} for line in out: m = pat.search(line) if m: name = m.group(1) - geom = get_hdd_geometry(name) - HDD[name] = { - 'geom' : geom, - 'desc' : m.group(2), - 'cap' : bytes_for_human(geom['ncyl']*geom['nhead']*geom['nsect']*geom['secsiz']), - 'use' : 0, - } + HDD[name] = Disk(name, m.group(2)) if len(HDD) == 0: d.msgbox(width=50, title='Error: no disks found', text='\nSorry, no hard disks found on your system. Installation is not possible.') sys.exit(1) - # if there is only one disk, use it by default: -# if len(HDD) == 1: -# HDD[0]['use'] = 1 def choose_hdd(): while True: choices = [] - for hdd in HDD: - props = HDD[hdd] - choices.append((hdd, props['cap'] + ', ' + props['desc'], props['use'])) - (code, disks) = d.checklist(choices=sorted(choices), width=70, height=20, - title='Choose disks to use for ZFS root pool', - text=''' -Each disk you choose should have a Solaris partition. \ -Only one Solaris partition per disk is allowed. \ -The partition can be a logical partition within an existing extended partition. \ -If disk does not have a Solaris partition you will be asked to create one.''') - if code: - break - if len(disks) > 0: - for h in HDD: - if h in disks: - HDD[h]['use'] = 1 - else: - HDD[h]['use'] = 0 - break - else: - d.msgbox(width=40, height=8, title='You need at least one disk', - text='\nPlease choose at least one disk.') + for hdd in sorted(HDD): + choices.append((hdd, HDD[hdd].cap + ' ' + HDD[hdd].desc)) + + cancel, disk = d.menu(choices=choices, width=70, height=20, + title='Choose a disk for ZFS root pool', + text='') + if cancel: + return False def welcome(): no = d.yesno(width=60, height=20, title='Welcome to Dyson installer', @@ -161,6 +76,6 @@ def choose_rpool_name(): welcome() choose_rpool_name() -get_hdd() +read_hdd() choose_hdd() #pprint.pprint(p) |