aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorWerner Koch <[email protected]>2003-09-30 17:34:38 +0000
committerWerner Koch <[email protected]>2003-09-30 17:34:38 +0000
commit316dc2fd60875bc102bd459a4b3d4a5a59086b02 (patch)
tree304a34a93df7ae9ccb34f26d36a684d6e8249338
parentMinor fixes (diff)
downloadgnupg-316dc2fd60875bc102bd459a4b3d4a5a59086b02.tar.gz
gnupg-316dc2fd60875bc102bd459a4b3d4a5a59086b02.zip
* keylist.c (print_card_serialno): New.
(list_keyblock_print): Use it here. * card-util.c (toggle_forcesig): New. (card_edit): New command "forcesig". * card-util.c (print_name, print_isoname): Use 0 and not LF fro the max_n arg of tty_print_utf8_string2. * call-agent.c (agent_scd_getattr): New. (learn_status_cb): Release values before assignment so that it can be used by getattr to update the structure. * card-util.c (change_pin): Simplified. We now have only a PIN and an Admin PIN.
Diffstat (limited to '')
-rw-r--r--g10/ChangeLog18
-rw-r--r--g10/call-agent.c42
-rw-r--r--g10/call-agent.h3
-rw-r--r--g10/card-util.c81
-rw-r--r--g10/keylist.c41
5 files changed, 153 insertions, 32 deletions
diff --git a/g10/ChangeLog b/g10/ChangeLog
index f8120230f..0e0e715fc 100644
--- a/g10/ChangeLog
+++ b/g10/ChangeLog
@@ -1,3 +1,21 @@
+2003-09-30 Werner Koch <[email protected]>
+
+ * keylist.c (print_card_serialno): New.
+ (list_keyblock_print): Use it here.
+
+ * card-util.c (toggle_forcesig): New.
+ (card_edit): New command "forcesig".
+
+ * card-util.c (print_name, print_isoname): Use 0 and not LF fro
+ the max_n arg of tty_print_utf8_string2.
+
+ * call-agent.c (agent_scd_getattr): New.
+ (learn_status_cb): Release values before assignment so that it can
+ be used by getattr to update the structure.
+
+ * card-util.c (change_pin): Simplified. We now have only a PIN
+ and an Admin PIN.
+
2003-09-27 Werner Koch <[email protected]>
* sign.c (do_sign): Removed disabled testcode.
diff --git a/g10/call-agent.c b/g10/call-agent.c
index 00d124f0b..f07c01f2a 100644
--- a/g10/call-agent.c
+++ b/g10/call-agent.c
@@ -479,14 +479,17 @@ learn_status_cb (void *opaque, const char *line)
if (keywordlen == 8 && !memcmp (keyword, "SERIALNO", keywordlen))
{
+ xfree (parm->serialno);
parm->serialno = store_serialno (line);
}
else if (keywordlen == 9 && !memcmp (keyword, "DISP-NAME", keywordlen))
{
+ xfree (parm->disp_name);
parm->disp_name = unescape_status_string (line);
}
else if (keywordlen == 9 && !memcmp (keyword, "DISP-LANG", keywordlen))
{
+ xfree (parm->disp_lang);
parm->disp_lang = unescape_status_string (line);
}
else if (keywordlen == 8 && !memcmp (keyword, "DISP-SEX", keywordlen))
@@ -495,10 +498,12 @@ learn_status_cb (void *opaque, const char *line)
}
else if (keywordlen == 10 && !memcmp (keyword, "PUBKEY-URL", keywordlen))
{
+ xfree (parm->pubkey_url);
parm->pubkey_url = unescape_status_string (line);
}
else if (keywordlen == 10 && !memcmp (keyword, "LOGIN-DATA", keywordlen))
{
+ xfree (parm->login_data);
parm->login_data = unescape_status_string (line);
}
else if (keywordlen == 11 && !memcmp (keyword, "SIG-COUNTER", keywordlen))
@@ -574,6 +579,34 @@ agent_learn (struct agent_card_info_s *info)
return map_assuan_err (rc);
}
+/* Call the agent to retrieve a data object. This function returns
+ the data in the same structure as used by the learn command. It is
+ allowed to update such a structure using this commmand. */
+int
+agent_scd_getattr (const char *name, struct agent_card_info_s *info)
+{
+ int rc;
+ char line[ASSUAN_LINELENGTH];
+
+ if (!*name)
+ return gpg_error (GPG_ERR_INV_VALUE);
+
+ /* We assume that NAME does not need escaping. */
+ if (12 + strlen (name) > DIM(line)-1)
+ return gpg_error (GPG_ERR_TOO_LARGE);
+ stpcpy (stpcpy (line, "SCD GETATTR "), name);
+
+ rc = start_agent ();
+ if (rc)
+ return rc;
+
+ memset (info, 0, sizeof *info);
+ rc = assuan_transact (agent_ctx, line, NULL, NULL, NULL, NULL,
+ learn_status_cb, info);
+
+ return map_assuan_err (rc);
+}
+
/* Send an setattr command to the SCdaemon. */
int
@@ -809,12 +842,11 @@ agent_scd_pkdecrypt (const char *serialno,
/* Change the PIN of an OpenPGP card or reset the retry counter.
- CHVNO 1: Change the digital signature PIN
- 2: Change the decryption and authentication PIN
+ CHVNO 1: Change the PIN
+ 2: Same as 1
3: Change the admin PIN
- 101: Set a new digital signature PIN and reset the retry counter
- 102: Set a decryption and authentication PIN
- and reset the retry counter
+ 101: Set a new PIN and reset the retry counter
+ 102: Same as 101
*/
int
agent_scd_change_pin (int chvno)
diff --git a/g10/call-agent.h b/g10/call-agent.h
index e8abfbc7b..101db9574 100644
--- a/g10/call-agent.h
+++ b/g10/call-agent.h
@@ -58,6 +58,9 @@ void agent_release_card_info (struct agent_card_info_s *info);
/* Return card info. */
int agent_learn (struct agent_card_info_s *info);
+/* Update INFO with the attribute NAME. */
+int agent_scd_getattr (const char *name, struct agent_card_info_s *info);
+
/* Check whether the secret key for the key identified by HEXKEYGRIP
is available. Return 0 for yes or an error code. */
int agent_havekey (const char *hexkeygrip);
diff --git a/g10/card-util.c b/g10/card-util.c
index f42efde61..1028cd373 100644
--- a/g10/card-util.c
+++ b/g10/card-util.c
@@ -44,7 +44,6 @@ change_pin (int chvno)
{
struct agent_card_info_s info;
int rc;
- int reset_mode = 0;
rc = agent_learn (&info);
if (rc)
@@ -70,17 +69,11 @@ change_pin (int chvno)
char *answer;
tty_printf ("\n");
- tty_printf ("1 - change signature PIN\n"
- "2 - change decryption and authentication PIN\n"
- "3 - change Admin's PIN\n"
- "R - toggle reset retry counter mode\n"
+ tty_printf ("1 - change PIN\n"
+ "2 - unblock PIN\n"
+ "3 - change Admin PIN\n"
"Q - quit\n");
tty_printf ("\n");
- if (reset_mode)
- {
- tty_printf ("Reset Retry Counter mode active\n");
- tty_printf ("\n");
- }
answer = cpr_get("cardutil.change_pin.menu",_("Your selection? "));
cpr_kill_prompt();
@@ -88,30 +81,35 @@ change_pin (int chvno)
continue;
rc = 0;
- if (reset_mode && *answer == '3')
+ if (*answer == '1')
{
- tty_printf ("Sorry, reset of the Admin PIN's retry counter "
- "is not possible.\n");
+ rc = agent_scd_change_pin (1);
+ if (rc)
+ tty_printf ("Error changing the PIN: %s\n", gpg_strerror (rc));
+ else
+ tty_printf ("PIN changed.\n");
}
- else if (*answer == '1' || *answer == '2' || *answer == '3')
+ else if (*answer == '2')
{
- rc = agent_scd_change_pin (*answer - '0' + (reset_mode?100:0));
+ rc = agent_scd_change_pin (101);
if (rc)
- tty_printf ("Error changing/resetting the PIN: %s\n",
- gpg_strerror (rc));
+ tty_printf ("Error unblocking the PIN: %s\n", gpg_strerror (rc));
else
- tty_printf ("New PIN successfully set.\n");
+ tty_printf ("PIN unblocked and new PIN set.\n");
}
- else if (*answer == 'r' || *answer == 'R')
+ else if (*answer == '3')
{
- reset_mode = !reset_mode;
+ rc = agent_scd_change_pin (3);
+ if (rc)
+ tty_printf ("Error changing the PIN: %s\n", gpg_strerror (rc));
+ else
+ tty_printf ("PIN changed.\n");
}
else if (*answer == 'q' || *answer == 'Q')
{
break;
}
}
-
}
static const char *
@@ -175,7 +173,7 @@ print_name (FILE *fp, const char *text, const char *name)
if (fp)
print_utf8_string2 (fp, name, strlen (name), '\n');
else
- tty_print_utf8_string2 (name, strlen (name), '\n');
+ tty_print_utf8_string2 (name, strlen (name), 0);
}
else
tty_fprintf (fp, _("[not set]"));
@@ -207,7 +205,7 @@ print_isoname (FILE *fp, const char *text, const char *tag, const char *name)
else if (fp)
print_utf8_string2 (fp, given, strlen (given), '\n');
else
- tty_print_utf8_string2 (given, strlen (given), '\n');
+ tty_print_utf8_string2 (given, strlen (given), 0);
if (opt.with_colons)
putc (':', fp);
@@ -220,7 +218,7 @@ print_isoname (FILE *fp, const char *text, const char *tag, const char *name)
else if (fp)
print_utf8_string2 (fp, buf, strlen (buf), '\n');
else
- tty_print_utf8_string2 (buf, strlen (buf), '\n');
+ tty_print_utf8_string2 (buf, strlen (buf), 0);
xfree (buf);
}
else
@@ -339,7 +337,7 @@ card_status (FILE *fp)
print_name (fp, "URL of public key : ", info.pubkey_url);
print_name (fp, "Login data .......: ", info.login_data);
tty_fprintf (fp, "Signature PIN ....: %s\n",
- info.chv1_cached? _("cached"): _("not cached"));
+ info.chv1_cached? _("not forced"): _("forced"));
tty_fprintf (fp, "Max. PIN lengths .: %d %d %d\n",
info.chvmaxlen[0], info.chvmaxlen[1], info.chvmaxlen[2]);
tty_fprintf (fp, "PIN retry counter : %d %d %d\n",
@@ -542,6 +540,30 @@ change_sex (void)
}
+static void
+toggle_forcesig (void)
+{
+ struct agent_card_info_s info;
+ int rc;
+ int newstate;
+
+ memset (&info, 0, sizeof info);
+ rc = agent_scd_getattr ("CHV-STATUS", &info);
+ if (rc)
+ {
+ log_error ("error getting current status: %s\n", gpg_strerror (rc));
+ return;
+ }
+ newstate = !info.chv1_cached;
+ agent_release_card_info (&info);
+
+ rc = agent_scd_setattr ("CHV-STATUS-1", newstate? "\x01":"", 1);
+ if (rc)
+ log_error ("error toggling signature PIN flag: %s\n", gpg_strerror (rc));
+}
+
+
+
/* Menu to edit all user changeable values on an OpenPGP card. Only
Key creation is not handled here. */
void
@@ -551,7 +573,7 @@ card_edit (STRLIST commands)
cmdNOP = 0,
cmdQUIT, cmdHELP, cmdLIST, cmdDEBUG,
cmdNAME, cmdURL, cmdLOGIN, cmdLANG, cmdSEX,
-
+ cmdFORCESIG,
cmdINVCMD
};
@@ -572,9 +594,10 @@ card_edit (STRLIST commands)
{ N_("login") , cmdLOGIN , N_("change the login name") },
{ N_("lang") , cmdLANG , N_("change the language preferences") },
{ N_("sex") , cmdSEX , N_("change card holder's sex") },
+ { N_("forcesig"), cmdFORCESIG, N_("toggle the signature force PIN flag") },
{ NULL, cmdINVCMD }
};
-
+
enum cmdids cmd = cmdNOP;
int have_commands = !!commands;
int redisplay = 1;
@@ -692,6 +715,10 @@ card_edit (STRLIST commands)
change_sex ();
break;
+ case cmdFORCESIG:
+ toggle_forcesig ();
+ break;
+
case cmdQUIT:
goto leave;
diff --git a/g10/keylist.c b/g10/keylist.c
index f4344f204..50850de71 100644
--- a/g10/keylist.c
+++ b/g10/keylist.c
@@ -41,6 +41,7 @@
static void list_all(int);
static void list_one( STRLIST names, int secret);
+static void print_card_serialno (PKT_secret_key *sk);
struct sig_stats
{
@@ -710,6 +711,7 @@ list_keyblock_print ( KBNODE keyblock, int secret, int fpr, void *opaque )
if( !any ) {
if( fpr )
print_fingerprint( pk, sk, 0 );
+ print_card_serialno (sk);
if( opt.with_key_data )
print_key_data( pk, keyid );
any = 1;
@@ -755,6 +757,7 @@ list_keyblock_print ( KBNODE keyblock, int secret, int fpr, void *opaque )
putchar('\n');
if( fpr )
print_fingerprint( pk, sk, 0 ); /* of the main key */
+ print_card_serialno (sk);
any = 1;
}
@@ -770,7 +773,10 @@ list_keyblock_print ( KBNODE keyblock, int secret, int fpr, void *opaque )
printf(_(" [expires: %s]"), expirestr_from_sk( sk2 ) );
putchar('\n');
if( fpr > 1 )
+ {
print_fingerprint( NULL, sk2, 0 );
+ print_card_serialno (sk);
+ }
}
else if( opt.list_sigs && node->pkt->pkttype == PKT_SIGNATURE ) {
PKT_signature *sig = node->pkt->pkt.signature;
@@ -813,6 +819,7 @@ list_keyblock_print ( KBNODE keyblock, int secret, int fpr, void *opaque )
putchar('\n');
if( fpr )
print_fingerprint( pk, sk, 0 );
+ print_card_serialno (sk);
any=1;
}
@@ -1398,6 +1405,40 @@ print_fingerprint (PKT_public_key *pk, PKT_secret_key *sk, int mode )
tty_printf ("\n");
}
+
+/* Print the serial number of an OpenPGP card if available. */
+static void
+print_card_serialno (PKT_secret_key *sk)
+{
+ int i;
+
+ if (!sk)
+ return;
+ if (!sk->is_protected || sk->protect.s2k.mode != 1002)
+ return; /* Not a card. */
+ if (opt.with_colons)
+ return; /* Format not yet defined. */
+
+ fputs (_(" Card serial no. ="), stdout);
+ putchar (' ');
+ if (sk->protect.ivlen == 16
+ && !memcmp (sk->protect.iv, "\xD2\x76\x00\x01\x24\x01", 6) )
+ { /* This is an OpenPGP card. Just print the relevant part. */
+ for (i=8; i < 14; i++)
+ {
+ if (i == 10)
+ putchar (' ');
+ printf ("%02X", sk->protect.iv[i]);
+ }
+ }
+ else
+ { /* Something is wrong: Print all. */
+ for (i=0; i < sk->protect.ivlen; i++)
+ printf ("%02X", sk->protect.iv[i]);
+ }
+ putchar ('\n');
+}
+
void set_attrib_fd(int fd)
{
static int last_fd=-1;