1
votes

I am developing a C++ application (on Windows 7) which interfaces with PC/SC card readers to perform some authentication operations. This application is the child process of another application (I don't know if that's relevant, but it might be).

I also have a simple standalone test application which performs all the interactions with the smart card that I need and does so successfully. However I have run into some odd behavior when integrating the code from this utility into my main application.

In particular the first command I send to the card is a SELECT FILE command:

0x00 0xa4 0x04 0x00 ...

The response to this command is the same as with my standalone test utility:

0x61 0x13

As this indicates that there are more response bytes available, I send a GET RESPONSE command:

0x00 0xc0 0x00 0x00 0x13

This command fails with an error indicating that the instruction is invalid:

0x6d 0x00

However my test utility (running with the same card reader and the same card) receives a successful response (e.g. ending in ... 0x90 0x00). However the test application requires the smart card to be in the reader when it's started (it's a simple application which starts, does what it needs to, then exists). The error I described for my actual application does not occur if the card is in the reader at startup (just like with my test reader).

Does anybody have any ideas what could be the source of this problem. The card does support the given instruction code as evidenced by the fact that under some situations it will respond to it successfully. The card is good (it responds to the initial SELECT FILE command as expected). I don't think it's a permissions issue (again, it works at startup). My main application is multi-threaded but all card interactions occur on a single thread. I am at a loss. Any suggestions would be greatly appreciated.

Another thing I've noticed is that in the successful scenario (e.g. with the card in the reader when the application starts up) the GET RESPONSE takes ~0.05 seconds while in the unsuccessful scenario (e.g. the card is inserted sometime after the application starts up) it takes ~2 seconds.

1
You might want to either try to wait a few seconds after the card was inserted into the reader before you start sending commands, or you open the card reader for exclusive access. What you experience might be related to Windows 7 plug-and-play for smartcards with automatically sends a whole bunch of commands to your card and may result into your commands getting interleaved with those plug-and-play commands.Michael Roland
@MichaelRoland is exactly correct. By switching to getting an exclusive handle to the card (and doing a wait-and-retry on failure) everything started working just fine. Thanks a lot!DAG

1 Answers

2
votes

What you experience might be related to Windows 7 plug-and-play for smartcards. This plug-and-play feature automatically sends a whole bunch of commands to a card right after its inserted into the reader. If your app also starts to send commands at that time, this may result into your commands getting interleaved with the commands from plug-and-play.

Therefore, you might want to either try to wait a few seconds after the card was inserted into the reader before you start sending commands, or you open the card reader for exclusive access.

For exclusive access, use the value SCARD_SHARE_EXCLUSIVE for the parameter dwShareMode of SCardConnect.