To add functionality to a service provider, you need to know how an ISO7816-4 ADPU is built within the base service provider DLLs. The following procedure gives a brief overview of the build process.
Note The code segments included here are not necessarily complete; refer to the example applications and DLLs for more information.
// Create an ISCardCmd object
// Note: To use CoCreateInstance on Windows 95, make sure no Distributed COM
// flags are included in the API call or during build. Do not define flags
// _WIN32_DCOM or _WIN32_WINNT >= 0x0400.
hresult = CoCreateInstance( CLSID_CSCardCmd,
NULL,
CLSCTX_ALL,
IID_ISCardCmd,
(LPVOID*) &g_pISCardCmd);
//Create an ISCardISO7816 object
hresult = CoCreateInstance( CLSID_CSCardISO7816,
NULL,
CLSCTX_ALL,
IID_ISCardISO7816,
(LPVOID*) &g_pISCardISO7816);
The ISCardCmd object contains two IByteBuffer buffers. One buffer contains the actual APDU command string (plus any data to send with the command). The other contains any reply information returned by the card after command execution.
// Do challenge
hresult = g_pISCardISO7816->GetChallenge( dwLengthOfChallenge,
&g_pISCardCmd);
Here is the code used in the GetChallenge method:
STDMETHODIMP CSCardISO7816::GetChallenge( IN DWORD dwBytesExpected /*= 0*/,
IN OUT LPSCARDCMD *ppCmd)
{
// Locals.
HRESULT hr = S_OK;
try
{
// Is the ISCardCmd object ok?
hr = IsSCardCmdValid(ppCmd);
if (FAILED(hr))
throw (hr);
// Do it!
hr = (*ppCmd)->BuildCmd( m_byClassId,
(BYTE) INS_GET_CHALLENGE),
(BYTE) INS_NULL),// P1 = 0x00
(BYTE) INS_NULL),// P2 = 0x00
NULL,
&dwBytesExpected);
if (FAILED(hr))
throw (hr);
}
The ISCardISO7816::GetChallenge method simply uses the ISCardCmd::BuildCmd to build the requested APDU. This is done by writing the appropriate information into the ISCardCmd APDU buffer in the hr = (*ppCmd)->BuildCmd line above.
The recommended way to expand the service provider build-execute process described above is to create a new COM object. This COM object should support a new interface that allows creation of non-ISO7816-4 commands and should aggregate the ISCardISO7816 interface.