Skip to content

Instantly share code, notes, and snippets.

View hpkaushik121's full-sized avatar

sourabh kaushik hpkaushik121

View GitHub Profile
// app/build.gradle
dependencies {
// ... other dependencies
implementation project(':module1')
implementation project(':module2')
}
// Define module priorities
/**
* p1 &= 0b00111111 = AAC = reject transaction (EMVApplication Authentication Cryptogram)
* p1 &= 0b10111111 = TC = proceed offline (Transaction Certificate)
* p1 &= 0b01111111 = ARQC = go online (Authorization Request Cryptogram ) +
* 0x00 = CDA signature not requested
* 0x10 = CDA signature requested
*/
ByteArrayOutputStream buf = new ByteArrayOutputStream();
byte[] authorizedAmount = Util.fromHexString("00 00 00 00 01 00"); // 1 Rs
byte[] secondaryAmount = Util.fromHexString("00 00 00 00 00 00"); // 0 Rs
77 4e -- Response Message Template Format 2
82 02 -- Application Interchange Profile
00 00 (BINARY)
9f 36 02 -- Application Transaction Counter (ATC)
00 01 (BINARY)
57 13 -- Track 2 Equivalent Data
40 23 60 09 00 12 50 08 d1 80 52 21 15 15 29 93
00 00 0f (BINARY)
9f 10 07 -- Issuer Application Data
06 0a 0a 03 a0 00 00 (BINARY)
/**
* The VERIFY command is used for OFFLINE authentication.
* The Transaction PIN Data (input) is compared with the Reference PIN Data
* stored in the application (ICC).
*
* NOTE: The EMV command "Offline PIN" (plaintext) is vulnerable to a Man-in-the-middle attack.
* Terminals should request online pin verification instead (or encipher PIN) !!
*
* Case 3 C-APDU
*
public class Main {
public static byte[] externalAuthenticate(byte[] cryptogram, byte[] proprietaryBytes) {
if (cryptogram == null) {
throw new IllegalArgumentException("Argument 'cryptogram' cannot be null");
}
if (cryptogram.length != 8) {
throw new IllegalArgumentException("Argument 'cryptogram' must have a length of 8. length=" + cryptogram.length);
}
if (proprietaryBytes != null && (proprietaryBytes.length < 1 || proprietaryBytes.length > 8)) {
6f 37
84 07 //AID
a0 00 00 00 03 10 10
a5 2c
50 04 //Application Label (= VISA)
56 49 53 41
87 01 //Application priority indicator
02
9f 38 06 //PDOL
9f 1a
/*
*
* Case 4s C-APDU
*/
public static byte[] getProcessingOpts(DOL pdol, EMVApplication app) {
String command;
if (pdol != null && pdol.getTagAndLengthList().size() > 0) {
byte[] pdolResponseData = EMVTerminal.constructDOLResponse(pdol, app);
command = "80 A8 00 00";
command += " " + Util.int2Hex(pdolResponseData.length + 2) + " 83 " + Util.int2Hex(pdolResponseData.length); //this PDOL get be fetch from response of SELECT command
public static byte[] readRecord(int recordNum, int sfi) {
//Valid Record numbers: 1 to 255
//Valid SFI: 1 to 30
//SFI=0 : Currently selected EF
if (recordNum < 1 || recordNum > 255) {
throw new IllegalArgumentException("Argument 'recordNum' must be in the rage 1 to 255. recordNum=" + recordNum);
}
if (sfi < 0 || sfi > 30) {
throw new IllegalArgumentException("Argument 'sfi' must be in the rage 1 to 30. Use 0 for currently selected EF. sfi=" + sfi);
}
6f 20 //FCI(File Control Information) Template
84 0e //DF Name
31 50 41 59 2e 53 59 53 2e 44 44 46 30 31 (=1PAY.SYS.DDF01)
a5 0e //FCI Proprietary Template
88 01 //SFI(Short Field Identifier ) of the Directory Elementary File
02
5f 2d 04 //Language Preference
6e 6f 65 6e
9f 11 01 //Issuer Code Table Index
01 (=ISO 8859-1)
70 23 //EMV Proprietary Template
61 21 // Application Template
4f 07 //AID
a0 00 00 00 03 10 10
50 04 //Application Label
56 49 53 41 (=VISA)
9f 12 0c //Application Preferred Name
56 49 53 41 20 43 6c 61 73 73 69 63 (=VISA Classic)
87 01 //Application priority indicator
02