Skip to content

Re-running in shrink mode shrinks the drive a second time #32

Description

@ALERTua

In shrink mode the script computes how far to shrink from the partition's current maximum:

$maxSize = $supportedSizes.SizeMax
$targetSize = $maxSize - [math]::Round($ShrinkGB * 1GB, 2)
Resize-Partition -DiskNumber $diskNum -PartitionNumber $partitionInfo.PartitionNumber -Size $targetSize

That is correct on a first run. It is wrong on a second one.

Suppose a run shrinks D: by 199 GB, creates the new partition, and then fails at formatting or at
BitLocker. The script ends with:

Please check the error message and try again.

A user who takes that advice picks the same drive and the same 199 GB. But SizeMax now reports the
partition's current size ΓÇö it cannot grow, because the newly created partition sits right after it ΓÇö
so targetSize is current size minus another 199 GB, and D: loses 199 GB a second time. Nothing
warns, because from the script's point of view this is an ordinary first run.

Nothing in the system records that a shrink happened, so the script cannot detect this by looking.
The free-space and .vhdx modes do not have the problem: an oversized request there fails a check
instead of quietly succeeding.

To do

  • stop telling the user to "try again" without qualification when the run has already changed the
    disk, and say plainly what was already done
  • in shrink mode specifically, warn that re-running will shrink again rather than resume
  • consider whether the target size should be expressed as an absolute size the user confirms, rather
    than an amount subtracted from whatever the maximum happens to be at the time

Found while designing #4.


Updated 2026-08-26, after #97

The defect stands, but the code quoted above is gone and the reasoning behind it was wrong.

#97 reworked this branch. The target is now computed from the partition's current size, not from SizeMax:

$shrinkPlan = Resolve-ShrinkPlan -CurrentSize $partitionInfo.Size -MaxSize $maxSize `
    -MinSize $minSize -ShrinkBytes (ConvertTo-ByteCount -GB $ShrinkGB)
Resize-Partition -DiskNumber $diskNum -PartitionNumber $partitionInfo.PartitionNumber -Size $shrinkPlan.TargetBytes

So the explanation above - that SizeMax reports the current size on a second run because the new partition sits behind it - no longer applies. The outcome is the same for a simpler reason: on a second run $partitionInfo.Size is the already-shrunk size, so the volume gives up the requested amount again, from a smaller starting point.

Worth knowing while fixing this, both measured in #97:

  • SizeMax is the partition's size plus the contiguous unallocated run immediately behind it. On a second run that run holds the partition the first run created, so SizeMax equals the current size and the drive gets nothing - the run now refuses rather than proceeding, because the resulting space falls below the 50 GB minimum.
  • The new partition is placed at an explicit offset, so a second run cannot silently reuse a different free region elsewhere on the disk.

The third to-do above - expressing the target as an absolute size the user confirms - is still the real answer, and is unaffected.

The third to-do above is struck. Asking what the drive should become, instead of how much to
cut, was already rejected once and was rejected again on 2026-08-26. Two reasons: it makes one wrong
answer survivable without addressing a run that dies half-finished and records nothing, which is what
#34 is for; and since #97 the answer no longer determines the Dev Drive's size on its own, because
the drive also takes any unallocated space adjoining the volume. It would need a second figure beside
it to say what the drive comes out as, so it is not the simple substitution it looked like.

The first two to-dos stand and are the whole of this issue: say plainly what a failed run already
changed, and warn that re-running shrinks again rather than resumes.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions