Merge pull request #26 from syzzer/query-for-pin

Query for PIN/PUK/mgmt-key if not supplied on command line
This commit is contained in:
Klas Lindfors
2015-08-13 14:35:08 +02:00
3 changed files with 73 additions and 28 deletions
+24
View File
@@ -37,6 +37,7 @@
#include <windows.h>
#endif
#include <openssl/evp.h>
#include <openssl/x509.h>
#include <ykpiv.h>
@@ -238,3 +239,26 @@ bool prepare_rsa_signature(const unsigned char *in, unsigned int in_len, unsigne
*out_len = (unsigned int)i2d_X509_SIG(&digestInfo, &out);
return true;
}
bool read_pw(const char *name, char *pwbuf, size_t pwbuflen, int verify) {
#define READ_PW_PROMPT_BASE "Enter %s: "
char prompt[sizeof(READ_PW_PROMPT_BASE) + 32] = {0};
int ret;
if (pwbuflen < 1) {
fprintf(stderr, "Failed to read %s: buffer too small.", name);
return false;
}
ret = snprintf(prompt, sizeof(prompt), READ_PW_PROMPT_BASE, name);
if (ret < 0 || ((unsigned int) ret) > (sizeof(prompt)-1)) {
fprintf(stderr, "Failed to read %s: snprintf failed.\n", name);
return false;
}
if (0 != EVP_read_pw_string(pwbuf, pwbuflen-1, prompt, verify)) {
fprintf(stderr, "Retrieving %s failed.\n", name);
return false;
}
return true;
}
+1
View File
@@ -48,5 +48,6 @@ int get_object_id(enum enum_slot slot);
bool set_component_with_len(unsigned char**, const BIGNUM*, int);
bool prepare_rsa_signature(const unsigned char*, unsigned int, unsigned char*,
unsigned int*, int);
bool read_pw(const char*, char*, size_t, int);
#endif
+48 -28
View File
@@ -938,7 +938,15 @@ selfsign_out:
static bool verify_pin(ykpiv_state *state, const char *pin) {
int tries = -1;
ykpiv_rc res;
int len = strlen(pin);
int len;
char pinbuf[9] = {0};
if(!pin) {
if (!read_pw("PIN", pinbuf, sizeof(pinbuf), false)) {
return false;
}
pin = pinbuf;
}
len = strlen(pin);
if(len > 8) {
fprintf(stderr, "Maximum 8 digits of PIN supported.\n");
@@ -967,9 +975,28 @@ static bool change_pin(ykpiv_state *state, enum enum_action action, const char *
unsigned char indata[0x10];
unsigned char data[0xff];
unsigned long recv_len = sizeof(data);
char pinbuf[9] = {0};
char new_pinbuf[9] = {0};
const char *name = action == action_arg_changeMINUS_pin ? "pin" : "puk";
const char *new_name = action == action_arg_changeMINUS_pin ? "new pin" : "new puk";
int sw;
size_t pin_len = strlen(pin);
size_t new_len = strlen(new_pin);
size_t pin_len;
size_t new_len;
if(!pin) {
if (!read_pw(name, pinbuf, sizeof(pinbuf), false)) {
return false;
}
pin = pinbuf;
}
if(!new_pin) {
if (!read_pw(new_name, new_pinbuf, sizeof(new_pinbuf), true)) {
return false;
}
new_pin = new_pinbuf;
}
pin_len = strlen(pin);
new_len = strlen(new_pin);
if(pin_len > 8 || new_len > 8) {
fprintf(stderr, "Maximum 8 digits of PIN supported.\n");
@@ -996,7 +1023,7 @@ static bool change_pin(ykpiv_state *state, enum enum_action action, const char *
if((sw >> 8) == 0x63) {
int tries = sw & 0xff;
fprintf(stderr, "Failed verifying %s code, now %d tries left before blocked.\n",
action == action_arg_changeMINUS_pin ? "pin" : "puk", tries);
name, tries);
} else if(sw == 0x6983) {
if(action == action_arg_changeMINUS_pin) {
fprintf(stderr, "The pin code is blocked, use the unblock-pin action to unblock it.\n");
@@ -1657,28 +1684,6 @@ int main(int argc, char *argv[]) {
return EXIT_FAILURE;
}
break;
case action_arg_changeMINUS_pin:
case action_arg_changeMINUS_puk:
case action_arg_unblockMINUS_pin:
if(!args_info.new_pin_arg) {
fprintf(stderr, "The '%s' action needs a new-pin (-N).\n",
cmdline_parser_action_values[action]);
return EXIT_FAILURE;
}
case action_arg_verifyMINUS_pin:
if(!args_info.pin_arg) {
fprintf(stderr, "The '%s' action needs a pin (-P).\n",
cmdline_parser_action_values[action]);
return EXIT_FAILURE;
}
break;
case action_arg_setMINUS_mgmMINUS_key:
if(!args_info.new_key_arg) {
fprintf(stderr, "The '%s' action needs the new-key (-n) argument.\n",
cmdline_parser_action_values[action]);
return EXIT_FAILURE;
}
break;
case action_arg_pinMINUS_retries:
if(!args_info.pin_retries_arg || !args_info.puk_retries_arg) {
fprintf(stderr, "The '%s' action needs both --pin-retries and --puk-retries arguments.\n",
@@ -1686,6 +1691,11 @@ int main(int argc, char *argv[]) {
return EXIT_FAILURE;
}
break;
case action_arg_changeMINUS_pin:
case action_arg_changeMINUS_puk:
case action_arg_unblockMINUS_pin:
case action_arg_verifyMINUS_pin:
case action_arg_setMINUS_mgmMINUS_key:
case action_arg_setMINUS_chuid:
case action_arg_version:
case action_arg_reset:
@@ -1764,6 +1774,8 @@ int main(int argc, char *argv[]) {
OpenSSL_add_all_algorithms();
for(i = 0; i < args_info.action_given; i++) {
char new_keybuf[KEY_LEN*2+1] = {0};
char *new_mgm_key = args_info.new_key_arg;
action = *(args_info.action_arg + i);
if(verbosity) {
fprintf(stderr, "Now processing for action '%s'.\n",
@@ -1781,10 +1793,18 @@ int main(int argc, char *argv[]) {
}
break;
case action_arg_setMINUS_mgmMINUS_key:
if(strlen(args_info.new_key_arg) == (KEY_LEN * 2)){
if(!new_mgm_key) {
if(!read_pw("new management key", new_keybuf, sizeof(new_keybuf), true)) {
fprintf(stderr, "Failed to read management key from stdin,\n");
ret = EXIT_FAILURE;
break;
}
new_mgm_key = new_keybuf;
}
if(strlen(new_mgm_key) == (KEY_LEN * 2)){
unsigned char new_key[KEY_LEN];
size_t new_key_len = sizeof(new_key);
if(ykpiv_hex_decode(args_info.new_key_arg, strlen(args_info.new_key_arg), new_key, &new_key_len) != YKPIV_OK) {
if(ykpiv_hex_decode(new_mgm_key, strlen(new_mgm_key), new_key, &new_key_len) != YKPIV_OK) {
fprintf(stderr, "Failed decoding new key!\n");
ret = EXIT_FAILURE;
} else if(ykpiv_set_mgmkey(state, new_key) != YKPIV_OK) {