APDU 命令异步调用

Posted

技术标签:

【中文标题】APDU 命令异步调用【英文标题】:APDU Command asynchronous calls 【发布时间】:2017-06-13 15:04:19 【问题描述】:

我一直在使用有线智能卡读卡器 SDK,其中的调用是同步的。最近一直在尝试蓝牙接口,但 APDU 命令是异步的,因此我们无法解释为形成下一个 APDU 命令而发送的调用的响应。

任何帮助将不胜感激。

请求

byte[] var1 = (byte)0, (byte)-92, (byte)4, (byte)0, (byte)12, (byte)-96, (byte)0, (byte)0, (byte)2, (byte)67, (byte)0, (byte)19, (byte)0, (byte)0, (byte)0, (byte)1, (byte)1;

        String apduString = QPOSUtil.byteArray2Hex(var1);
        pos.sendApdu(apduString);

结果:

@Override public void onReturnApduResult(boolean arg0, String arg1, int arg2)

【问题讨论】:

Wrapping an asynchronous computation into a synchronous (blocking) computation的可能重复 【参考方案1】:

您可以将异步调用封装为同步调用。主要思想是在等待结果时阻塞当前线程。我喜欢使用锁,所以我使用了java.util.concurrent.locks.ReentrantLock。但是有很多方法可以实现这种行为,例如java.util.concurrent.Future<T> 或Busy Waiting。

// Lock that is used for waiting
private final ReentrantLock waitLock = new ReentrantLock();

private APDUResult result = null;

// synchronous wrapper 
// synchronized keyword is used to serialize requests
public synchronized APDUResult sendAPDUSynchronous(byte[] apdu) 
    // calles asynchronous function
    sendAPDUAsynchronous(apdu);
    // waits until .unlock() is called
    waitLock.lock();
    // returns the result
    return result;


// this function sould not be called outside - so its private
private void sendAPDUAsynchronous(byte[] apdu) 
    String apduString = QPOSUtil.byteArray2Hex(var1);
    pos.sendApdu(apduString);


@Override
public void onReturnApduResult(boolean arg0, String arg1, int arg2) 
    // stores the result
    result = new APDUResult(arg0, arg1, arg2);
    // notifys the waiting thread in synchronous call
    waitLock.unlock();

APDUResult 只是将三个参数包装到一个可以由同步函数传递的对象。不要忘记在错误回调上也调用waitLock.unlock()。否则会出现死锁。

如果您需要更多灵感,还有其他 posts 关于这个主题。

【讨论】:

以上是关于APDU 命令异步调用的主要内容,如果未能解决你的问题,请参考以下文章

tornado 异步调用系统命令和非阻塞线程池

如何将低级命令(非 APDU)发送到 Windows 10(移动)上的智能卡?

如何为不和谐机器人调用异步函数

Discord.js - 尝试等待异步进程并允许递归调用包装器

调用服务器的 PHP 脚本是不是异步运行?

有时,我的 AWS lambda 函数没有使用调用异步运行