pub(crate) unsafe fn _cache_pin(state: *mut YubiKey, pin: *const c_char, len: usize) -> ErrorKind {
    if state.is_null() {
        return ErrorKind::ArgumentError;
    }

    if !pin.is_null() && ((*state).pin as *const c_char == pin) {
        return ErrorKind::Ok;
    }

    if !(*state).pin.is_null() {
        // Zeroize the old cached PIN
        let old_len = strlen((*state).pin as *const c_char);
        let pin_slice = slice::from_raw_parts_mut((*state).pin, old_len);
        pin_slice.zeroize();

        free((*state).pin as (*mut c_void));
        (*state).pin = ptr::null_mut();
    }

    if !pin.is_null() && len > 0 {
        (*state).pin = malloc(len + 1) as (*mut u8);

        if (*state).pin.is_null() {
            return ErrorKind::MemoryError;
        }

        memcpy((*state).pin as (*mut c_void), pin as (*const c_void), len);
        *(*state).pin.add(len) = 0u8;
    }

    ErrorKind::Ok
}
/// Cache PIN in memory
// TODO(tarcieri): better security around the cached PIN
Cache PIN in memory
TODO(tarcieri): better security around the cached PIN
Cache PIN in memory TODO ( tarcieri ) : better security around the cached PIN
pub(crate) unsafe fn _cache_pin(state: *mut YubiKey, pin: *const c_char, len: usize) -> ErrorKind {
    if state.is_null() {
        return ErrorKind::ArgumentError;
    }
    if !pin.is_null() && ((*state).pin as *const c_char == pin) {
        return ErrorKind::Ok;
    }
    if !(*state).pin.is_null() {
        // Zeroize the old cached PIN
        let old_len = strlen((*state).pin as *const c_char);
        let pin_slice = slice::from_raw_parts_mut((*state).pin, old_len);
        pin_slice.zeroize();
        free((*state).pin as (*mut c_void));
        (*state).pin = ptr::null_mut();
    }
    if !pin.is_null() && len > 0 {
        (*state).pin = malloc(len + 1) as (*mut u8);
        if (*state).pin.is_null() {
            return ErrorKind::MemoryError;
        }
        memcpy((*state).pin as (*mut c_void), pin as (*const c_void), len);
        *(*state).pin.add(len) = 0u8;
    }
    ErrorKind::Ok
}
pub ( crate ) unsafe fn _cache_pin ( state : * mut YubiKey , pin : * const c_char , len : usize ) -> ErrorKind { if state . is_null ( ) { return ErrorKind :: ArgumentError ; } if ! pin . is_null ( ) && ( ( * state ) . pin as * const c_char == pin ) { return ErrorKind :: Ok ; } if ! ( * state ) . pin . is_null ( ) { // Zeroize the old cached PIN let old_len = strlen ( ( * state ) . pin as * const c_char ) ; let pin_slice = slice :: from_raw_parts_mut ( ( * state ) . pin , old_len ) ; pin_slice . zeroize ( ) ; free ( ( * state ) . pin as ( * mut c_void ) ) ; ( * state ) . pin = ptr :: null_mut ( ) ; } if ! pin . is_null ( ) && len > 0 { ( * state ) . pin = malloc ( len + 1 ) as ( * mut u8 ) ; if ( * state ) . pin . is_null ( ) { return ErrorKind :: MemoryError ; } memcpy ( ( * state ) . pin as ( * mut c_void ) , pin as ( * const c_void ) , len ) ; * ( * state ) . pin . add ( len ) = 0u8 ; } ErrorKind :: Ok }
Cache PIN in memory
TODO(tarcieri): better security around the cached PIN
Cache PIN in memory TODO ( tarcieri ) : better security around the cached PIN
state
*mut YubiKey
pin
*const c_char
len
usize