summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaniel Mueller <deso@posteo.net>2019-01-09 16:31:31 -0800
committerDaniel Mueller <deso@posteo.net>2019-01-09 16:31:31 -0800
commiteea4f7357d7a3e3b365d887671ba78fd386a6d2d (patch)
treed1d230385c6985f4b112d4028ef9203a934c83ba
parentae939694c598ae23690f6a56f977c66ae7c0f020 (diff)
downloadnitrocli-eea4f7357d7a3e3b365d887671ba78fd386a6d2d.tar.gz
nitrocli-eea4f7357d7a3e3b365d887671ba78fd386a6d2d.tar.bz2
Honor context provided Admin & User PIN in pin commands
The second source of interactivity comes from the pin set and pin unblock commands, which also inquire with the pinentry module to ask the user for a PIN. This change adjusts the two commands to honor the PINs as available in the command execution context. It also updates the documentation to reflect the availability of the newly introduced and honored environment variables NITROCLI_ADMIN_PIN & NITROCLI_USER_PIN as well as NITROCLI_NEW_ADMIN_PIN & NITROCLI_NEW_USER_PIN.
-rw-r--r--nitrocli/CHANGELOG.md3
-rw-r--r--nitrocli/doc/nitrocli.119
-rw-r--r--nitrocli/doc/nitrocli.1.pdfbin14513 -> 15436 bytes
-rw-r--r--nitrocli/src/commands.rs42
4 files changed, 61 insertions, 3 deletions
diff --git a/nitrocli/CHANGELOG.md b/nitrocli/CHANGELOG.md
index da44c4a..fe9b69c 100644
--- a/nitrocli/CHANGELOG.md
+++ b/nitrocli/CHANGELOG.md
@@ -6,6 +6,9 @@ Unreleased
- Added the `-f`/`--format` option for the `otp set` subcommand to
choose the secret format
- Deprecated the `--ascii` option
+- Honor `NITROCLI_ADMIN_PIN` and `NITROCLI_USER_PIN` as well as
+ `NITROCLI_NEW_ADMIN_PIN` and `NITROCLI_NEW_USER_PIN` environment
+ variables for non-interactive PIN supply
- Format `nitrokey` reported errors in more user-friendly format
- Bumped `nitrokey` dependency to `0.3.1`
diff --git a/nitrocli/doc/nitrocli.1 b/nitrocli/doc/nitrocli.1
index 036c25f..234b588 100644
--- a/nitrocli/doc/nitrocli.1
+++ b/nitrocli/doc/nitrocli.1
@@ -220,6 +220,25 @@ The admin PIN cannot be unblocked.
This operation is equivalent to the unblock PIN option provided by \fBgpg\fR(1)
(using the \fB\-\-change\-pin\fR option).
+.SH ENVIRONMENT
+The program honors a set of environment variables that can be used to
+suppress interactive PIN entry through \fBpinentry\fR(1). The following
+variables are recognized:
+.TP
+.B NITROCLI_ADMIN_PIN
+The admin PIN to use.
+.TP
+.B NITROCLI_USER_PIN
+The user PIN to use.
+.TP
+.B NITROCLI_NEW_ADMIN_PIN
+The new admin PIN to set. This variable is only used by the \fBnitrocli
+pin set\fR command for the \fBadmin\fR type.
+.TP
+.B NITROCLI_NEW_USER_PIN
+The new user PIN to set. This variable is only used by the \fBnitrocli
+pin set\fR command for the \fBuser\fR type.
+
.SH EXAMPLES
.SS One-time passwords
Configure a one-time password slot with a hexadecimal secret representation:
diff --git a/nitrocli/doc/nitrocli.1.pdf b/nitrocli/doc/nitrocli.1.pdf
index 5fa9049..3d28310 100644
--- a/nitrocli/doc/nitrocli.1.pdf
+++ b/nitrocli/doc/nitrocli.1.pdf
Binary files differ
diff --git a/nitrocli/src/commands.rs b/nitrocli/src/commands.rs
index 6316c92..f8765cc 100644
--- a/nitrocli/src/commands.rs
+++ b/nitrocli/src/commands.rs
@@ -610,7 +610,7 @@ fn check_pin(pin_type: pinentry::PinType, pin: &str) -> Result<()> {
}
}
-fn choose_pin(pin_type: pinentry::PinType) -> Result<String> {
+fn choose_pin_with_pinentry(pin_type: pinentry::PinType) -> Result<String> {
pinentry::clear_pin(pin_type)?;
let new_pin = pinentry::inquire_pin(pin_type, pinentry::Mode::Choose, None)?;
pinentry::clear_pin(pin_type)?;
@@ -626,10 +626,46 @@ fn choose_pin(pin_type: pinentry::PinType) -> Result<String> {
}
}
+/// Choose a PIN of the given type.
+///
+/// If the user has set the respective environment variable for the
+/// given PIN type, it will be used.
+fn choose_pin(
+ ctx: &mut args::ExecCtx<'_>,
+ pin_type: pinentry::PinType,
+ new: bool,
+) -> Result<String> {
+ let new_pin = match pin_type {
+ pinentry::PinType::Admin => {
+ if new {
+ &ctx.new_admin_pin
+ } else {
+ &ctx.admin_pin
+ }
+ }
+ pinentry::PinType::User => {
+ if new {
+ &ctx.new_user_pin
+ } else {
+ &ctx.user_pin
+ }
+ }
+ };
+
+ if let Some(new_pin) = new_pin {
+ new_pin
+ .to_str()
+ .ok_or_else(|| Error::Error("Failed to read PIN: invalid Unicode data found".into()))
+ .map(ToOwned::to_owned)
+ } else {
+ choose_pin_with_pinentry(pin_type)
+ }
+}
+
/// Change a PIN.
pub fn pin_set(ctx: &mut args::ExecCtx<'_>, pin_type: pinentry::PinType) -> Result<()> {
let device = get_device(ctx)?;
- let new_pin = choose_pin(pin_type)?;
+ let new_pin = choose_pin(ctx, pin_type, true)?;
try_with_pin(
ctx,
pin_type,
@@ -644,7 +680,7 @@ pub fn pin_set(ctx: &mut args::ExecCtx<'_>, pin_type: pinentry::PinType) -> Resu
/// Unblock and reset the user PIN.
pub fn pin_unblock(ctx: &mut args::ExecCtx<'_>) -> Result<()> {
let device = get_device(ctx)?;
- let user_pin = choose_pin(pinentry::PinType::User)?;
+ let user_pin = choose_pin(ctx, pinentry::PinType::User, false)?;
try_with_pin(
ctx,
pinentry::PinType::Admin,