summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--fsset.py32
-rw-r--r--lvm.py24
-rw-r--r--lvmErrors.py10
-rw-r--r--packages.py5
-rw-r--r--partRequests.py23
-rw-r--r--partitions.py23
6 files changed, 103 insertions, 14 deletions
diff --git a/fsset.py b/fsset.py
index 6ff118922..1065d8b84 100644
--- a/fsset.py
+++ b/fsset.py
@@ -1502,7 +1502,8 @@ MAILADDR root
if bootPart:
del bootPart
- def resizeFilesystems (self, chroot = '/', shrink = False, grow = False):
+ def resizeFilesystems (self, diskset, chroot = '/', shrink = False, grow = False):
+ todo = []
for entry in self.entries:
if not entry.fsystem or not entry.fsystem.isResizable():
continue
@@ -1512,13 +1513,34 @@ MAILADDR root
continue
if grow and not (entry.resizeTargetSize > entry.resizeOrigSize):
continue
+ todo.append(entry)
+ if len(todo) == 0:
+ return
+
+ # we have to have lvm activated to be able to do resizes of LVs
+ active = lvm.vgcheckactive()
+ if not active:
+ diskset.startMPath()
+ diskset.startDmRaid()
+ diskset.startMdRaid()
+
+ lvm.vgscan()
+ lvm.vgactivate()
+
+ for entry in todo:
entry.fsystem.resize(entry, entry.resizeTargetSize,
self.progressWindow, chroot)
- def shrinkFilesystems (self, chroot):
- self.resizeFilesystems(chroot, shrink = True)
- def growFilesystems (self, chroot):
- self.resizeFilesystems(chroot, grow = True)
+ if not active:
+ lvm.vgdeactivate()
+ diskset.stopMPath()
+ diskset.stopDmRaid()
+ diskset.stopMdRaid()
+
+ def shrinkFilesystems (self, diskset, chroot):
+ self.resizeFilesystems(diskset, chroot, shrink = True)
+ def growFilesystems (self, diskset, chroot):
+ self.resizeFilesystems(diskset, chroot, grow = True)
def formatSwap (self, chroot, forceFormat=False):
formatted = []
diff --git a/lvm.py b/lvm.py
index e1ead92e8..4e14ac45d 100644
--- a/lvm.py
+++ b/lvm.py
@@ -200,6 +200,22 @@ def lvremove(lvname, vgname):
if rc:
raise LVRemoveError(vgname, lvname)
+def lvresize(lvname, vgname, size):
+ global lvmDevicePresent
+ if flags.test or lvmDevicePresent == 0:
+ return
+
+ args = ["lvresize", "-An", "-L", "%dM" %(size,), "-v",
+ "/dev/%s/%s" %(vgname, lvname,)]
+
+ try:
+ rc = lvmExec(*args)
+ except:
+ rc = 1
+ if rc:
+ raise LVMResizeError(vgname, lvname)
+
+
def vgcreate(vgname, PESize, nodes):
"""Creates a new volume group."
@@ -364,18 +380,18 @@ def vglist():
vgs = []
args = ["vgdisplay", "-C", "--noheadings", "--units", "b",
"--nosuffix", "--separator", ":", "--options",
- "vg_name,vg_size,vg_extent_size"
+ "vg_name,vg_size,vg_extent_size,vg_free"
]
for line in lvmCapture(*args):
try:
- (vg, size, pesize) = line
+ (vg, size, pesize, free) = line
size = long(math.floor(long(size) / (1024 * 1024)))
pesize = long(pesize)/1024
+ free = math.floor(long(free) / (1024 * 1024))
except:
continue
log.info("vg %s, size is %s, pesize is %s" %(vg, size, pesize))
- vgs.append( (vg, size, pesize) )
-
+ vgs.append( (vg, size, pesize, free) )
return vgs
def partialvgs():
diff --git a/lvmErrors.py b/lvmErrors.py
index 3371c05a4..c69e9b5ee 100644
--- a/lvmErrors.py
+++ b/lvmErrors.py
@@ -59,6 +59,16 @@ class LVRemoveError(LvmError):
return "lvremove of lv \"%s\" from vg \"%s\" failed\nLog:\n%s" % ( \
self.lvname, self.vgname, self.log)
+class LVResizeError(LvmError):
+ def __init__(self, vgname, lvname):
+ self.vgname = vgname
+ self.lvname = lvname
+ self.log = self.getLvmOutput()
+
+ def __str__(self):
+ return "lvresize of lv \"%s\" from vg \"%s\" failed\nLog:\n%s" % ( \
+ self.lvname, self.vgname, self.log)
+
class VGCreateError(LvmError):
def __init__(self, vgname, PESize, nodes):
self.vgname = vgname
diff --git a/packages.py b/packages.py
index 99f9a3842..42dc12bd6 100644
--- a/packages.py
+++ b/packages.py
@@ -148,10 +148,11 @@ def turnOnFilesystems(anaconda):
searchPath = 1)
anaconda.id.partitions.doMetaDeletes(anaconda.id.diskset)
anaconda.id.fsset.setActive(anaconda.id.diskset)
- anaconda.id.fsset.shrinkFilesystems(anaconda.rootPath)
+ anaconda.id.fsset.shrinkFilesystems(anaconda.id.diskset, anaconda.rootPath)
if not anaconda.id.fsset.isActive():
anaconda.id.diskset.savePartitions ()
- anaconda.id.fsset.growFilesystems(anaconda.rootPath)
+ anaconda.id.partitions.doMetaResizes(anaconda.id.diskset)
+ anaconda.id.fsset.growFilesystems(anaconda.id.diskset, anaconda.rootPath)
if not anaconda.id.fsset.volumesCreated:
anaconda.id.fsset.createLogicalVolumes(anaconda.rootPath)
anaconda.id.fsset.formatSwap(anaconda.rootPath)
diff --git a/partRequests.py b/partRequests.py
index 84ff18a68..a7664047a 100644
--- a/partRequests.py
+++ b/partRequests.py
@@ -795,6 +795,7 @@ class VolumeGroupRequestSpec(RequestSpec):
self.physicalVolumes = physvols
self.pesize = pesize
self.preexist = preexist
+ self.free = 0
# FIXME: this is a hack so that we can set the vg name automagically
# with autopartitioning to not conflict with existing vgs
@@ -915,13 +916,15 @@ class LogicalVolumeRequestSpec(RequestSpec):
self.grow = grow
self.maxSizeMB = maxSizeMB
self.startSize = size
+
+ self.minResizeSize = None
+ self.resizable = True
if not percent and not size and not preexist:
raise RuntimeError, "Error with Volume Group:Logical Volume %s:%s - Logical Volume must specify either percentage of vgsize or size" % (volgroup, lvname)
if percent and grow:
raise RuntimeError, "Error with Volume Group:Logical Volume %s:%s - Logical Volume cannot grow if percentage given" % (volgroup, lvname)
-
def __str__(self):
if self.fstype:
@@ -955,14 +958,19 @@ class LogicalVolumeRequestSpec(RequestSpec):
existing = self.preexist)
return self.dev
- def getActualSize(self, partitions, diskset):
+ def getActualSize(self, partitions = None, diskset = None, target = False):
"""Return the actual size allocated for the request in megabytes."""
if self.percent:
+ if partitions is None or diskset is None:
+ raise RuntimeError, "trying to get a percentage lv size on resize path"
vgreq = partitions.getRequestByID(self.volumeGroup)
vgsize = vgreq.getActualSize(partitions, diskset)
lvsize = int(self.percent * 0.01 * vgsize)
#lvsize = lvm.clampLVSizeRequest(lvsize, vgreq.pesize)
return lvsize
+ # FIXME: the target bit here is a bit of a hack...
+ elif self.targetSize is not None and target:
+ return self.targetSize
else:
return self.size
@@ -996,3 +1004,14 @@ class LogicalVolumeRequestSpec(RequestSpec):
"containing encrypted physical volumes.")
return RequestSpec.sanityCheckRequest(self, partitions, skipMntPtExistCheck)
+
+ def getMaximumResizeMB(self, partitions):
+ vg = partitions.getRequestByID(self.volumeGroup)
+ print "max is", self.getActualSize(), vg.free, self.getActualSize() + vg.free
+ return self.getActualSize() + vg.free
+
+ def getMinimumResizeMB(self, partitions):
+ if self.minResizeSize is None:
+ log.warning("don't know the minimum size of %s" %(self.logicalVolumeName,))
+ return 1
+ return self.minResizeSize
diff --git a/partitions.py b/partitions.py
index 02f5df6f6..3c6f5fe7a 100644
--- a/partitions.py
+++ b/partitions.py
@@ -292,7 +292,7 @@ class Partitions:
lvm.vgactivate()
pvs = lvm.pvlist()
- for (vg, size, pesize) in lvm.vglist():
+ for (vg, size, pesize, vgfree) in lvm.vglist():
try:
preexist_size = float(size)
except:
@@ -315,6 +315,7 @@ class Partitions:
pesize = pesize,
preexist = 1,
preexist_size = preexist_size)
+ spec.free = vgfree
vgid = self.addRequest(spec)
for (lvvg, lv, size, lvorigin) in lvm.lvlist():
@@ -346,6 +347,8 @@ class Partitions:
format = format, size = lvsize, volgroup = vgid,
lvname = lv, mountpoint = mnt, fslabel = fslabel,
preexist = 1)
+ if fsystem.isResizable():
+ spec.minResizeSize = fsystem.getMinimumSize("%s/%s" %(vg, lv))
self.addRequest(spec)
for vg in lvm.partialvgs():
@@ -1474,6 +1477,24 @@ class Partitions:
lvm.vgdeactivate()
diskset.stopMdRaid()
+ def doMetaResizes(self, diskset):
+ """Does resizing of non-physical volumes."""
+ # NOTE: this should be called with volumes active
+
+ # we only support resizing LVM of these types of things currently
+ for lv in self.getLVMLVRequests():
+ if not lv.preexist:
+ continue
+ if lv.targetSize is None:
+ continue
+
+ vg = self.getRequestByID(lv.volumeGroup)
+ if vg is None:
+ continue
+
+ lvm.lvresize(lv.logicalVolumeName, vg.volumeGroupName,
+ lv.targetSize)
+
def deleteDependentRequests(self, request):
"""Handle deletion of this request and all requests which depend on it.