]> git.proxmox.com Git - proxmox-backup.git/blobdiff - src/tape/drive/lto/mod.rs
moved key_derivation.rs from pbs_datastore to pbs-config/src/key_config.rs
[proxmox-backup.git] / src / tape / drive / lto / mod.rs
index c7ea0b276246fa1211021164858630361bef0fdb..e5040613f1e60dc595a14418c735f0dde6f26d30 100644 (file)
@@ -27,26 +27,24 @@ use proxmox::{
     sys::error::SysResult,
 };
 
+use pbs_api_types::Fingerprint;
+use pbs_config::key_config::KeyConfig;
+use pbs_tools::run_command;
+
 use crate::{
     config,
-    tools::run_command,
-    backup::{
-        Fingerprint,
-        KeyConfig,
-    },
     api2::types::{
         MamAttribute,
         LtoDriveAndMediaStatus,
         LtoTapeDrive,
+        Lp17VolumeStatistics,
     },
     tape::{
         TapeRead,
         TapeWrite,
+        BlockReadError,
         drive::{
             TapeDriver,
-            TapeAlertFlags,
-            Lp17VolumeStatistics,
-            mam_extract_media_usage,
         },
         file_formats::{
             PROXMOX_BACKUP_MEDIA_SET_LABEL_MAGIC_1_0,
@@ -56,37 +54,34 @@ use crate::{
     },
 };
 
-impl LtoTapeDrive {
-
-    /// Open a tape device
-    ///
-    /// This does additional checks:
-    ///
-    /// - check if it is a non-rewinding tape device
-    /// - check if drive is ready (tape loaded)
-    /// - check block size
-    /// - for autoloader only, try to reload ejected tapes
-    pub fn open(&self) -> Result<LtoTapeHandle, Error> {
+/// Open a tape device
+///
+/// This does additional checks:
+///
+/// - check if it is a non-rewinding tape device
+/// - check if drive is ready (tape loaded)
+/// - check block size
+/// - for autoloader only, try to reload ejected tapes
+pub fn open_lto_tape_drive(config: &LtoTapeDrive) -> Result<LtoTapeHandle, Error> {
 
-        proxmox::try_block!({
-            let file = open_lto_tape_device(&self.path)?;
+    proxmox::try_block!({
+        let file = open_lto_tape_device(&config.path)?;
 
-            let mut handle = LtoTapeHandle::new(file)?;
+        let mut handle = LtoTapeHandle::new(file)?;
 
-            if !handle.sg_tape.test_unit_ready().is_ok() {
-                // for autoloader only, try to reload ejected tapes
-                if self.changer.is_some() {
-                    let _ = handle.sg_tape.load(); // just try, ignore error
-                }
+        if !handle.sg_tape.test_unit_ready().is_ok() {
+            // for autoloader only, try to reload ejected tapes
+            if config.changer.is_some() {
+                let _ = handle.sg_tape.load(); // just try, ignore error
             }
+        }
 
-            handle.sg_tape.wait_until_ready()?;
+        handle.sg_tape.wait_until_ready()?;
 
-            handle.set_default_options()?;
+        handle.set_default_options()?;
 
-            Ok(handle)
-        }).map_err(|err: Error| format_err!("open drive '{}' ({}) failed - {}", self.name, self.path, err))
-    }
+        Ok(handle)
+    }).map_err(|err: Error| format_err!("open drive '{}' ({}) failed - {}", config.name, config.path, err))
 }
 
 /// Lto Tape device handle
@@ -139,6 +134,9 @@ impl LtoTapeHandle {
             .ok();
 
         let mut status = LtoDriveAndMediaStatus {
+            vendor: self.sg_tape.info().vendor.clone(),
+            product: self.sg_tape.info().product.clone(),
+            revision: self.sg_tape.info().revision.clone(),
             blocksize: drive_status.block_length,
             compression: drive_status.compression,
             buffer_mode: drive_status.buffer_mode,
@@ -213,31 +211,8 @@ impl LtoTapeHandle {
     }
 
     /// Position the tape after filemark count. Count 0 means BOT.
-    ///
-    /// Note: we dont use LOCATE(10), because that needs LTO5
     pub fn locate_file(&mut self, position: u64) ->  Result<(), Error> {
-
-        if position == 0 {
-            return self.rewind();
-        }
-
-        let current_position = self.current_file_number()?;
-
-        if current_position == position {
-            // make sure we are immediated afer the filemark
-            self.sg_tape.space_filemarks(-1)?;
-            self.sg_tape.space_filemarks(1)?;
-        } else if current_position < position {
-            let diff = position - current_position;
-            self.sg_tape.space_filemarks(diff.try_into()?)?;
-        } else {
-            let diff = current_position - position + 1;
-            self.sg_tape.space_filemarks(-diff.try_into()?)?;
-            // move to EOT side of filemark
-            self.sg_tape.space_filemarks(1)?;
-        }
-
-        Ok(())
+        self.sg_tape.locate_file(position)
     }
 
     pub fn erase_media(&mut self, fast: bool) -> Result<(), Error> {
@@ -307,6 +282,10 @@ impl TapeDriver for LtoTapeHandle {
         Ok(())
     }
 
+    fn move_to_file(&mut self, file: u64) -> Result<(), Error> {
+        self.locate_file(file)
+    }
+
     fn rewind(&mut self) -> Result<(), Error> {
         self.sg_tape.rewind()
     }
@@ -319,16 +298,9 @@ impl TapeDriver for LtoTapeHandle {
         self.sg_tape.format_media(fast)
     }
 
-    fn read_next_file<'a>(&'a mut self) -> Result<Option<Box<dyn TapeRead + 'a>>, std::io::Error> {
+    fn read_next_file<'a>(&'a mut self) -> Result<Box<dyn TapeRead + 'a>, BlockReadError> {
         let reader = self.sg_tape.open_reader()?;
-        let handle = match reader {
-            Some(reader) => {
-                let reader: Box<dyn TapeRead> = Box::new(reader);
-                Some(reader)
-            }
-            None => None,
-        };
-
+        let handle: Box<dyn TapeRead> = Box::new(reader);
         Ok(handle)
     }
 
@@ -433,7 +405,7 @@ impl TapeDriver for LtoTapeHandle {
         }
 
         let output = if let Some((fingerprint, uuid)) = key_fingerprint {
-            let fingerprint = crate::tools::format::as_fingerprint(fingerprint.bytes());
+            let fingerprint = pbs_tools::format::as_fingerprint(fingerprint.bytes());
             run_sg_tape_cmd("encryption", &[
                 "--fingerprint", &fingerprint,
                 "--uuid", &uuid.to_string(),