Summary
Tested with Open Smart Card Shell tool , it is part of Open Smart Card Development Platform. I used my expired credit card, executed the script dump.js, and read out the basic credit card information.
Installing the Smart Card Shell
Installation is simple, just follow the guide.
You can also use [Eclipse plug-in] to use the Smart Card Shell.
Use the Smart Card Shell
It is easy to use, just click “SCSH3GUI.CMD” to start the Smart Card Shell Windows GUI.
Below is the command example:
Running setup script config.js ...
Smart Card Shell Scripting Engine (scdp4j) 3.13.220
----------------------------------------------------------------------------
(c) 2005-2016 CardContact Systems GmbH, Minden, Germany (www.cardcontact.de)
Enter 'help' for a command overview or 'quit' to close the shell
>r
0000 3B 69 00 00 80 65 A2 01 01 01 3D 72 D6 ;i...e....=r.
TS : 3B Direct logic
TO : 69 K = 9 byte [historical characters]
TB1 : 00 pa = 4 % [programming voltage accurancy]
I = 25 mA [maximum current]
P = 0 V [programming voltage]
TC1 : 00 N = 0 etu [extra guardtime]
Pre-issuing data : A20101013D ¢...=
Error: Compact TLV length field exceeds historical bytes - truncated
Card capabilities :
DF selection by full DF name
DF selection by partial DF name
DF selection by file identifier
Short EF identifier supported
Record number supported
>help
q | quit Quit shell
r | reset Reset card in reader
a | apdu(string) Send APDU to card
print(string, ..) Print string(s)
load(file) Load and execute file
assert(expression, ..) Assert that expressions are all true
defineClass(file) Load Java class defining native objects
restart Restart shell (clears all variables)
or any other valid ECMAScript expression.
See doc/index.html for the complete documentation.
If this is the first time you use the Smart Card Shell and you want
to try it out, then insert a card into your reader and enter
load("tools/explore.js")
>apdu('00A4000400')
Card error SW1/SW2=6b00 - Checking error: Wrong parameter P1-P2
>apdu('00A4040000')
6F 65 84 08 A0 00 00 00 03 00 00 00 A5 59 73 4A 06 07 2A 86 48 86 FC 6B 01 60 0C 06 0A 2A 86 48 86 FC 6B 02 02 01 01 63 09 06 07 2A 86 48 86 FC 6B 03 64 0B 06 09 2A 86 48 86 FC 6B 04 02 55 65 0B 06 09 2B 85 10 86 48 64 02 01 03 66 0C 06 0A 2B 06 01 04 01 2A 02 6E 01 02 9F 6E 06 19 81 22 02 01 00 9F 65 01 FF
>
To run the js script, you just need use load command, example:
load('emv/dump.js')
Test on dump.js
Used my expired Citibank credit card.
Used Omnikey 5321v2 reader.
dump.js shell test result
>load('emv/dump.js')
AIDA0 00 00 00 03 10 10
0000 83 02 02 76 ...v
< ----Read application data as indicated in the Application File Locator.------
---------------------Collect input to data authentication.--------------------->
Record No. 2
0000 70 4D 57 13 41 47 46 30 66 66 66 66 D1 70 82 01 pMW.AGF0.c(H.p..
0010 00 00 03 66 10 00 0F 5F 20 1A 58 49 4F 4E 47 20 ...&..._ .XIONG
0020 48 55 49 4C 49 4E 20 20 20 20 20 20 20 20 20 20 HUILIN
0030 20 20 20 20 9F 1F 18 30 30 30 30 30 30 30 30 30 ...000000000
Record No. 1
0000 70 81 B3 90 81 B0 67 51 D5 FE 44 74 C7 A7 F9 1D p.....gQ..Dt....
//below raw date was deleted...
...
//above raw date was deleted...
------------------------------------------------------------------------------
----------------------------Display Data Elements-----------------------------
Application Identifier (AID) - card: A0000000031010
Application Label: 5649534120435245444954 - VISA CREDIT
Track 2 Equivalent Data (Magnetic Strip):
Primary Account Number: 4147463066666666
Expiration Date (YYMM): 1705
Service Code: 201
Discretionary Data: 0000066660000
//below data element was deleted...
...
//above data element was deleted...
------------------------------------------------------------------------------
EMV TLV Decoder
You can trace the log, and use EMV TLV Decoder to analyze the data, example as below,
00B20314F2
7081EF8F01089224CCE4335A1A3CD7E4271A50B8D804D95ABA4E349811244D73336D196A6D969F25025B27D99F3201039F4681B025EBB698F660FB9E177F4A611E2FD4AB4C14A86A159E8838D10B6E47C99956D78C2E04C870F525227ABAA8D46BFE09CF46A372CD6FEBF8B59CA22FC646B6B38C1A061A5AF1E4D7556303EA5F7924C519D6D5EA5E10A25B6F9A4F4421081F4E9C7865F7ADEC183D39489C0B4A34E947C2D535426A7545EF4A2B9BF3A19DC1A07252F70A63E7A94A85C46FD55AFDB2348C402FA53905123A97A161F07D8E712576DCC15E92A10E93E504804E09629048AE9F4701039F49039F37049F4A01829000
70 EMV Proprietary Template
8F Certification Authority Public Key Index
08
92 Issuer Public Key Remainder
CCE4335A1A3CD7E4271A50B8D804D95ABA4E349811244D73336D196A6D969F25025B27D9
9F32 Issuer Public Key Exponent
03
9F46 Integrated Circuit Card (ICC) Public Key Certificate
25EBB698F660FB9E177F4A611E2FD4AB4C14A86A159E8838D10B6E47C99956D78C2E04C870F525227ABAA8D46BFE09CF46A372CD6FEBF8B59CA22FC646B6B38C1A061A5AF1E4D7556303EA5F7924C519D6D5EA5E10A25B6F9A4F4421081F4E9C7865F7ADEC183D39489C0B4A34E947C2D535426A7545EF4A2B9BF3A19DC1A07252F70A63E7A94A85C46FD55AFDB2348C402FA53905123A97A161F07D8E712576DCC15E92A10E93E504804E09629048AE
9F47 Integrated Circuit Card (ICC) Public Key Exponent
03
9F49 Dynamic Data Authentication Data Object List (DDOL)
9F3704
9F4A Static Data Authentication Tag List
82
About the source code
It may not be easy to debug the source code, I use the print function to print out the intermediate data, as below read out application data example shows.
It read out Application Interchange Profile (AIP) and the Application File Locator (AFL). For detail, can refer to EMV_v4.3_Book_3_Application_Specification.
The APDU command example is as below,
80A800000483020276
6114
80C0000014
80127C00080202001001010010030400180102019000
The GET PROCESSING OPTIONS command initiates the transaction within the
ICC.
The ICC returns the Application Interchange Profile (AIP) and the Application
File Locator (AFL).
The source code is as below,
/**
* Read application data as indicated in the Application File Locator.
* Collect input to data authentication.
*
*/
EMV.prototype.readApplData = function() {
print("<-----Read application data as indicated in the Application File Locator.------");
print("---------------------Collect input to data authentication.---------------------");
// Application File Locator must exist
assert(typeof(this.cardDE[EMV.AFL]) != "undefined");
var afl = this.cardDE[EMV.AFL];
//print('4444444444 ' + afl); //08 02 02 00 10 01 01 00 10 03 04 00 18 01 02 01
// Must be a multiple of 4
assert((afl.length & 0x03) == 0);
// Collect input to data authentication
var da = new ByteBuffer();
while(afl.length > 0) {
var sfi = afl.byteAt(0) >> 3; // Short file identifier
var srec = afl.byteAt(1); // Start record
var erec = afl.byteAt(2); // End record
var dar = afl.byteAt(3); // Number of records included in data authentication
//print("4444444444 " + sfi + " " + srec + " " + erec+ " " +dar);
for (; srec <= erec; srec++) {
// Read all indicated records
var data = this.readRecord(sfi, srec);
print("Record No. " + srec);
print(data);
// Decode template
var tl = new TLVList(data, TLV.EMV);
//print("55555555 " + TLV.EMV + " 666 " + data);
assert(tl.length == 1);
var t = tl.index(0);
assert(t.getTag() == EMV.TEMPLATE);
// Add data authentication input
if (dar > 0) {
if (sfi <= 10) { // Only value
da.append(t.getValue());
//print("5555555 " + t.getValue());
} else { // Full template
da.append(data);
//print("6666666 " + data);
}
dar--;
}
// Add card based data elements to internal list
var tl = new TLVList(t.getValue(), TLV.EMV);
this.addCardDEFromList(tl);
}
// Continue with next entry in AFL
afl = afl.bytes(4);
}
this.daInput = da.toByteString();
print(this.daInput);
print("------------------------------------------------------------------------------>\n");
}
Reference
EMV TLV Decoder https://www.emvlab.org/tlvutils/
Open Smart Card Shell
dump.js source code
https://github.com/CardContact/OpenSC
CardContact Github
Open Smart Card Development Platform
Installing the Smart Card Shell
The Smart Card Scripting Environment for Eclipse (SSE4E)
EMV_v4.3_Book_3_Application_Specification
Webmentions
[…] to dump.js and EMV SDA Test, continue to test on DDA. The DDA test result is […]