@@ -404,6 +404,8 @@ struct Iso7816::Impl : IsoTech
404
404
{
405
405
case FullCharacter:
406
406
{
407
+ log->trace (" \t byte [{}]: {02x}" , {frameStatus.frameSize , characterStatus.data });
408
+
407
409
// check TS byte to detect convention
408
410
switch (characterStatus.data )
409
411
{
@@ -433,7 +435,7 @@ struct Iso7816::Impl : IsoTech
433
435
frameStatus.frameFlags = 0 ;
434
436
frameStatus.frameSize = 0 ;
435
437
frameStatus.frameData [frameStatus.frameSize ++] = characterStatus.data ;
436
- frameStatus.symbolRate = 1.0 / protocolStatus.elementaryTimeUnit ;
438
+ frameStatus.symbolRate = 1 .0f / protocolStatus.elementaryTimeUnit ;
437
439
438
440
// clear status for next character
439
441
characterStatus = {};
@@ -456,6 +458,8 @@ struct Iso7816::Impl : IsoTech
456
458
{
457
459
case FullCharacter:
458
460
{
461
+ log->trace (" \t byte [{}]: {02x} {}->{}" , {frameStatus.frameSize , characterStatus.data , characterStatus.start , characterStatus.end });
462
+
459
463
// update frame status and add character to frame data
460
464
frameStatus.frameEnd = characterStatus.end ;
461
465
frameStatus.frameFlags |= characterStatus.flags ;
@@ -661,7 +665,7 @@ struct Iso7816::Impl : IsoTech
661
665
if (!frameStatus.frameStart )
662
666
frameStatus.frameStart = characterStatus.start ;
663
667
664
- log->trace (" \t byte [{}]: {02x}" , {frameStatus.frameSize , characterStatus.data });
668
+ log->trace (" \t byte [{}]: {02x} {}->{} " , {frameStatus.frameSize , characterStatus.data , characterStatus. start , characterStatus. end });
665
669
666
670
// update frame and add character to frame data
667
671
frameStatus.frameEnd = characterStatus.end ;
@@ -709,7 +713,7 @@ struct Iso7816::Impl : IsoTech
709
713
if (!frameStatus.frameStart )
710
714
frameStatus.frameStart = characterStatus.start ;
711
715
712
- log->trace (" \t byte [{}]: {02x}" , {frameStatus.frameSize , characterStatus.data });
716
+ log->trace (" \t byte [{}]: {02x} {}->{} " , {frameStatus.frameSize , characterStatus.data , characterStatus. start , characterStatus. end });
713
717
714
718
// update frame and add character to frame data
715
719
frameStatus.frameEnd = characterStatus.end ;
@@ -965,7 +969,7 @@ struct Iso7816::Impl : IsoTech
965
969
966
970
bool updateParameters = false ;
967
971
968
- int i = 1 , n = 2 , k = 1 , p = 0 ;
972
+ int i = 1 , n = 2 , k = 1 , c = 0 ;
969
973
970
974
do
971
975
{
@@ -1065,8 +1069,8 @@ struct Iso7816::Impl : IsoTech
1065
1069
// check presence of TDk
1066
1070
if (frame[i] & ATR_TD_MASK)
1067
1071
{
1068
- // next protocol parameters
1069
- p = frame[i] & 0x0f ;
1072
+ // check presence of TCK (then T!=0 on some of TDk bytes)
1073
+ c | = frame[i] & 0x0f ;
1070
1074
1071
1075
// next structural byte
1072
1076
i = n++;
@@ -1081,6 +1085,10 @@ struct Iso7816::Impl : IsoTech
1081
1085
1082
1086
log->info (" \t historical bytes {}" , {hb});
1083
1087
1088
+ // check presence of TCK
1089
+ if (c)
1090
+ frame.setFrameFlags (!checkLrc (frame) ? CrcError : 0 );
1091
+
1084
1092
// update protocol parameters
1085
1093
if (updateParameters)
1086
1094
updateProtocol (protocolStatus.elementaryTime , protocolStatus.frequencyFactorIndex , protocolStatus.baudRateFactorIndex );
@@ -1183,7 +1191,7 @@ struct Iso7816::Impl : IsoTech
1183
1191
if (frame.frameType () != IsoRequestFrame && frame.frameType () != IsoResponseFrame)
1184
1192
return false ;
1185
1193
1186
- // check if frame is an I-Block, bit 8 must be and length must be at least prologue + epilogue bytes
1194
+ // check if frame is an I-Block, bit 8 must be clear
1187
1195
if (frame[1 ] & 0x80 )
1188
1196
return false ;
1189
1197
@@ -1206,7 +1214,7 @@ struct Iso7816::Impl : IsoTech
1206
1214
if (frame.frameType () != IsoRequestFrame && frame.frameType () != IsoResponseFrame)
1207
1215
return false ;
1208
1216
1209
- // check if frame is an I -Block, bit 8 must be and length must be at least 4 bytes
1217
+ // check if frame is an R -Block, bit 8,7 must be 1,0
1210
1218
if ((frame[1 ] & 0xC0 ) != 0x80 )
1211
1219
return false ;
1212
1220
@@ -1225,7 +1233,7 @@ struct Iso7816::Impl : IsoTech
1225
1233
if (frame.frameType () != IsoRequestFrame && frame.frameType () != IsoResponseFrame)
1226
1234
return false ;
1227
1235
1228
- // check if frame is an I -Block, bit 8 must be and length must be at least 4 bytes
1236
+ // check if frame is an S -Block, bit 8,7 must be 1,1
1229
1237
if ((frame[1 ] & 0xC0 ) != 0xC0 )
1230
1238
return false ;
1231
1239
@@ -1350,30 +1358,33 @@ struct Iso7816::Impl : IsoTech
1350
1358
if (size > ATR_MAX_LEN)
1351
1359
return ResultFailed;
1352
1360
1353
- int i = 1 , n = 1 ;
1361
+ int i = 1 , n = 1 , c = 0 ;
1354
1362
int hb = atr[n++] & 0x0f ;
1355
- int ck = 0 ;
1356
1363
1357
1364
do
1358
1365
{
1359
1366
if (atr[i] & ATR_TA_MASK) n++; // skip TAi
1360
1367
if (atr[i] & ATR_TB_MASK) n++; // skip TBi
1361
1368
if (atr[i] & ATR_TC_MASK) n++; // skip TCi
1362
- if (atr[i] & ATR_TD_MASK) i = n++; // check next TDi
1363
1369
1370
+ // check presence of TDk, and protocol indicator != 0 to trigger TCK check
1371
+ if (atr[i] & ATR_TD_MASK)
1372
+ {
1373
+ // get protocol indicator
1374
+ c |= atr[i] & 0x0f ;
1375
+
1376
+ // next structural byte
1377
+ i = n++;
1378
+ }
1364
1379
}
1365
1380
while ((i == n - 1 ) && n < size);
1366
1381
1367
- // check frame size with historical bytes
1368
- if (size < n + hb + 1 )
1382
+ // check frame size with historical bytes and presence of TCK
1383
+ if (size < n + hb + (c ? 1 : 0 ) )
1369
1384
return ResultInvalid;
1370
1385
1371
- // finally check LCR parity
1372
- for (int j = 1 ; j < size; j++)
1373
- ck ^= atr[j];
1374
-
1375
- // check parity
1376
- return !ck ? ResultSuccess : ResultFailed;
1386
+ // ATR completed
1387
+ return ResultSuccess;
1377
1388
}
1378
1389
1379
1390
/*
0 commit comments