Dealloc Desfire singleton instance

Forum / MIFARE SDK / Dealloc Desfire singleton instance

  • 5. December 2017 at 16:43
    Hi,
    I've got two NFC tag Desfire EV2 (named here A and B).

    When I connect to the tag A and then to the tag B (or viceversa) it seems that the Mifare SDK can't authenticates itself to the tag B.
    Briefly, once I'm connected to a tag (no matter which it is) I can't connect to another tag until I restart the app.
    The error is (the common) "Authentication Error", obviously without any other details.

    I repeat, I can connect to each tag individually, but not in sequence until I restart the entire app.

    I report the code highlights.

    Activity

    @Override
    protected void onCreate(Bundle savedInstanceState) {
    //other stuff..

    mDesfire = DesfireSingleton.getInstance();
    runDesfire();
    }

    @Override
    protected void onNewIntent(final Intent intent)
    {
    super.onNewIntent(intent);
    mDesfire.dispose();
    mDesfire = DesfireSingleton.getInstance();
    runDesfire();
    }

    private void runDesfire() {
    //other stuff
    final Handler handler = new Handler();
    handler.postDelayed(new Runnable()
    {
    public void run()
    {
    Intent currentIntent = getIntent();
    if (mDesfire.isActivityRegistered())
    mDesfire.initialize(NFCReaderActivity.this);

    boolean result = mDesfire.connect(currentIntent);
    if (result)
    {
    List files = mDesfire.readAllFiles();
    //other stuff
    }
    else {
    //other stuff
    }
    }
    }, 500);
    }


    DesfireSingleton

    public class DesfireSingleton {
    //classic Singleton stuff

    private static DesfireReader mDesfireReader;

    public void initialize(Activity caller) {
    mDesfireReader.initialize(caller);
    }

    public boolean connect(final Intent intent) throws Exception {
    return mDesfireReader.connect(intent);
    }

    public void dispose() {
    mDesfireReader.closeReader();
    mDesfireReader = null;
    instance = null;
    }

    //other stuff


    DesfireReader

    class DesfireReader {

    private String TAG = DesfireReader.class.getSimpleName();
    private NxpNfcLib mLibInstance = null;
    private CardType mCardType = CardType.UnknownCard;
    private IDESFireEV2 mDesfire;

    void initialize(Activity caller) {
    mLibInstance = NxpNfcLib.getInstance();
    mLibInstance.registerActivity(caller, DesfireConstants.LICENSE_KEY);
    }

    boolean connect(final Intent intent) {

    if (mDesfire != null && mDesfire.getReader().isConnected())
    return true;

    mCardType = mLibInstance.getCardType(intent);
    Log.d(TAG, String.format("Card type: %s", mCardType.getTagName()));

    if (mCardType != DESFireEV2) return false;

    mDesfire = DESFireFactory.getInstance().getDESFireEV2(mLibInstance.getCustomModules());
    mDesfire.getReader().connect();
    mDesfire.getReader().setTimeout(2000); //timeout to prevent exceptions in authentication
    return true;
    }

    boolean isActivityRegistered() {
    return mLibInstance.isActivityRegistered();
    }

    void closeReader() {
    if (mDesfire != null)
    mDesfire.getReader().close();

    mDesfire = null;
    }

    //other stuff contains a method where I authenticated while I read each application in the tag:
    DesfireRepository desfireApplication = DesfireApplicationFactory.GetDesfireApplication(i); //where 'i' is the current application index
    mDesfire.selectApplication(i);
    DesfireAuth authentication = new DesfireAuth(mDesfire);
    if (!authentication.authenticate(i))
    continue;
    List filesApplicationFiles = desfireApplication.getFiles(mDesfire);


    DesfireAuth

    public class DesfireAuth {

    private final IDESFireEV2 mDesfire;

    DesfireAuth(IDESFireEV2 desfire) {
    mDesfire = desfire;
    }

    boolean authenticate(int i) {
    byte[] uuid = mDesfire.getUID();
    byte[] secondAppKeyAccess = generateKey(uuid, DesfireConstants.KEY_APP_02_INT);
    KeyData secondAppKey = getAppKey(secondAppKeyAccess);
    mDesfire.selectApplication(i);
    return authenticate(secondAppKey);
    }

    private KeyData getAppKey(byte[] keyAccess) {
    Key key = new SecretKeySpec(keyAccess, DesfireConstants.AesAlghorithm);
    KeyData keyData = new KeyData();
    keyData.setKey(key);
    return keyData;
    }

    private boolean authenticate(KeyData keyData) {
    try {
    mDesfire.authenticate(2, IDESFireEV2.AuthType.AES, KeyType.AES128, keyData);
    return true;
    } catch (Exception ex) {
    ex.printStackTrace();
    return false;
    }
    }

    //other stuff


    Onestly I think the causes of my problems are the two Desfire singleton, "DESFireFactory" and "NxpNfcLib". Is there a way to reinitialize them? I think when I connect the second tag, their instances still contains the data of the old tag disconnected.
    Is that? There is a way to solve this?

    Thank you for the support,
    Bye
    + 0  |  - 0

    Re: Dealloc Desfire singleton instance

    6. December 2017 at 16:06
    Hi Fabio,

    You cannot remove one tag from the reader and put another tag on it and expect, a session can be continued! Any remove will terminate the session.

    The TapLinx team
    + 0  |  - 0

    Re: Dealloc Desfire singleton instance

    6. December 2017 at 16:44
    Hi,
    Which 'remove' do you refer to?
    The only method that can dispose the connection with a tag I found is "mDesfire.getReader().close()"
    + 0  |  - 0

    Re: Dealloc Desfire singleton instance

    7. December 2017 at 10:14
    Hi Fabio,

    If the newIntent() method is called, you know that a session has started. This session continues, until the user remove the tag. Inside of newIntent() you get the intermediate objects of the current session. You can save these objects, but this is useless for me, because you will get a new object and with the assignment from the factory methods the old object will be disposed.

    One favor: please do not post hundred lines of code in the forum. None of us has the time to study user code or debug user code. Few lines which makes clear what you want is always helpful.

    The TapLinx team
    + 0  |  - 0

    Re: Dealloc Desfire singleton instance

    7. December 2017 at 10:46
    Ok, I'm sorry.

    Anyway, when I switch the tag and newIntent() event is fired, the sdk still search the old tag even I reinitialize (as shown above) it.

    I have to absolutely solve this issue.
    + 0  |  - 0

    Re: Dealloc Desfire singleton instance

    7. December 2017 at 10:53
    Hi Fabio,

    No, the SDK cannot search for the old tag, because it is new session. You call connect() to new tag and all subsequent calls will directly interact with the current tag.

    The TapLinx team

    + 0  |  - 0

    Re: Dealloc Desfire singleton instance

    7. December 2017 at 16:41
    Ok, thank you.

    Does it work if the intent in "mLibInstance.getCardType(intent)" is the same and then I call "connect()" method too?
    + 0  |  - 0
Viewing 7 posts - 1 through 7 (of 7 total)

You must be logged in to reply to this topic.