diff --git a/Cargo.toml b/Cargo.toml index d137dc5..3f314e3 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -18,6 +18,9 @@ keywords = ["ccid", "ecdsa", "rsa", "piv", "yubikey"] [dependencies] getrandom = "0.1" +hmac = "0.7" libc = "0.2" log = "0.4" +pbkdf2 = "0.3" +sha-1 = "0.8" zeroize = "1" diff --git a/src/internal.rs b/src/internal.rs index 4a80894..e773ea2 100644 --- a/src/internal.rs +++ b/src/internal.rs @@ -60,15 +60,6 @@ extern "C" { ); fn DES_is_weak_key(key: *mut [u8; 8]) -> i32; fn DES_set_key_unchecked(key: *mut [u8; 8], schedule: *mut DesSubKey); - fn PKCS5_PBKDF2_HMAC_SHA1( - pass: *const u8, - passlen: i32, - salt: *const u8, - saltlen: i32, - iter: i32, - keylen: i32, - out: *mut u8, - ) -> i32; } /// DES-related errors @@ -244,29 +235,6 @@ pub enum Pkcs5ErrorKind { GeneralError = -1, } -/// Decrypt a PKCS#5 key -pub unsafe fn pkcs5_pbkdf2_sha1( - password: *const u8, - cb_password: usize, - salt: *const u8, - cb_salt: usize, - iterations: usize, - key: *const u8, - cb_key: usize, -) -> Pkcs5ErrorKind { - PKCS5_PBKDF2_HMAC_SHA1( - password, - cb_password as (i32), - salt, - cb_salt as (i32), - iterations as (i32), - cb_key as (i32), - key as (*mut u8), - ); - - Pkcs5ErrorKind::Ok -} - /// Strip whitespace // TODO(tarcieri): implement this pub unsafe fn _strip_ws(sz: *mut c_char) -> *mut c_char { diff --git a/src/util.rs b/src/util.rs index 68442d5..7f6ee88 100644 --- a/src/util.rs +++ b/src/util.rs @@ -35,8 +35,11 @@ use crate::{consts::*, error::ErrorKind, internal::*, yubikey::*}; use getrandom::getrandom; +use hmac::Hmac; use libc::{calloc, free, memcpy, memmove, realloc, time}; use log::{error, warn}; +use pbkdf2::pbkdf2; +use sha1::Sha1; use std::ops::DerefMut; use std::{ffi::CString, mem, os::raw::c_void, ptr}; use zeroize::{Zeroize, Zeroizing}; @@ -1463,19 +1466,14 @@ impl Drop for YkPivMgm { /// Get derived management key (MGM) pub unsafe fn ykpiv_util_get_derived_mgm( state: &mut YubiKey, - pin: *const u8, - pin_len: usize, - mgm: *mut YkPivMgm, + pin: &[u8], + mgm: &mut YkPivMgm, ) -> Result<(), ErrorKind> { let mut data = [0u8; YKPIV_OBJ_MAX_SIZE]; let mut cb_data: usize = data.len(); let mut p_item: *mut u8 = ptr::null_mut(); let mut cb_item: usize = 0; - if pin.is_null() || pin_len == 0 || mgm.is_null() { - return Err(ErrorKind::GenericError); - } - _ykpiv_begin_transaction(state)?; let mut res = _ykpiv_ensure_application_selected(state); @@ -1503,25 +1501,13 @@ pub unsafe fn ykpiv_util_get_derived_mgm( "derived mgm salt exists, but is incorrect size = {}", cb_item, ); + + let _ = _ykpiv_end_transaction(state); + return Err(ErrorKind::GenericError); } - let _ = _ykpiv_end_transaction(state); - return Err(ErrorKind::GenericError); - } - - let p5rc = pkcs5_pbkdf2_sha1( - pin, - pin_len, - p_item, - cb_item, - ITER_MGM_PBKDF2, - (*mgm).0.as_mut_ptr(), - (*mgm).0.len(), - ); - - if p5rc != Pkcs5ErrorKind::Ok { - error!("pbkdf2 failure, err = {:?}", p5rc); - res = Err(ErrorKind::GenericError); + let salt = std::slice::from_raw_parts_mut(p_item, cb_item); + pbkdf2::>(pin, &salt, ITER_MGM_PBKDF2, &mut (*mgm).0); } }