private boolean selectPpse() throws TagLostException, IOException { Log.d(TAG, "select PPSE"); CommandApdu selectPpseApdu = new SelectApdu(mPpseAidBytes); selectPpseApdu.setCommandName("select ppse"); ResponseApdu rspApdu = sendAndRcv(selectPpseApdu, true); if (rspApdu.isStatus(SW_NO_ERROR)) { mUiCallbacks.onOkay(mContext.getString(R.string.select_ppse_ok, rspApdu.getSW1SW2())); } else { mUiCallbacks.onError( mContext.getString(R.string.select_ppse_err, rspApdu.getSW1SW2(), ApduParser.parse(false, rspApdu.toBytes()))); return false; } try { mPpseDdf = parseFCIDDF(rspApdu.getData()); } catch (TLVException e) { mPpseDdf = null; mUiCallbacks.onError(e.getMessage()); return true; } return true; }
private boolean selectApp(String aid, EMVApp app) throws TagLostException, IOException { Log.d(TAG, "select app: " + aid); byte[] aidBytes = Util.hexToBytes(aid); ResponseApdu rspApdu = sendAndRcv(new SelectApdu(aidBytes), true); if (rspApdu.isStatus(SW_NO_ERROR)) { mUiCallbacks.onOkay(mContext.getString(R.string.select_app_ok, rspApdu.getSW1SW2())); if (app != null) { try { parseFCIADF(rspApdu.getData(), app); } catch (Exception e) { mUiCallbacks.onError(e.getMessage()); } } } else { if (rspApdu.getSW1SW2() == SW_SELECTED_FILE_INVALIDATED) { Log.d(TAG, "Application blocked!"); } mUiCallbacks.onError( mContext.getString(R.string.select_app_err, rspApdu.getSW1SW2(), ApduParser.parse(false, rspApdu.toBytes()))); return false; } return true; }
protected ResponseApdu sendAndRcv(CommandApdu cmdApdu, boolean ascii) throws TagLostException, IOException { byte[] cmdBytes = cmdApdu.toBytes(); String cmdStr = CommandApdu.toString(cmdBytes, cmdApdu.getLc()); mUiCallbacks.onMessageSend(cmdStr, cmdApdu.getCommandName()); byte[] rsp = mIsoDep.transceive(cmdBytes); ResponseApdu rspApdu = new ResponseApdu(rsp); byte[] data = rspApdu.getData(); String parsed = null; String errMsg = "no error"; try { if (data.length > 0) { parsed = TLVUtil.prettyPrintAPDUResponse(data); } } catch (TLVException e) { parsed = null; errMsg = e.getMessage(); } mUiCallbacks.onMessageRcv(bytesToHexAndAscii(rsp, ascii), cmdApdu.getCommandName(), parsed); if (data.length > 0 && parsed == null) { mUiCallbacks.onError(errMsg); } /* Log.d(TAG, "response APDU: " + Util.bytesToHex(rsp)); if (data.length > 0) { Log.d(TAG, TLVUtil.prettyPrintAPDUResponse(data)); } */ return rspApdu; }
private void onTagDiscovered(Tag tag, IsoDep isoDep, boolean trySoftReset) { Log.d(TAG, "onTagDiscovered: " + tag); final long startTime = System.currentTimeMillis(); long duration; try { boolean done = false; final AtomicReference<DERObject> outputPaymentRequestSend = new AtomicReference<>(); final AtomicReference<DERObject> outputPaymentResponseReceive = new AtomicReference<>(); final AtomicReference<DERObject> paymentAck = new AtomicReference<>(); Thread authorization = null; Log.d(TAG, "first transmit: payment request, startTime(ms)=" + startTime); PaymentRequestSendStep paymentRequestSendStep = new PaymentRequestSendStep( getPaymentRequestUri(), getWalletServiceBinder().getMultisigClientKey()); DERObject derPaymentRequest = paymentRequestSendStep.process(DERObject.NULLOBJECT); outputPaymentRequestSend.set(derPaymentRequest); Log.d(TAG, "transceive outputPaymentRequestSend"); final DERObject paymentRequestOutput = transceiveDER(isoDep, outputPaymentRequestSend.get(), true); while (!done) { if (paymentRequestOutput != null && authorization == null && outputPaymentResponseReceive.get() == null) { duration = System.currentTimeMillis() - startTime; Log.d(TAG, "got payment response ("+duration+" ms since startTime)"); Runnable runnable = new PaymentResponseReceiveRunnable(paymentRequestOutput, outputPaymentResponseReceive); authorization = new Thread(runnable, "NFCServer.PaymentResponseReceive"); authorization.start(); continue; } if (outputPaymentResponseReceive.get() != null && paymentAck.get() == null) { duration = System.currentTimeMillis() - startTime; Log.d(TAG, "send server response ("+duration+" ms since startTime)"); DERObject toSend = outputPaymentResponseReceive.get(); DERObject ackResponse = transceiveDER(isoDep, toSend); paymentAck.set(ackResponse); continue; } if (paymentAck.get() != null) { duration = System.currentTimeMillis() - startTime; Log.d(TAG, "Send final ACK ("+duration+" ms since startTime)"); isoDep.transceive(DERObject.NULLOBJECT.serializeToDER()); done = true; continue; } // default: keep alive loop byte[] response = transceiveKeepAlive(isoDep); Log.d(TAG, "transceive keep alive, response length=" + response.length); } trySoftReset = false; isoDep.close(); getPaymentRequestDelegate().onPaymentSuccess(); duration = System.currentTimeMillis() - startTime; Log.d(TAG, "Payment finished - total duration: " + duration + " ms"); } catch (TagLostException tle) { Log.d(TAG, "Tag lost"); if(trySoftReset) { softResetNFC(tag); } } catch (Throwable e) { Log.e(TAG, "Exception in onTagDiscovered", e); getPaymentRequestDelegate().onPaymentError(e.getMessage()); } }
@TargetApi(10) private static byte[] transceive(IsoDep paramIsoDep, byte[] paramArrayOfByte) throws IOException, TagReadTimeoutException { long l = SystemClock.elapsedRealtime(); try { byte[] arrayOfByte = paramIsoDep.transceive(paramArrayOfByte); return arrayOfByte; } catch (TagLostException localTagLostException) { if (SystemClock.elapsedRealtime() - l >= NFC_TIMEOUT_MS) { throw new TagReadTimeoutException(localTagLostException); } throw localTagLostException; } }
public void write(NdefMessage message) throws IOException, TagLostException, FormatException, IllegalStateException;
public NdefMessage read() throws IOException, TagLostException, FormatException, IllegalStateException;
@Override public void write(NdefMessage message) throws IOException, TagLostException, FormatException, IllegalStateException { mNdef.writeNdefMessage(message); }
@Override public NdefMessage read() throws IOException, TagLostException, FormatException, IllegalStateException { return mNdef.getNdefMessage(); }
@Override public void write(NdefMessage message) throws IOException, TagLostException, FormatException, IllegalStateException { mNdefFormattable.format(message); }
/** * Connects to NFC tag. */ public void connect() throws IOException, TagLostException { if (!mTech.isConnected()) { mTech.connect(); mWasConnected = true; } }
/** * Writes NdefMessage to NFC tag. */ public void write(NdefMessage message) throws IOException, TagLostException, FormatException, IllegalStateException { mTechHandler.write(message); }
public NdefMessage read() throws IOException, TagLostException, FormatException, IllegalStateException { return mTechHandler.read(); }
@Override protected Boolean doInBackground(Void... params) { AppController ctl = AppController.getInstance(); ctl.clearLog(); try { ctl.log(getResources().getString(R.string.app_name) + " version " + getAppVersion(MainActivity.this)); NfcBankomatCardReader reader = new NfcBankomatCardReader( nfcTag, MainActivity.this); reader.connectIsoDep(); // read setting value SharedPreferences prefs = PreferenceManager .getDefaultSharedPreferences(MainActivity.this); _cardReadingResults = reader.readAllCardData(prefs.getBoolean( "perform_full_file_scan", false)); ctl.setCardInfo(_cardReadingResults); reader.disconnectIsoDep(); } catch (NoSmartCardException nsce) { Log.w(TAG, "Catched NoSmartCardException during reading the card", nsce); error = ERROR_NO_SMARTCARD; return false; } catch (TagLostException tle) { Log.w(TAG, "Catched TagLostException during reading the card", tle); error = ERROR_TAG_LOST; return false; } catch (IOException e) { Log.e(TAG, "Catched IOException during reading the card", e); error = ERROR_IO_EX; ctl.log("-----------------------------------------------"); ctl.log("ERROR ERROR ERROR:"); ctl.log("Catched IOException during reading the card:"); ctl.log(getStacktrace(e)); ctl.log("-----------------------------------------------"); return false; } return true; }