From fb235d0cf88687eb214b3ec7cb5fab596609d2b6 Mon Sep 17 00:00:00 2001 From: Daniel Mueller Date: Fri, 28 Dec 2018 11:01:08 -0800 Subject: Move printing of storage related status into 'storage status' sub-command The 'status' command has traditionally printed information about the connected Nitrokey and that included storage specific data if the device present is a Nitrokey Storage. Given that we have a root-level 'storage' command it arguably makes sense to move the printing of the storage related status information into a 'status' sub-command of the said command, which makes the output more predictable. --- nitrocli/CHANGELOG.md | 2 ++ nitrocli/README.md | 3 ++ nitrocli/doc/nitrocli.1 | 9 ++++-- nitrocli/src/args.rs | 15 +++++++++- nitrocli/src/commands.rs | 76 +++++++++++++++++++++++++----------------------- 5 files changed, 65 insertions(+), 40 deletions(-) diff --git a/nitrocli/CHANGELOG.md b/nitrocli/CHANGELOG.md index 813f853..ae6b422 100644 --- a/nitrocli/CHANGELOG.md +++ b/nitrocli/CHANGELOG.md @@ -10,6 +10,8 @@ Unreleased - Added the `config` command for reading and writing the device configuration - Moved `open` and `close` commands as subcommands into newly introduced `storage` command + - Moved printing of storage related information from `status` command + into new `storage status` subcommand - Made `status` command work with Nitrokey Pro devices - Enabled CI pipeline comprising code style conformance checks, linting, and building of the project diff --git a/nitrocli/README.md b/nitrocli/README.md index b28f09e..7504b1c 100644 --- a/nitrocli/README.md +++ b/nitrocli/README.md @@ -16,6 +16,7 @@ The following commands are currently supported: - storage: Work with the Nitrokey's storage. - open: Open the encrypted volume. The user PIN needs to be entered. - close: Close the encrypted volume. + - status: Print information about the Nitrokey's storage. - otp: Access one-time passwords (OTP). - get: Generate a one-time password. - set: Set an OTP slot. @@ -49,6 +50,8 @@ Status: user retry count: 3 admin retry count: 3 +$ nitrocli storage status +Status: SD card ID: 0x05dcad1d firmware: unlocked storage keys: created diff --git a/nitrocli/doc/nitrocli.1 b/nitrocli/doc/nitrocli.1 index 44d41fd..5f18abd 100644 --- a/nitrocli/doc/nitrocli.1 +++ b/nitrocli/doc/nitrocli.1 @@ -14,9 +14,7 @@ It can be used to access the encrypted volume and the one-time password generato .TP .B nitrocli status Print the status of the connected Nitrokey device, including the stick serial -number, SD card serial number, the firmware version and the PIN retry count. -For the Nitrokey Storage, it also includes the encryption status and the status -of the volumes. +number, the firmware version, and the PIN retry count. .TP .B nitrocli clear Clear the passphrases cached by the other commands. @@ -30,6 +28,11 @@ The user PIN that is required to open the volume is queried using .TP \fBnitrocli storage close Close the encrypted volume on the Nitrokey Storage. +.TP +\fBnitrocli storage status +Print the status of the connected Nitrokey Storage device's storage. The +printed information includes the SD card serial number, the encryption +status, and the status of the volumes. .SS One-time passwords .TP diff --git a/nitrocli/src/args.rs b/nitrocli/src/args.rs index e7e7717..e533c82 100644 --- a/nitrocli/src/args.rs +++ b/nitrocli/src/args.rs @@ -286,7 +286,7 @@ fn parse(parser: &argparse::ArgumentParser<'_>, args: Vec) -> Result<()> /// Inquire the status of the nitrokey. fn status(args: Vec) -> Result<()> { let mut parser = argparse::ArgumentParser::new(); - parser.set_description("Print the status of the connected Nitrokey device"); + parser.set_description("Prints the status of the connected Nitrokey device"); parse(&parser, args)?; commands::status() @@ -296,6 +296,7 @@ fn status(args: Vec) -> Result<()> { enum StorageCommand { Close, Open, + Status, } impl StorageCommand { @@ -303,6 +304,7 @@ impl StorageCommand { match *self { StorageCommand::Close => storage_close(args), StorageCommand::Open => storage_open(args), + StorageCommand::Status => storage_status(args), } } } @@ -315,6 +317,7 @@ impl fmt::Display for StorageCommand { match *self { StorageCommand::Close => "close", StorageCommand::Open => "open", + StorageCommand::Status => "status", } ) } @@ -327,6 +330,7 @@ impl str::FromStr for StorageCommand { match s { "close" => Ok(StorageCommand::Close), "open" => Ok(StorageCommand::Open), + "status" => Ok(StorageCommand::Status), _ => Err(()), } } @@ -374,6 +378,15 @@ fn storage_close(args: Vec) -> Result<()> { commands::storage_close() } +/// Print the status of the nitrokey's storage. +fn storage_status(args: Vec) -> Result<()> { + let mut parser = argparse::ArgumentParser::new(); + parser.set_description("Prints the status of the Nitrokey's storage"); + parse(&parser, args)?; + + commands::storage_status() +} + /// Clear the PIN as cached by various other commands. fn clear(args: Vec) -> Result<()> { let mut parser = argparse::ArgumentParser::new(); diff --git a/nitrocli/src/commands.rs b/nitrocli/src/commands.rs index fdfe049..17426cd 100644 --- a/nitrocli/src/commands.rs +++ b/nitrocli/src/commands.rs @@ -197,34 +197,6 @@ fn print_status(model: &'static str, device: &nitrokey::DeviceWrapper) -> Result Ok(()) } -/// Pretty print the status of a Nitrokey Storage. -fn print_storage_status(status: &nitrokey::StorageStatus) { - println!( - r#" - SD card ID: {id:#x} - firmware: {fw} - storage keys: {sk} - volumes: - unencrypted: {vu} - encrypted: {ve} - hidden: {vh}"#, - id = status.serial_number_sd_card, - fw = if status.firmware_locked { - "locked" - } else { - "unlocked" - }, - sk = if status.stick_initialized { - "created" - } else { - "not created" - }, - vu = get_volume_status(&status.unencrypted_volume), - ve = get_volume_status(&status.encrypted_volume), - vh = get_volume_status(&status.hidden_volume), - ); -} - /// Inquire the status of the nitrokey. pub fn status() -> Result<()> { let device = get_device()?; @@ -232,14 +204,7 @@ pub fn status() -> Result<()> { nitrokey::DeviceWrapper::Pro(_) => "Pro", nitrokey::DeviceWrapper::Storage(_) => "Storage", }; - print_status(model, &device)?; - if let nitrokey::DeviceWrapper::Storage(storage) = device { - let status = storage - .get_status() - .map_err(|err| get_error("Getting Storage status failed", &err))?; - print_storage_status(&status); - } - Ok(()) + print_status(model, &device) } /// Open the encrypted volume on the nitrokey. @@ -270,6 +235,45 @@ pub fn storage_close() -> Result<()> { .map_err(|err| get_error("Closing encrypted volume failed", &err)) } +/// Pretty print the status of a Nitrokey Storage. +fn print_storage_status(status: &nitrokey::StorageStatus) { + println!( + r#"Status: + SD card ID: {id:#x} + firmware: {fw} + storage keys: {sk} + volumes: + unencrypted: {vu} + encrypted: {ve} + hidden: {vh}"#, + id = status.serial_number_sd_card, + fw = if status.firmware_locked { + "locked" + } else { + "unlocked" + }, + sk = if status.stick_initialized { + "created" + } else { + "not created" + }, + vu = get_volume_status(&status.unencrypted_volume), + ve = get_volume_status(&status.encrypted_volume), + vh = get_volume_status(&status.hidden_volume), + ); +} + +/// Connect to and pretty print the status of a Nitrokey Storage. +pub fn storage_status() -> Result<()> { + let device = get_storage_device()?; + let status = device + .get_status() + .map_err(|err| get_error("Getting Storage status failed", &err))?; + + print_storage_status(&status); + Ok(()) +} + /// Clear the PIN stored when opening the nitrokey's encrypted volume. pub fn clear() -> Result<()> { pinentry::clear_passphrase(pinentry::PinType::Admin)?; -- cgit v1.2.1