]> git.proxmox.com Git - pve-installer.git/blame - proxmox-fetch-answer/src/fetch_plugins/partition.rs
fetch answers: rename partition search label
[pve-installer.git] / proxmox-fetch-answer / src / fetch_plugins / partition.rs
CommitLineData
412871c9
TL
1use anyhow::{format_err, Error, Result};
2use log::{info, warn};
3use std::{
4 fs::{self, create_dir_all},
5 path::{Path, PathBuf},
6 process::Command,
7};
2949f825
AL
8
9static ANSWER_FILE: &str = "answer.toml";
412871c9 10static ANSWER_MP: &str = "/mnt/answer";
528d1268 11static PARTLABEL: &str = "proxmox-inst-src";
412871c9 12static SEARCH_PATH: &str = "/dev/disk/by-label";
2949f825
AL
13
14pub struct FetchFromPartition;
15
16impl FetchFromPartition {
17 /// Returns the contents of the answer file
18 pub fn get_answer() -> Result<String> {
19 info!("Checking for answer file on partition.");
412871c9 20
249a10e9
AL
21 let mut mount_path = PathBuf::from(mount_proxmoxinst_part()?);
22 mount_path.push(ANSWER_FILE);
412871c9
TL
23 let answer = fs::read_to_string(mount_path)
24 .map_err(|err| format_err!("failed to read answer file - {err}"))?;
25
2949f825 26 info!("Found answer file on partition.");
412871c9 27
2949f825
AL
28 Ok(answer)
29 }
2949f825 30}
412871c9
TL
31
32/// Searches for upper and lower case existence of the partlabel in the search_path
33///
34/// # Arguemnts
35/// * `partlabel_source` - Partition Label, used as upper and lower case
36/// * `search_path` - Path where to search for the partiiton label
37fn scan_partlabels(partlabel_source: &str, search_path: &str) -> Result<PathBuf> {
38 let partlabel = partlabel_source.to_uppercase();
39 let path = Path::new(search_path).join(&partlabel);
40 match path.try_exists() {
41 Ok(true) => {
42 info!("Found partition with label '{partlabel}'");
43 return Ok(path);
44 }
45 Ok(false) => info!("Did not detect partition with label '{partlabel}'"),
46 Err(err) => info!("Encountered issue, accessing '{}': {err}", path.display()),
47 }
48
49 let partlabel = partlabel_source.to_lowercase();
50 let path = Path::new(search_path).join(&partlabel);
51 match path.try_exists() {
52 Ok(true) => {
53 info!("Found partition with label '{partlabel}'");
54 return Ok(path);
55 }
56 Ok(false) => info!("Did not detect partition with label '{partlabel}'"),
57 Err(err) => info!("Encountered issue, accessing '{}': {err}", path.display()),
58 }
59 Err(Error::msg(format!(
60 "Could not detect upper or lower case labels for '{partlabel_source}'"
61 )))
62}
63
528d1268
TL
64/// Will search and mount a partition/FS labeled PARTLABEL (proxmox-inst-src) in lower or uppercase
65/// to ANSWER_MP
412871c9
TL
66fn mount_proxmoxinst_part() -> Result<String> {
67 if let Ok(true) = check_if_mounted(ANSWER_MP) {
68 info!("Skipping: '{ANSWER_MP}' is already mounted.");
69 return Ok(ANSWER_MP.into());
70 }
71 let part_path = scan_partlabels(PARTLABEL, SEARCH_PATH)?;
72 info!("Mounting partition at {ANSWER_MP}");
73 // create dir for mountpoint
74 create_dir_all(ANSWER_MP)?;
75 match Command::new("mount")
76 .args(["-o", "ro"])
77 .arg(part_path)
78 .arg(ANSWER_MP)
79 .output()
80 {
81 Ok(output) => {
82 if output.status.success() {
83 Ok(ANSWER_MP.into())
84 } else {
85 warn!("Error mounting: {}", String::from_utf8(output.stderr)?);
86 Ok(ANSWER_MP.into())
87 }
88 }
89 Err(err) => Err(Error::msg(format!("Error mounting: {err}"))),
90 }
91}
92
93fn check_if_mounted(target_path: &str) -> Result<bool> {
94 let mounts = fs::read_to_string("/proc/mounts")?;
95 for line in mounts.lines() {
96 if let Some(mp) = line.split(' ').nth(1) {
97 if mp == target_path {
98 return Ok(true);
99 }
100 }
101 }
102 Ok(false)
103}