Improved chaining for large APDU commands,
by Mats Andersson and Douglas E. Engert. git-svn-id: https://www.opensc-project.org/svnp/opensc/trunk@3997 c6295689-39f2-0310-b995-f0e70906c6a9
This commit is contained in:
parent
85613b459d
commit
119c7751c7
@ -530,10 +530,13 @@ int sc_transmit_apdu(sc_card_t *card, sc_apdu_t *apdu)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if ((apdu->flags & SC_APDU_FLAGS_CHAINING) != 0) {
|
if ((apdu->flags & SC_APDU_FLAGS_CHAINING) != 0) {
|
||||||
/* divide et impera: transmit APDU in chunks with Lc < 255
|
/* divide et impera: transmit APDU in chunks with Lc <= max_send_size
|
||||||
* bytes using command chaining */
|
* bytes using command chaining */
|
||||||
size_t len = apdu->datalen;
|
size_t len = apdu->datalen;
|
||||||
const u8 *buf = apdu->data;
|
const u8 *buf = apdu->data;
|
||||||
|
size_t max_send_size = ((card->max_send_size > 0) ?
|
||||||
|
card->max_send_size :
|
||||||
|
card->reader->driver->max_send_size);
|
||||||
|
|
||||||
while (len != 0) {
|
while (len != 0) {
|
||||||
size_t plen;
|
size_t plen;
|
||||||
@ -543,14 +546,14 @@ int sc_transmit_apdu(sc_card_t *card, sc_apdu_t *apdu)
|
|||||||
tapdu = *apdu;
|
tapdu = *apdu;
|
||||||
/* clear chaining flag */
|
/* clear chaining flag */
|
||||||
tapdu.flags &= ~SC_APDU_FLAGS_CHAINING;
|
tapdu.flags &= ~SC_APDU_FLAGS_CHAINING;
|
||||||
if (len > 255) {
|
if (len > max_send_size) {
|
||||||
/* adjust APDU case: in case of CASE 4 APDU
|
/* adjust APDU case: in case of CASE 4 APDU
|
||||||
* the intermediate APDU are of CASE 3 */
|
* the intermediate APDU are of CASE 3 */
|
||||||
if ((tapdu.cse & SC_APDU_SHORT_MASK) == SC_APDU_CASE_4_SHORT)
|
if ((tapdu.cse & SC_APDU_SHORT_MASK) == SC_APDU_CASE_4_SHORT)
|
||||||
tapdu.cse--;
|
tapdu.cse--;
|
||||||
/* XXX: the chunk size must be adjusted when
|
/* XXX: the chunk size must be adjusted when
|
||||||
* secure messaging is used */
|
* secure messaging is used */
|
||||||
plen = 255;
|
plen = max_send_size;
|
||||||
tapdu.cla |= 0x10;
|
tapdu.cla |= 0x10;
|
||||||
tapdu.le = 0;
|
tapdu.le = 0;
|
||||||
/* the intermediate APDU don't expect data */
|
/* the intermediate APDU don't expect data */
|
||||||
|
Loading…
Reference in New Issue
Block a user