From b95a023faa4b6248c9526d1a76ed4e26b1dfc997 Mon Sep 17 00:00:00 2001 From: tkellner Date: Tue, 3 Sep 2013 15:38:58 +0000 Subject: Gemalto .NET V2 Card integration git-svn-id: https://joinup.ec.europa.eu/svn/mocca/trunk@1201 8a26b1a7-26f0-462f-b9ef-d0e30c41f5a4 --- .../java/at/gv/egiz/smcc/util/MSCMTransfer.java | 146 +++++++++++++++++++++ 1 file changed, 146 insertions(+) create mode 100644 smcc/src/main/java/at/gv/egiz/smcc/util/MSCMTransfer.java (limited to 'smcc/src/main/java/at/gv/egiz/smcc/util/MSCMTransfer.java') diff --git a/smcc/src/main/java/at/gv/egiz/smcc/util/MSCMTransfer.java b/smcc/src/main/java/at/gv/egiz/smcc/util/MSCMTransfer.java new file mode 100644 index 00000000..ea4121a5 --- /dev/null +++ b/smcc/src/main/java/at/gv/egiz/smcc/util/MSCMTransfer.java @@ -0,0 +1,146 @@ +package at.gv.egiz.smcc.util; + +import java.io.ByteArrayOutputStream; +import java.io.IOException; + +import javax.smartcardio.CardChannel; +import javax.smartcardio.CardException; +import javax.smartcardio.CommandAPDU; +import javax.smartcardio.ResponseAPDU; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import at.gv.egiz.smcc.GemaltoNetV2_0Card; + +import java.nio.ByteBuffer; + +public class MSCMTransfer implements MSCMConstants { + + private final Logger log = LoggerFactory + .getLogger(MSCMTransfer.class); + + private CardChannel channel; + + public MSCMTransfer(CardChannel channel) { + this.channel = channel; + } + + public byte[] transfer(byte[] payload, short expectedType) throws IOException, CardException, MSCMException { + byte[] header = new byte[] { (byte) 0x80, (byte) 0xC2, (byte) 0x00, + (byte) 0x00 }; + byte[] cmd = null; + byte[] len = new byte[1]; + byte[] con = new byte[] { (byte) 0xD8, (byte) 0xFF, (byte) 0xFF }; + ByteArrayOutputStream cmdbuffer = new ByteArrayOutputStream(); + ResponseAPDU response = null; + if(payload.length <= 0xFF) { + cmdbuffer.write(header); + len[0] = (byte) payload.length; + cmdbuffer.write(len); + cmdbuffer.write(payload); + // Transfer cmdbuffer + cmd = cmdbuffer.toByteArray(); + String str = MSCMService.bytArrayToHex(cmd); + log.info("Sending: >>> " + str); + //ByteBuffer bb = ByteBuffer.wrap(cmd); + //ByteBuffer resp = ByteBuffer.allocate(18000); + //response = channel.transmit(bb, resp); + //int resps = channel.transmit(bb, resp); + //ByteArrayOutputStream out = new ByteArrayOutputStream(); + //out.write(resp.array(), 0, resps); + //out.close(); + //response = new ResponseAPDU(out.toByteArray()); + response = channel.transmit(new CommandAPDU(cmd)); + } else { // (> 0xFF) + // divide payload + int length = payload.length; + int offset = 0; + int curlen = 0; + boolean first = true; + while(length > 0) { + curlen = (length > 0xF4) ? 0xF4 : length; + ByteArrayOutputStream dpay = new ByteArrayOutputStream(); + dpay.write(con); + if(first) { + dpay.write(MSCMService.intToBytes(payload.length-18)); + dpay.write(MSCMService.intToBytes(curlen-18)); + } else { + dpay.write(MSCMService.intToBytes(offset-18)); + dpay.write(MSCMService.intToBytes(curlen)); + } + first = false; + + dpay.write(payload, offset, curlen); + dpay.close(); + byte[] ppay = dpay.toByteArray(); + + cmdbuffer.write(header); + len[0] = (byte)ppay.length; + cmdbuffer.write(len); + cmdbuffer.write(ppay); + + length -= curlen; + offset += curlen; + + cmd = cmdbuffer.toByteArray(); + String str = MSCMService.bytArrayToHex(cmd); + log.info("Sending: >>> " + str); + response = channel.transmit(new CommandAPDU(cmd)); + + + //ByteBuffer bb = ByteBuffer.wrap(cmd); + //ByteBuffer resp = ByteBuffer.allocate(18000); + //response = channel.transmit(bb, resp); + //int resps = channel.transmit(bb, resp); + //ByteArrayOutputStream out = new ByteArrayOutputStream(); + //out.write(resp.array(), 0, resps); + //out.close(); + //response = new ResponseAPDU(out.toByteArray()); + log.info("Resp: <<< " + MSCMService.bytArrayToHex(MSCMService.intToBytes(response.getSW()))); + cmdbuffer.reset(); + } + } + + log.info(" SW : <<< " + MSCMService.bytArrayToHex( + MSCMService.intToBytes(response.getSW()))); + byte[] data = response.getData(); + log.info("DATA: <<< " + MSCMService.bytArrayToHex(data)); + + if(data.length == 0) { + return null; + } + + MSCMDecoder.checkExceptionInResponse(data, 0); + + if(expectedType == HIVECODE_TYPE_SYSTEM_VOID) { + return data; + } + + String namespaceString = MSCMDecoder.namespaceHiveToString(data, 0); + String typeString = MSCMDecoder.typeHiveToString(data, 4); + short resultType = MSCMService.bytesToShort(data, 4); + if(expectedType == resultType) { + ByteArrayOutputStream str = new ByteArrayOutputStream(); + str.write(data, 6, data.length-6); + return str.toByteArray(); + } else { + throw new CardException("Wrong result type"); + }/* + if(typeString.equals(HIVECODE_TYPE_SYSTEM_STRING_STRING)) { + System.out.println(namespaceString + "." + typeString + ": " + + MSCMDecoder.decodeString(data, 6)); + } else if(typeString.equals(HIVECODE_TYPE_SYSTEM_STRING_ARRAY_STRING)) { + String[] results = MSCMDecoder.decodeStringArray(data, 6); + System.out.println(typeString + ": "); + for(String str : results) { + System.out.println(str); + } + } else { + System.out.println(namespaceString + "." + typeString + ": " + + MSCMService.bytArrayToHex(MSCMDecoder.decodeByteArray(data, 6))); + } + return data;*/ + } + +} -- cgit v1.2.3