Skip to content

Commit

Permalink
Add comments
Browse files Browse the repository at this point in the history
  • Loading branch information
quexten committed Dec 19, 2024
1 parent 015cd8e commit 5afaae6
Show file tree
Hide file tree
Showing 2 changed files with 36 additions and 21 deletions.
36 changes: 15 additions & 21 deletions crates/bitwarden-ssh/src/import.rs
Original file line number Diff line number Diff line change
@@ -1,14 +1,11 @@
use ed25519;
use pem_rfc7468::PemLabel;
use pkcs8::{der::Decode, pkcs5, DecodePrivateKey, PrivateKeyInfo, SecretDocument};
use rsa::pkcs1;
use ssh_key::private::{Ed25519Keypair, RsaKeypair};

use crate::{error::SshKeyImportError, SshKey};

const PKCS1_LABEL: &str = "RSA PRIVATE KEY";
const PKCS8_UNENCRYPTED_LABEL: &str = "PRIVATE KEY";
const PKCS8_ENCRYPTED_LABEL: &str = "ENCRYPTED PRIVATE KEY";
const OPENSSH_LABEL: &str = "OPENSSH PRIVATE KEY";

/// Import a PKCS8 or OpenSSH encoded private key, and returns a decoded SshKey,
/// with the public key and fingerprint, and the private key in OpenSSH format.
/// A password can be provided for encrypted keys.
Expand All @@ -25,7 +22,7 @@ pub fn import_key(
.map_err(|_| SshKeyImportError::ParsingError)?;

match label {
PKCS1_LABEL => Err(SshKeyImportError::UnsupportedKeyType),
pkcs1::RsaPrivateKey::PEM_LABEL => Err(SshKeyImportError::UnsupportedKeyType),
pkcs8::PrivateKeyInfo::PEM_LABEL => import_pkcs8_key(encoded_key, None),
pkcs8::EncryptedPrivateKeyInfo::PEM_LABEL => import_pkcs8_key(
encoded_key,
Expand All @@ -40,7 +37,7 @@ fn import_pkcs8_key(
encoded_key: String,
password: Option<String>,
) -> Result<SshKey, SshKeyImportError> {
let der = if let Some(password) = password {
let doc = if let Some(password) = password {
SecretDocument::from_pkcs8_encrypted_pem(&encoded_key, password.as_bytes()).map_err(
|err| match err {
pkcs8::Error::EncryptedPrivateKey(pkcs5::Error::DecryptFailed) => {
Expand All @@ -54,7 +51,7 @@ fn import_pkcs8_key(
};

let private_key_info =
PrivateKeyInfo::from_der(der.as_bytes()).map_err(|_| SshKeyImportError::ParsingError)?;
PrivateKeyInfo::from_der(doc.as_bytes()).map_err(|_| SshKeyImportError::ParsingError)?;

let private_key = match private_key_info.algorithm.oid {
ed25519::pkcs8::ALGORITHM_OID => {
Expand Down Expand Up @@ -93,21 +90,18 @@ fn import_openssh_key(
_ => SshKeyImportError::ParsingError,
})?;

if private_key.is_encrypted() {
if let Some(password) = password {
private_key
.decrypt(password.as_bytes())
.map_err(|_| SshKeyImportError::WrongPassword)?
.try_into()
.map_err(|_| SshKeyImportError::ParsingError)
} else {
Err(SshKeyImportError::PasswordRequired)
}
let private_key = if private_key.is_encrypted() {
let password = password.ok_or(SshKeyImportError::PasswordRequired)?;
private_key
.decrypt(password.as_bytes())
.map_err(|_| SshKeyImportError::WrongPassword)?
} else {
private_key
.try_into()
.map_err(|_| SshKeyImportError::ParsingError)
}
};

private_key
.try_into()
.map_err(|_| SshKeyImportError::ParsingError)
}

#[cfg(test)]
Expand Down
21 changes: 21 additions & 0 deletions crates/bitwarden-wasm-internal/src/ssh.rs
Original file line number Diff line number Diff line change
@@ -1,12 +1,33 @@
use wasm_bindgen::prelude::*;

/// Generate a new SSH key pair
///
/// # Arguments
/// - `key_algorithm` - The algorithm to use for the key pair
///
/// # Returns
/// - `Ok(SshKey)` if the key was successfully generated
/// - `Err(KeyGenerationError)` if the key could not be generated
#[wasm_bindgen]
pub fn generate_ssh_key(
key_algorithm: bitwarden_ssh::generator::KeyAlgorithm,
) -> Result<bitwarden_ssh::SshKey, bitwarden_ssh::error::KeyGenerationError> {
bitwarden_ssh::generator::generate_sshkey(key_algorithm)
}

/// Convert a PCKS8 or OpenSSH encrypted or unencrypted private key
/// to an OpenSSH private key with public key and fingerprint
///
/// # Arguments
/// - `imported_key` - The private key to convert
/// - `password` - The password to use for decrypting the key
///
/// # Returns
/// - `Ok(SshKey)` if the key was successfully coneverted
/// - `Err(PasswordRequired)` if the key is encrypted and no password was provided
/// - `Err(WrongPassword)` if the password provided is incorrect
/// - `Err(ParsingError)` if the key could not be parsed
/// - `Err(UnsupportedKeyType)` if the key type is not supported
#[wasm_bindgen]
pub fn import_ssh_key(
imported_key: &str,
Expand Down

0 comments on commit 5afaae6

Please sign in to comment.