-
Notifications
You must be signed in to change notification settings - Fork 246
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
WIP: sfdisk implementation #1929
base: main
Are you sure you want to change the base?
Conversation
I think I might need a bit more for wipefs to work correctly. (looking into it but wanted to share) Clean device using old way
Write to device using command I will use again to verify it works
Wipe device using wipefs to see if we can use a device that is wiped with it
Verify disk is empty according to sfdisk
Try sgdisk command to create partition created above.
|
Hmm, I seem to be stumbling a bit, I ended up focusing directly on the pretend section today. I found a few odds and ends that were missed in the first pass. I had been running against a creation test which only created one partition, however I stumbled into a test which makes two partitions, this is relevant because the nature of how the sfdisk is currently receiving my script input is painful. Currently I don't see a way to express multiple partitions when running commands in the using '\n' does not do what I would hope, so I think that leaves me two two imput ideas which I see
I have been leaning towards option 1 as it seems the least invasive, but I dont think its working as I expect, and its difficult to debug blackbox tests. Is option 2 even acceptable? More on option 1: Given ignition config 👇 {
"ignition": {
"version": "3.3.0"
},
"storage": {
"disks": [{
"device": "/dev/loop22",
"partitions": [
{
"label": "newpart",
"sizeMiB": 32
},
{
"number": 1,
"label": "foobar"
}
]
}]
}
} the code expands it into an array of commands for sfdisk { "1 : start=2048 size=65536 name=foobar " ,
"size=65536 name=newpart "} cmd := exec.Command("sh", "-c", fmt.Sprintf("sudo %s %s", distro.SfdiskCmd(), op.dev))
for _, s := range scripts {
println("script %s", s)
cmd.Stdin = bytes.NewBufferString(s)
}
cmd.Stdin = bytes.NewBufferString("quit")
cmd.Stdin = bytes.NewBufferString("Y") However then subsequently running a dump command I only find this std output
Which does not have any partitions listed, acting out these commands manually does; I wonder if |
dd8f0b9
to
bba6095
Compare
Ok, in the latest push a few things have happened.
Next steps:
|
internal/sfdisk/sfdisk.go
Outdated
// If wipe we need to reset the partition table | ||
if op.wipe { | ||
// sgdisk --zap-all /dev/sda destroys the partition table, let's do the same with wipefs | ||
// Found out that wipefs is not sufficient, as it results in a corrupt partition table, look into sgdisk's way of doing --zap-all |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks like util-linux/util-linux#3191 is an outstanding RFE to have an sgdisk --zap-all
like option for sfdisk. We should verify the sgdisk code, but according to util-linux/util-linux#3191 (comment), it should be sufficient to zero out the first and last 34 sectors of the disk.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm but actually, testing locally I can't get the corrupted partition table message to happen after using wipefs -a
. It also seems like wipefs -a
does not delete filesystem data hosted at the partitions as I previously thought.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you; Yeah -a seems like the right combo for our needs. Thank you thank you.
bba6095
to
aaff066
Compare
Latest push includes the parsing for sfdisk's pretend. Additionally added a few unit tests to sanity check the parsing. Will likely need to expand with examples but so far thats passing. Additionally adjusted the wipe script as per @jlebon 's comment. Next steps (from last comment):
|
) | ||
func getDeviceManager(logger *log.Logger, dev string) device_managers.DeviceManager { | ||
// To be replaced with build tag support or something similar. | ||
if false { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Note: will be dynamic based on arguments later just hard coded switch atm.
Update: added interface for device_managers (name could be better not sure what would be good; feedback wanted lol), thus abstracting implementation from partitions.go, additionally lifted and placed parse responsibility on the implementation rather then the caller. Still need to work against commit. |
034d49f
to
88e9194
Compare
@@ -0,0 +1,28 @@ | |||
package device_managers |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How about partitioners
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah thats a better name; will do!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I know renames can be confusing in prs, so i did some commit juggling and it has been renamed; I hope I did it in a way that made sense.
|
||
op.logger.Info("running sfdisk with script: %v", script) | ||
exec.Command("sh", "-c", fmt.Sprintf("echo label: gpt | sudo %s %s", distro.SfdiskCmd(), op.dev)) | ||
cmd := exec.Command("sh", "-c", fmt.Sprintf("echo \"%s\" | sudo %s %s", script, distro.SfdiskCmd(), op.dev)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same comments here.
Probably cleanest is to make a helper function that actually calls sfdisk
and takes the script as an argument that it feeds to its stdin?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I gave it a swing
// ParseOutput takes the output from sfdisk. Similarly to sgdisk | ||
// it then uses regex to parse the output into understood values like 'start' 'size' and attempts | ||
// to catch any failures and wrap them to return to the caller. | ||
func (op *Operation) ParseOutput(sfdiskOutput string, partitionNumbers []int) (map[int]device_managers.Output, error) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK yeah, this is pretty unfortunate. I was expecting --json
or -d
to also work in combination with --no-act
, but that doesn't seem the case. Let's at least file an RFE upstream for now?
This has a high chance of regression if the output of sfdisk changes. We'll indeed want to make sure we have good coverage for this.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah; 100%, Ok will do and tag it here once done.
} | ||
|
||
// Prepare the data, and a regex for matching on partitions | ||
partitionRegex := regexp.MustCompile(`^/dev/\S+\s+\S*\s+(\d+)\s+(\d+)\s+\d+\s+\S+\s+\S+\s+\S+.*$`) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This deserves some explanation.
Also, I feel like we should ignore anything before the "New situation:" line.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Added some details
1a20248
to
8e7dc92
Compare
Ugh; I accidentally rebased too far back and effected external commits sigh; I will fix that. edit: fixed |
This is a copy of sgdisk, with mapping around sfdisk tooling. Update the buildOptions to understand sfdisk requirements and focus on adding support for the pretend function. Fixes: https://issues.redhat.com/browse/COS-2837
d152f1c
to
32b61d7
Compare
Add an interface to abstract implementation details for partition management, allowing tooling to pivot between implementations. TBD: argument/tag reading for triggering the pivot Fixes: https://issues.redhat.com/browse/COS-2930
32b61d7
to
99e632a
Compare
This is a WIP PR to add sfdisk support to ignition, Current state is iterating through failing tests and adding mapping to pretend to interface the same as before with sgdisk.
Resolves #1926