Avoid catch-22 with README.main not being distributed but having the
[gnupg.git] / scd / iso7816.c
blobe3f2c1bebe923393352cb6a7c120d7805689e1fe
1 /* iso7816.c - ISO 7816 commands
2 * Copyright (C) 2003, 2004, 2008, 2009 Free Software Foundation, Inc.
4 * This file is part of GnuPG.
6 * GnuPG is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 3 of the License, or
9 * (at your option) any later version.
11 * GnuPG is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, see <http://www.gnu.org/licenses/>.
20 #include <config.h>
21 #include <errno.h>
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <string.h>
26 #if defined(GNUPG_SCD_MAIN_HEADER)
27 #include GNUPG_SCD_MAIN_HEADER
28 #elif GNUPG_MAJOR_VERSION == 1
29 /* This is used with GnuPG version < 1.9. The code has been source
30 copied from the current GnuPG >= 1.9 and is maintained over
31 there. */
32 #include "options.h"
33 #include "errors.h"
34 #include "memory.h"
35 #include "util.h"
36 #include "i18n.h"
37 #else /* GNUPG_MAJOR_VERSION != 1 */
38 #include "scdaemon.h"
39 #endif /* GNUPG_MAJOR_VERSION != 1 */
41 #include "iso7816.h"
42 #include "apdu.h"
45 #define CMD_SELECT_FILE 0xA4
46 #define CMD_VERIFY ISO7816_VERIFY
47 #define CMD_CHANGE_REFERENCE_DATA ISO7816_CHANGE_REFERENCE_DATA
48 #define CMD_RESET_RETRY_COUNTER ISO7816_RESET_RETRY_COUNTER
49 #define CMD_GET_DATA 0xCA
50 #define CMD_PUT_DATA 0xDA
51 #define CMD_MSE 0x22
52 #define CMD_PSO 0x2A
53 #define CMD_INTERNAL_AUTHENTICATE 0x88
54 #define CMD_GENERATE_KEYPAIR 0x47
55 #define CMD_GET_CHALLENGE 0x84
56 #define CMD_READ_BINARY 0xB0
57 #define CMD_READ_RECORD 0xB2
59 static gpg_error_t
60 map_sw (int sw)
62 gpg_err_code_t ec;
64 switch (sw)
66 case SW_EEPROM_FAILURE: ec = GPG_ERR_HARDWARE; break;
67 case SW_TERM_STATE: ec = GPG_ERR_CARD; break;
68 case SW_WRONG_LENGTH: ec = GPG_ERR_INV_VALUE; break;
69 case SW_SM_NOT_SUP: ec = GPG_ERR_NOT_SUPPORTED; break;
70 case SW_CC_NOT_SUP: ec = GPG_ERR_NOT_SUPPORTED; break;
71 case SW_CHV_WRONG: ec = GPG_ERR_BAD_PIN; break;
72 case SW_CHV_BLOCKED: ec = GPG_ERR_PIN_BLOCKED; break;
73 case SW_USE_CONDITIONS: ec = GPG_ERR_USE_CONDITIONS; break;
74 case SW_NOT_SUPPORTED: ec = GPG_ERR_NOT_SUPPORTED; break;
75 case SW_BAD_PARAMETER: ec = GPG_ERR_INV_VALUE; break;
76 case SW_FILE_NOT_FOUND: ec = GPG_ERR_ENOENT; break;
77 case SW_RECORD_NOT_FOUND:ec= GPG_ERR_NOT_FOUND; break;
78 case SW_REF_NOT_FOUND: ec = GPG_ERR_NO_OBJ; break;
79 case SW_BAD_P0_P1: ec = GPG_ERR_INV_VALUE; break;
80 case SW_EXACT_LENGTH: ec = GPG_ERR_INV_VALUE; break;
81 case SW_INS_NOT_SUP: ec = GPG_ERR_CARD; break;
82 case SW_CLA_NOT_SUP: ec = GPG_ERR_CARD; break;
83 case SW_SUCCESS: ec = 0; break;
85 case SW_HOST_OUT_OF_CORE: ec = GPG_ERR_ENOMEM; break;
86 case SW_HOST_INV_VALUE: ec = GPG_ERR_INV_VALUE; break;
87 case SW_HOST_INCOMPLETE_CARD_RESPONSE: ec = GPG_ERR_CARD; break;
88 case SW_HOST_NOT_SUPPORTED: ec = GPG_ERR_NOT_SUPPORTED; break;
89 case SW_HOST_LOCKING_FAILED: ec = GPG_ERR_BUG; break;
90 case SW_HOST_BUSY: ec = GPG_ERR_EBUSY; break;
91 case SW_HOST_NO_CARD: ec = GPG_ERR_CARD_NOT_PRESENT; break;
92 case SW_HOST_CARD_INACTIVE: ec = GPG_ERR_CARD_RESET; break;
93 case SW_HOST_CARD_IO_ERROR: ec = GPG_ERR_EIO; break;
94 case SW_HOST_GENERAL_ERROR: ec = GPG_ERR_GENERAL; break;
95 case SW_HOST_NO_READER: ec = GPG_ERR_ENODEV; break;
96 case SW_HOST_ABORTED: ec = GPG_ERR_CANCELED; break;
97 case SW_HOST_NO_KEYPAD: ec = GPG_ERR_NOT_SUPPORTED; break;
99 default:
100 if ((sw & 0x010000))
101 ec = GPG_ERR_GENERAL; /* Should not happen. */
102 else if ((sw & 0xff00) == SW_MORE_DATA)
103 ec = 0; /* This should actually never been seen here. */
104 else
105 ec = GPG_ERR_CARD;
107 return gpg_error (ec);
110 /* Map a status word from the APDU layer to a gpg-error code. */
111 gpg_error_t
112 iso7816_map_sw (int sw)
114 /* All APDU functions should return 0x9000 on success but for
115 historical reasons of the implementation some return 0 to
116 indicate success. We allow for that here. */
117 return sw? map_sw (sw) : 0;
121 /* This function is specialized version of the SELECT FILE command.
122 SLOT is the card and reader as created for example by
123 apdu_open_reader (), AID is a buffer of size AIDLEN holding the
124 requested application ID. The function can't be used to enumerate
125 AIDs and won't return the AID on success. The return value is 0
126 for okay or a GPG error code. Note that ISO error codes are
127 internally mapped. Bit 0 of FLAGS should be set if the card does
128 not understand P2=0xC0. */
129 gpg_error_t
130 iso7816_select_application (int slot, const char *aid, size_t aidlen,
131 unsigned int flags)
133 int sw;
134 sw = apdu_send_simple (slot, 0, 0x00, CMD_SELECT_FILE, 4,
135 (flags&1)? 0 :0x0c, aidlen, aid);
136 return map_sw (sw);
140 gpg_error_t
141 iso7816_select_file (int slot, int tag, int is_dir,
142 unsigned char **result, size_t *resultlen)
144 int sw, p0, p1;
145 unsigned char tagbuf[2];
147 tagbuf[0] = (tag >> 8) & 0xff;
148 tagbuf[1] = tag & 0xff;
150 if (result || resultlen)
152 *result = NULL;
153 *resultlen = 0;
154 return gpg_error (GPG_ERR_NOT_IMPLEMENTED);
156 else
158 p0 = (tag == 0x3F00)? 0: is_dir? 1:2;
159 p1 = 0x0c; /* No FC return. */
160 sw = apdu_send_simple (slot, 0, 0x00, CMD_SELECT_FILE,
161 p0, p1, 2, (char*)tagbuf );
162 return map_sw (sw);
165 return 0;
169 /* Do a select file command with a direct path. */
170 gpg_error_t
171 iso7816_select_path (int slot, const unsigned short *path, size_t pathlen,
172 unsigned char **result, size_t *resultlen)
174 int sw, p0, p1;
175 unsigned char buffer[100];
176 int buflen;
178 if (result || resultlen)
180 *result = NULL;
181 *resultlen = 0;
182 return gpg_error (GPG_ERR_NOT_IMPLEMENTED);
185 if (pathlen/2 >= sizeof buffer)
186 return gpg_error (GPG_ERR_TOO_LARGE);
188 for (buflen = 0; pathlen; pathlen--, path++)
190 buffer[buflen++] = (*path >> 8);
191 buffer[buflen++] = *path;
194 p0 = 0x08;
195 p1 = 0x0c; /* No FC return. */
196 sw = apdu_send_simple (slot, 0, 0x00, CMD_SELECT_FILE,
197 p0, p1, buflen, (char*)buffer );
198 return map_sw (sw);
202 /* This is a private command currently only working for TCOS cards. */
203 gpg_error_t
204 iso7816_list_directory (int slot, int list_dirs,
205 unsigned char **result, size_t *resultlen)
207 int sw;
209 if (!result || !resultlen)
210 return gpg_error (GPG_ERR_INV_VALUE);
211 *result = NULL;
212 *resultlen = 0;
214 sw = apdu_send (slot, 0, 0x80, 0xAA, list_dirs? 1:2, 0, -1, NULL,
215 result, resultlen);
216 if (sw != SW_SUCCESS)
218 /* Make sure that pending buffers are released. */
219 xfree (*result);
220 *result = NULL;
221 *resultlen = 0;
223 return map_sw (sw);
227 /* This funcion sends an already formatted APDU to the card. With
228 HANDLE_MORE set to true a MORE DATA status will be handled
229 internally. The return value is a gpg error code (i.e. a mapped
230 status word). This is basically the same as apdu_send_direct but
231 it maps the status word and does not return it in the result
232 buffer. */
233 gpg_error_t
234 iso7816_apdu_direct (int slot, const void *apdudata, size_t apdudatalen,
235 int handle_more,
236 unsigned char **result, size_t *resultlen)
238 int sw;
240 if (!result || !resultlen)
241 return gpg_error (GPG_ERR_INV_VALUE);
242 *result = NULL;
243 *resultlen = 0;
245 sw = apdu_send_direct (slot, 0, apdudata, apdudatalen, handle_more,
246 result, resultlen);
247 if (!sw)
249 if (*resultlen < 2)
250 sw = SW_HOST_GENERAL_ERROR;
251 else
253 sw = ((*result)[*resultlen-2] << 8) | (*result)[*resultlen-1];
254 (*resultlen)--;
255 (*resultlen)--;
258 if (sw != SW_SUCCESS)
260 /* Make sure that pending buffers are released. */
261 xfree (*result);
262 *result = NULL;
263 *resultlen = 0;
265 return map_sw (sw);
269 /* Check whether the reader supports the ISO command code COMMAND on
270 the keypad. Returns 0 on success. */
271 gpg_error_t
272 iso7816_check_keypad (int slot, int command, iso7816_pininfo_t *pininfo)
274 int sw;
276 sw = apdu_check_keypad (slot, command,
277 pininfo->mode, pininfo->minlen, pininfo->maxlen,
278 pininfo->padlen);
279 return iso7816_map_sw (sw);
283 /* Perform a VERIFY command on SLOT using the card holder verification
284 vector CHVNO with a CHV of lenght CHVLEN. With PININFO non-NULL
285 the keypad of the reader will be used. Returns 0 on success. */
286 gpg_error_t
287 iso7816_verify_kp (int slot, int chvno, const char *chv, size_t chvlen,
288 iso7816_pininfo_t *pininfo)
290 int sw;
292 if (pininfo && pininfo->mode)
293 sw = apdu_send_simple_kp (slot, 0x00, CMD_VERIFY, 0, chvno, chvlen, chv,
294 pininfo->mode,
295 pininfo->minlen,
296 pininfo->maxlen,
297 pininfo->padlen);
298 else
299 sw = apdu_send_simple (slot, 0, 0x00, CMD_VERIFY, 0, chvno, chvlen, chv);
300 return map_sw (sw);
303 /* Perform a VERIFY command on SLOT using the card holder verification
304 vector CHVNO with a CHV of lenght CHVLEN. Returns 0 on success. */
305 gpg_error_t
306 iso7816_verify (int slot, int chvno, const char *chv, size_t chvlen)
308 return iso7816_verify_kp (slot, chvno, chv, chvlen, NULL);
311 /* Perform a CHANGE_REFERENCE_DATA command on SLOT for the card holder
312 verification vector CHVNO. If the OLDCHV is NULL (and OLDCHVLEN
313 0), a "change reference data" is done, otherwise an "exchange
314 reference data". The new reference data is expected in NEWCHV of
315 length NEWCHVLEN. With PININFO non-NULL the keypad of the reader
316 will be used. */
317 gpg_error_t
318 iso7816_change_reference_data_kp (int slot, int chvno,
319 const char *oldchv, size_t oldchvlen,
320 const char *newchv, size_t newchvlen,
321 iso7816_pininfo_t *pininfo)
323 int sw;
324 char *buf;
326 if ((!oldchv && oldchvlen)
327 || (oldchv && !oldchvlen)
328 || !newchv || !newchvlen )
329 return gpg_error (GPG_ERR_INV_VALUE);
331 buf = xtrymalloc (oldchvlen + newchvlen);
332 if (!buf)
333 return gpg_error (gpg_err_code_from_errno (errno));
334 if (oldchvlen)
335 memcpy (buf, oldchv, oldchvlen);
336 memcpy (buf+oldchvlen, newchv, newchvlen);
338 if (pininfo && pininfo->mode)
339 sw = apdu_send_simple_kp (slot, 0x00, CMD_CHANGE_REFERENCE_DATA,
340 oldchvlen? 0 : 1, chvno, oldchvlen+newchvlen, buf,
341 pininfo->mode,
342 pininfo->minlen,
343 pininfo->maxlen,
344 pininfo->padlen);
345 else
346 sw = apdu_send_simple (slot, 0, 0x00, CMD_CHANGE_REFERENCE_DATA,
347 oldchvlen? 0 : 1, chvno, oldchvlen+newchvlen, buf);
348 xfree (buf);
349 return map_sw (sw);
353 /* Perform a CHANGE_REFERENCE_DATA command on SLOT for the card holder
354 verification vector CHVNO. If the OLDCHV is NULL (and OLDCHVLEN
355 0), a "change reference data" is done, otherwise an "exchange
356 reference data". The new reference data is expected in NEWCHV of
357 length NEWCHVLEN. */
358 gpg_error_t
359 iso7816_change_reference_data (int slot, int chvno,
360 const char *oldchv, size_t oldchvlen,
361 const char *newchv, size_t newchvlen)
363 return iso7816_change_reference_data_kp (slot, chvno, oldchv, oldchvlen,
364 newchv, newchvlen, NULL);
368 gpg_error_t
369 iso7816_reset_retry_counter_kp (int slot, int chvno,
370 const char *newchv, size_t newchvlen,
371 iso7816_pininfo_t *pininfo)
373 int sw;
375 if (!newchv || !newchvlen )
376 return gpg_error (GPG_ERR_INV_VALUE);
378 /* FIXME: The keypad mode has not yet been tested. */
379 if (pininfo && pininfo->mode)
380 sw = apdu_send_simple_kp (slot, 0x00, CMD_RESET_RETRY_COUNTER,
381 2, chvno, newchvlen, newchv,
382 pininfo->mode,
383 pininfo->minlen,
384 pininfo->maxlen,
385 pininfo->padlen);
386 else
387 sw = apdu_send_simple (slot, 0, 0x00, CMD_RESET_RETRY_COUNTER,
388 2, chvno, newchvlen, newchv);
389 return map_sw (sw);
393 gpg_error_t
394 iso7816_reset_retry_counter_with_rc (int slot, int chvno,
395 const char *data, size_t datalen)
397 int sw;
399 if (!data || !datalen )
400 return gpg_error (GPG_ERR_INV_VALUE);
402 sw = apdu_send_simple (slot, 0, 0x00, CMD_RESET_RETRY_COUNTER,
403 0, chvno, datalen, data);
404 return map_sw (sw);
408 gpg_error_t
409 iso7816_reset_retry_counter (int slot, int chvno,
410 const char *newchv, size_t newchvlen)
412 return iso7816_reset_retry_counter_kp (slot, chvno, newchv, newchvlen, NULL);
417 /* Perform a GET DATA command requesting TAG and storing the result in
418 a newly allocated buffer at the address passed by RESULT. Return
419 the length of this data at the address of RESULTLEN. */
420 gpg_error_t
421 iso7816_get_data (int slot, int extended_mode, int tag,
422 unsigned char **result, size_t *resultlen)
424 int sw;
425 int le;
427 if (!result || !resultlen)
428 return gpg_error (GPG_ERR_INV_VALUE);
429 *result = NULL;
430 *resultlen = 0;
432 if (extended_mode > 0 && extended_mode < 256)
433 le = 65534; /* Not 65535 in case it is used as some special flag. */
434 else if (extended_mode > 0)
435 le = extended_mode;
436 else
437 le = 256;
439 sw = apdu_send_le (slot, extended_mode, 0x00, CMD_GET_DATA,
440 ((tag >> 8) & 0xff), (tag & 0xff), -1, NULL, le,
441 result, resultlen);
442 if (sw != SW_SUCCESS)
444 /* Make sure that pending buffers are released. */
445 xfree (*result);
446 *result = NULL;
447 *resultlen = 0;
448 return map_sw (sw);
451 return 0;
455 /* Perform a PUT DATA command on card in SLOT. Write DATA of length
456 DATALEN to TAG. EXTENDED_MODE controls whether extended length
457 headers or command chaining is used instead of single length
458 bytes. */
459 gpg_error_t
460 iso7816_put_data (int slot, int extended_mode, int tag,
461 const void *data, size_t datalen)
463 int sw;
465 sw = apdu_send_simple (slot, extended_mode, 0x00, CMD_PUT_DATA,
466 ((tag >> 8) & 0xff), (tag & 0xff),
467 datalen, (const char*)data);
468 return map_sw (sw);
471 /* Same as iso7816_put_data but uses an odd instruction byte. */
472 gpg_error_t
473 iso7816_put_data_odd (int slot, int extended_mode, int tag,
474 const void *data, size_t datalen)
476 int sw;
478 sw = apdu_send_simple (slot, extended_mode, 0x00, CMD_PUT_DATA+1,
479 ((tag >> 8) & 0xff), (tag & 0xff),
480 datalen, (const char*)data);
481 return map_sw (sw);
484 /* Manage Security Environment. This is a weird operation and there
485 is no easy abstraction for it. Furthermore, some card seem to have
486 a different interpreation of 7816-8 and thus we resort to let the
487 caller decide what to do. */
488 gpg_error_t
489 iso7816_manage_security_env (int slot, int p1, int p2,
490 const unsigned char *data, size_t datalen)
492 int sw;
494 if (p1 < 0 || p1 > 255 || p2 < 0 || p2 > 255 )
495 return gpg_error (GPG_ERR_INV_VALUE);
497 sw = apdu_send_simple (slot, 0, 0x00, CMD_MSE, p1, p2,
498 data? datalen : -1, (const char*)data);
499 return map_sw (sw);
503 /* Perform the security operation COMPUTE DIGITAL SIGANTURE. On
504 success 0 is returned and the data is availavle in a newly
505 allocated buffer stored at RESULT with its length stored at
506 RESULTLEN. For LE see do_generate_keypair. */
507 gpg_error_t
508 iso7816_compute_ds (int slot, int extended_mode,
509 const unsigned char *data, size_t datalen, int le,
510 unsigned char **result, size_t *resultlen)
512 int sw;
514 if (!data || !datalen || !result || !resultlen)
515 return gpg_error (GPG_ERR_INV_VALUE);
516 *result = NULL;
517 *resultlen = 0;
519 if (!extended_mode)
520 le = 256; /* Ignore provided Le and use what apdu_send uses. */
521 else if (le >= 0 && le < 256)
522 le = 256;
524 sw = apdu_send_le (slot, extended_mode,
525 0x00, CMD_PSO, 0x9E, 0x9A,
526 datalen, (const char*)data,
528 result, resultlen);
529 if (sw != SW_SUCCESS)
531 /* Make sure that pending buffers are released. */
532 xfree (*result);
533 *result = NULL;
534 *resultlen = 0;
535 return map_sw (sw);
538 return 0;
542 /* Perform the security operation DECIPHER. PADIND is the padding
543 indicator to be used. It should be 0 if no padding is required, a
544 value of -1 suppresses the padding byte. On success 0 is returned
545 and the plaintext is available in a newly allocated buffer stored
546 at RESULT with its length stored at RESULTLEN. For LE see
547 do_generate_keypair. */
548 gpg_error_t
549 iso7816_decipher (int slot, int extended_mode,
550 const unsigned char *data, size_t datalen, int le,
551 int padind, unsigned char **result, size_t *resultlen)
553 int sw;
554 unsigned char *buf;
556 if (!data || !datalen || !result || !resultlen)
557 return gpg_error (GPG_ERR_INV_VALUE);
558 *result = NULL;
559 *resultlen = 0;
561 if (!extended_mode)
562 le = 256; /* Ignore provided Le and use what apdu_send uses. */
563 else if (le >= 0 && le < 256)
564 le = 256;
566 if (padind >= 0)
568 /* We need to prepend the padding indicator. */
569 buf = xtrymalloc (datalen + 1);
570 if (!buf)
571 return gpg_error (gpg_err_code_from_errno (errno));
573 *buf = padind; /* Padding indicator. */
574 memcpy (buf+1, data, datalen);
575 sw = apdu_send_le (slot, extended_mode,
576 0x00, CMD_PSO, 0x80, 0x86,
577 datalen+1, (char*)buf, le,
578 result, resultlen);
579 xfree (buf);
581 else
583 sw = apdu_send_le (slot, extended_mode,
584 0x00, CMD_PSO, 0x80, 0x86,
585 datalen, (const char *)data, le,
586 result, resultlen);
588 if (sw != SW_SUCCESS)
590 /* Make sure that pending buffers are released. */
591 xfree (*result);
592 *result = NULL;
593 *resultlen = 0;
594 return map_sw (sw);
597 return 0;
601 /* For LE see do_generate_keypair. */
602 gpg_error_t
603 iso7816_internal_authenticate (int slot, int extended_mode,
604 const unsigned char *data, size_t datalen,
605 int le,
606 unsigned char **result, size_t *resultlen)
608 int sw;
610 if (!data || !datalen || !result || !resultlen)
611 return gpg_error (GPG_ERR_INV_VALUE);
612 *result = NULL;
613 *resultlen = 0;
615 if (!extended_mode)
616 le = 256; /* Ignore provided Le and use what apdu_send uses. */
617 else if (le >= 0 && le < 256)
618 le = 256;
620 sw = apdu_send_le (slot, extended_mode,
621 0x00, CMD_INTERNAL_AUTHENTICATE, 0, 0,
622 datalen, (const char*)data,
624 result, resultlen);
625 if (sw != SW_SUCCESS)
627 /* Make sure that pending buffers are released. */
628 xfree (*result);
629 *result = NULL;
630 *resultlen = 0;
631 return map_sw (sw);
634 return 0;
638 /* LE is the expected return length. This is usually 0 except if
639 extended length mode is used and more than 256 byte will be
640 returned. In that case a value of -1 uses a large default
641 (e.g. 4096 bytes), a value larger 256 used that value. */
642 static gpg_error_t
643 do_generate_keypair (int slot, int extended_mode, int readonly,
644 const unsigned char *data, size_t datalen,
645 int le,
646 unsigned char **result, size_t *resultlen)
648 int sw;
650 if (!data || !datalen || !result || !resultlen)
651 return gpg_error (GPG_ERR_INV_VALUE);
652 *result = NULL;
653 *resultlen = 0;
655 sw = apdu_send_le (slot, extended_mode,
656 0x00, CMD_GENERATE_KEYPAIR, readonly? 0x81:0x80, 0,
657 datalen, (const char*)data,
658 le >= 0 && le < 256? 256:le,
659 result, resultlen);
660 if (sw != SW_SUCCESS)
662 /* Make sure that pending buffers are released. */
663 xfree (*result);
664 *result = NULL;
665 *resultlen = 0;
666 return map_sw (sw);
669 return 0;
673 gpg_error_t
674 iso7816_generate_keypair (int slot, int extended_mode,
675 const unsigned char *data, size_t datalen,
676 int le,
677 unsigned char **result, size_t *resultlen)
679 return do_generate_keypair (slot, extended_mode, 0,
680 data, datalen, le, result, resultlen);
684 gpg_error_t
685 iso7816_read_public_key (int slot, int extended_mode,
686 const unsigned char *data, size_t datalen,
687 int le,
688 unsigned char **result, size_t *resultlen)
690 return do_generate_keypair (slot, extended_mode, 1,
691 data, datalen, le, result, resultlen);
696 gpg_error_t
697 iso7816_get_challenge (int slot, int length, unsigned char *buffer)
699 int sw;
700 unsigned char *result;
701 size_t resultlen, n;
703 if (!buffer || length < 1)
704 return gpg_error (GPG_ERR_INV_VALUE);
708 result = NULL;
709 n = length > 254? 254 : length;
710 sw = apdu_send_le (slot, 0,
711 0x00, CMD_GET_CHALLENGE, 0, 0, -1, NULL, n,
712 &result, &resultlen);
713 if (sw != SW_SUCCESS)
715 /* Make sure that pending buffers are released. */
716 xfree (result);
717 return map_sw (sw);
719 if (resultlen > n)
720 resultlen = n;
721 memcpy (buffer, result, resultlen);
722 buffer += resultlen;
723 length -= resultlen;
724 xfree (result);
726 while (length > 0);
728 return 0;
731 /* Perform a READ BINARY command requesting a maximum of NMAX bytes
732 from OFFSET. With NMAX = 0 the entire file is read. The result is
733 stored in a newly allocated buffer at the address passed by RESULT.
734 Returns the length of this data at the address of RESULTLEN. */
735 gpg_error_t
736 iso7816_read_binary (int slot, size_t offset, size_t nmax,
737 unsigned char **result, size_t *resultlen)
739 int sw;
740 unsigned char *buffer;
741 size_t bufferlen;
742 int read_all = !nmax;
743 size_t n;
745 if (!result || !resultlen)
746 return gpg_error (GPG_ERR_INV_VALUE);
747 *result = NULL;
748 *resultlen = 0;
750 /* We can only encode 15 bits in p0,p1 to indicate an offset. Thus
751 we check for this limit. */
752 if (offset > 32767)
753 return gpg_error (GPG_ERR_INV_VALUE);
757 buffer = NULL;
758 bufferlen = 0;
759 n = read_all? 0 : nmax;
760 sw = apdu_send_le (slot, 0, 0x00, CMD_READ_BINARY,
761 ((offset>>8) & 0xff), (offset & 0xff) , -1, NULL,
762 n, &buffer, &bufferlen);
763 if ( SW_EXACT_LENGTH_P(sw) )
765 n = (sw & 0x00ff);
766 sw = apdu_send_le (slot, 0, 0x00, CMD_READ_BINARY,
767 ((offset>>8) & 0xff), (offset & 0xff) , -1, NULL,
768 n, &buffer, &bufferlen);
771 if (*result && sw == SW_BAD_P0_P1)
773 /* Bad Parameter means that the offset is outside of the
774 EF. When reading all data we take this as an indication
775 for EOF. */
776 break;
779 if (sw != SW_SUCCESS && sw != SW_EOF_REACHED)
781 /* Make sure that pending buffers are released. */
782 xfree (buffer);
783 xfree (*result);
784 *result = NULL;
785 *resultlen = 0;
786 return map_sw (sw);
788 if (*result) /* Need to extend the buffer. */
790 unsigned char *p = xtryrealloc (*result, *resultlen + bufferlen);
791 if (!p)
793 gpg_error_t err = gpg_error_from_syserror ();
794 xfree (buffer);
795 xfree (*result);
796 *result = NULL;
797 *resultlen = 0;
798 return err;
800 *result = p;
801 memcpy (*result + *resultlen, buffer, bufferlen);
802 *resultlen += bufferlen;
803 xfree (buffer);
804 buffer = NULL;
806 else /* Transfer the buffer into our result. */
808 *result = buffer;
809 *resultlen = bufferlen;
811 offset += bufferlen;
812 if (offset > 32767)
813 break; /* We simply truncate the result for too large
814 files. */
815 if (nmax > bufferlen)
816 nmax -= bufferlen;
817 else
818 nmax = 0;
820 while ((read_all && sw != SW_EOF_REACHED) || (!read_all && nmax));
822 return 0;
825 /* Perform a READ RECORD command. RECNO gives the record number to
826 read with 0 indicating the current record. RECCOUNT must be 1 (not
827 all cards support reading of more than one record). SHORT_EF
828 should be 0 to read the current EF or contain a short EF. The
829 result is stored in a newly allocated buffer at the address passed
830 by RESULT. Returns the length of this data at the address of
831 RESULTLEN. */
832 gpg_error_t
833 iso7816_read_record (int slot, int recno, int reccount, int short_ef,
834 unsigned char **result, size_t *resultlen)
836 int sw;
837 unsigned char *buffer;
838 size_t bufferlen;
840 if (!result || !resultlen)
841 return gpg_error (GPG_ERR_INV_VALUE);
842 *result = NULL;
843 *resultlen = 0;
845 /* We can only encode 15 bits in p0,p1 to indicate an offset. Thus
846 we check for this limit. */
847 if (recno < 0 || recno > 255 || reccount != 1
848 || short_ef < 0 || short_ef > 254 )
849 return gpg_error (GPG_ERR_INV_VALUE);
851 buffer = NULL;
852 bufferlen = 0;
853 sw = apdu_send_le (slot, 0, 0x00, CMD_READ_RECORD,
854 recno,
855 short_ef? short_ef : 0x04,
856 -1, NULL,
857 0, &buffer, &bufferlen);
859 if (sw != SW_SUCCESS && sw != SW_EOF_REACHED)
861 /* Make sure that pending buffers are released. */
862 xfree (buffer);
863 xfree (*result);
864 *result = NULL;
865 *resultlen = 0;
866 return map_sw (sw);
868 *result = buffer;
869 *resultlen = bufferlen;
871 return 0;