1
0
mirror of git://git.gnupg.org/gnupg.git synced 2024-06-01 22:28:02 +02:00

scd: Support reading the Yubikey 4 firmware version.

* scd/app.c (app_new_register): Detect yk4 version numbers.
--

Having the version of the yubikey is important to select which other
methods can be used with a Yubikey.  Note that we do not detect the
formfactor of a Yubikey 4 and instead use 0 for our serial number
prefix.  This does not affect app-openpgp becuase there we use the app
specific serial number.

Signed-off-by: Werner Koch <wk@gnupg.org>
This commit is contained in:
Werner Koch 2019-03-27 17:34:50 +01:00
parent 4324560b2c
commit 5a3055eb72
No known key found for this signature in database
GPG Key ID: E3FDFF218E45B72B

View File

@ -247,9 +247,12 @@ app_new_register (int slot, ctrl_t ctrl, const char *name,
* config. */ * config. */
static char const yk_aid[] = static char const yk_aid[] =
{ 0xA0, 0x00, 0x00, 0x05, 0x27, 0x47, 0x11, 0x17 }; /*MGR*/ { 0xA0, 0x00, 0x00, 0x05, 0x27, 0x47, 0x11, 0x17 }; /*MGR*/
static char const otp_aid[] =
{ 0xA0, 0x00, 0x00, 0x05, 0x27, 0x20, 0x01 }; /*OTP*/
unsigned char *buf; unsigned char *buf;
size_t buflen; size_t buflen;
const unsigned char *s0, *s1; const unsigned char *s0;
unsigned char formfactor;
size_t n; size_t n;
if (!iso7816_select_application (slot, yk_aid, sizeof yk_aid, if (!iso7816_select_application (slot, yk_aid, sizeof yk_aid,
@ -269,29 +272,43 @@ app_new_register (int slot, ctrl_t ctrl, const char *name,
if (buflen > 1) if (buflen > 1)
{ {
s0 = find_tlv (buf+1, buflen-1, 0x04, &n); /* Form factor */ s0 = find_tlv (buf+1, buflen-1, 0x04, &n); /* Form factor */
if (s0 && n == 1) formfactor = (s0 && n == 1)? *s0 : 0;
s0 = find_tlv (buf+1, buflen-1, 0x02, &n); /* Serial */
if (s0 && n >= 4)
{ {
s1 = find_tlv (buf+1, buflen-1, 0x02, &n); /* Serial */ app->serialno = xtrymalloc (3 + 1 + n);
if (s1 && n >= 4) if (app->serialno)
{ {
app->serialno = xtrymalloc (3 + 1 + n); app->serialnolen = 3 + 1 + n;
if (app->serialno) app->serialno[0] = 0xff;
{ app->serialno[1] = 0x02;
app->serialnolen = 3 + 1 + n; app->serialno[2] = 0x0;
app->serialno[0] = 0xff; app->serialno[3] = formfactor;
app->serialno[1] = 0x02; memcpy (app->serialno + 4, s0, n);
app->serialno[2] = 0x0; /* Note that we do not clear the error
app->serialno[3] = *s0; * so that no further serial number
memcpy (app->serialno + 4, s1, n); * testing is done. After all we just
/* Note that we do not clear the error * set the serial number. */
* so that no further serial number
* testing is done. After all we just
* set the serial number. */
}
} }
s1 = find_tlv (buf+1, buflen-1, 0x05, &n); /* version */ }
if (s1 && n == 3)
app->cardversion = ((s1[0]<<16)|(s1[1]<<8)|s1[2]); s0 = find_tlv (buf+1, buflen-1, 0x05, &n); /* version */
if (s0 && n == 3)
app->cardversion = ((s0[0]<<16)|(s0[1]<<8)|s0[2]);
else if (!s0)
{
/* No version - this is not a Yubikey 5. We now
* switch to the OTP app and take the first
* three bytes of the reponse as version
* number. */
xfree (buf);
buf = NULL;
if (!iso7816_select_application_ext (slot,
otp_aid, sizeof otp_aid,
1, &buf, &buflen)
&& buflen > 3)
app->cardversion = ((buf[0]<<16)|(buf[1]<<8)|buf[2]);
} }
} }
xfree (buf); xfree (buf);