@@ -9,9 +9,7 @@ use uefi::fs::{FileSystem, Path};
99use uefi:: proto:: device_path:: DevicePath ;
1010use uefi:: proto:: media:: file:: { File , FileSystemVolumeLabel } ;
1111use uefi:: proto:: media:: fs:: SimpleFileSystem ;
12- use uefi:: proto:: media:: partition:: PartitionInfo ;
13- use uefi:: { CString16 , Guid , Handle } ;
14- use uefi_raw:: Status ;
12+ use uefi:: { CString16 , Guid } ;
1513
1614/// The filesystem device match extractor.
1715/// This extractor finds a filesystem using some search criteria and returns
@@ -41,48 +39,6 @@ pub struct FilesystemDeviceMatchExtractor {
4139 pub fallback : Option < String > ,
4240}
4341
44- /// Represents the partition UUIDs for a filesystem.
45- struct PartitionIds {
46- /// The UUID of the partition.
47- partition_uuid : Guid ,
48- /// The type UUID of the partition.
49- type_uuid : Guid ,
50- }
51-
52- /// Fetches the partition UUIDs for the specified filesystem handle.
53- fn fetch_partition_uuids ( handle : Handle ) -> Result < Option < PartitionIds > > {
54- // Open the partition info protocol for this handle.
55- let partition_info = uefi:: boot:: open_protocol_exclusive :: < PartitionInfo > ( handle) ;
56-
57- match partition_info {
58- Ok ( partition_info) => {
59- // GPT partitions have a unique partition GUID.
60- // MBR does not.
61- if let Some ( gpt) = partition_info. gpt_partition_entry ( ) {
62- let uuid = gpt. unique_partition_guid ;
63- let type_uuid = gpt. partition_type_guid ;
64- Ok ( Some ( PartitionIds {
65- partition_uuid : uuid,
66- type_uuid : type_uuid. 0 ,
67- } ) )
68- } else {
69- Ok ( None )
70- }
71- }
72-
73- Err ( error) => {
74- // If the filesystem does not have a partition, that is okay.
75- if error. status ( ) == Status :: NOT_FOUND || error. status ( ) == Status :: UNSUPPORTED {
76- Ok ( None )
77- } else {
78- // We should still handle other errors gracefully.
79- Err ( error) . context ( "unable to open filesystem partition info" ) ?;
80- unreachable ! ( )
81- }
82- }
83- }
84- }
85-
8642/// Extract a filesystem device path using the specified `context` and `extractor` configuration.
8743pub fn extract (
8844 context : Rc < SproutContext > ,
@@ -106,30 +62,49 @@ pub fn extract(
10662 // This defines whether a match has been found.
10763 let mut has_match = false ;
10864
109- // Extract the partition info for this filesystem.
110- // There is no guarantee that the filesystem has a partition.
111- let partition_info =
112- fetch_partition_uuids ( handle) . context ( "unable to fetch partition info" ) ?;
113-
11465 // Check if the partition info matches partition uuid criteria.
115- if let Some ( ref partition_info) = partition_info
116- && let Some ( ref has_partition_uuid) = extractor. has_partition_uuid
117- {
66+ if let Some ( ref has_partition_uuid) = extractor. has_partition_uuid {
67+ // Parse the partition uuid from the extractor.
11868 let parsed_uuid = Guid :: from_str ( has_partition_uuid)
11969 . map_err ( |e| anyhow ! ( "unable to parse has-partition-uuid: {}" , e) ) ?;
120- if partition_info. partition_uuid != parsed_uuid {
70+
71+ // Fetch the root of the device.
72+ let root = uefi:: boot:: open_protocol_exclusive :: < DevicePath > ( handle)
73+ . context ( "unable to fetch the device path of the filesystem" ) ?
74+ . deref ( )
75+ . to_boxed ( ) ;
76+
77+ // Fetch the partition uuid for this filesystem.
78+ let partition_uuid = utils:: partition_guid ( & root, utils:: PartitionGuidForm :: Partition )
79+ . context ( "unable to fetch the partition uuid of the filesystem" ) ?;
80+
81+ // Compare the partition uuid to the parsed uuid.
82+ // If it does not match, continue to the next filesystem.
83+ if partition_uuid != Some ( parsed_uuid) {
12184 continue ;
12285 }
12386 has_match = true ;
12487 }
12588
12689 // Check if the partition info matches partition type uuid criteria.
127- if let Some ( ref partition_info) = partition_info
128- && let Some ( ref has_partition_type_uuid) = extractor. has_partition_type_uuid
129- {
90+ if let Some ( ref has_partition_type_uuid) = extractor. has_partition_type_uuid {
91+ // Parse the partition type uuid from the extractor.
13092 let parsed_uuid = Guid :: from_str ( has_partition_type_uuid)
13193 . map_err ( |e| anyhow ! ( "unable to parse has-partition-type-uuid: {}" , e) ) ?;
132- if partition_info. type_uuid != parsed_uuid {
94+
95+ // Fetch the root of the device.
96+ let root = uefi:: boot:: open_protocol_exclusive :: < DevicePath > ( handle)
97+ . context ( "unable to fetch the device path of the filesystem" ) ?
98+ . deref ( )
99+ . to_boxed ( ) ;
100+
101+ // Fetch the partition uuid for this filesystem.
102+ let partition_type_uuid =
103+ utils:: partition_guid ( & root, utils:: PartitionGuidForm :: Partition )
104+ . context ( "unable to fetch the partition uuid of the filesystem" ) ?;
105+ // Compare the partition type uuid to the parsed uuid.
106+ // If it does not match, continue to the next filesystem.
107+ if partition_type_uuid != Some ( parsed_uuid) {
133108 continue ;
134109 }
135110 has_match = true ;
0 commit comments