Stream_Zero(irp->output, add);
}
-static void smartcard_output_repos(IRP* irp, UINT32 written)
-{
- UINT32 add = (4 - (written % 4)) % 4;
-
- if (add > 0)
- Stream_Zero(irp->output, add);
-}
-
size_t smartcard_multi_string_length_a(const char* msz)
{
char* p = (char*) msz;
SCARDCONTEXT hContext;
State_Call call;
State_Return ret;
- DWORD readerLen;
- char* readerName = NULL;
- BYTE atr[SCARD_ATR_LENGTH];
status = smartcard_unpack_state_call(smartcard, irp->input, &call);
if (status)
- goto finish;
+ return status;
hCard = (ULONG_PTR) call.hCard.pbHandle;
hContext = (ULONG_PTR) call.hCard.Context.pbContext;
- readerLen = SCARD_AUTOALLOCATE;
-
- ret.rgAtr = atr;
ret.cbAtrLen = SCARD_ATR_LENGTH;
- status = SCardStatusA(hCard, (LPSTR) &readerName, &readerLen,
- &ret.dwState, &ret.dwProtocol, ret.rgAtr, &ret.cbAtrLen);
+ status = SCardState(hCard, &ret.dwState, &ret.dwProtocol, (BYTE*) &ret.rgAtr, &ret.cbAtrLen);
if (status != SCARD_S_SUCCESS)
{
Stream_Zero(irp->output, 256);
- goto finish;
+ return status;
}
- Stream_Write_UINT32(irp->output, ret.dwState); /* dwState (4 bytes) */
- Stream_Write_UINT32(irp->output, ret.dwProtocol); /* dwProtocol (4 bytes) */
- Stream_Write_UINT32(irp->output, ret.cbAtrLen); /* cbAtrLen (4 bytes) */
- Stream_Write_UINT32(irp->output, 0x00000001); /* rgAtrPointer (4 bytes) */
- Stream_Write_UINT32(irp->output, ret.cbAtrLen); /* rgAtrLength (4 bytes) */
- Stream_Write(irp->output, ret.rgAtr, ret.cbAtrLen); /* rgAtr */
-
- smartcard_output_repos(irp, ret.cbAtrLen);
+ smartcard_pack_state_return(smartcard, irp->output, &ret);
smartcard_output_alignment(irp, 8);
-finish:
- if (readerName)
- {
- SCardFreeMemory(hContext, readerName);
- }
-
return status;
}
call.pvInBuffer, (DWORD) call.cbInBufferSize,
ret.pvOutBuffer, (DWORD) call.cbOutBufferSize, &ret.cbOutBufferSize);
- Stream_Write_UINT32(irp->output, (UINT32) ret.cbOutBufferSize); /* cbOutBufferSize (4 bytes) */
- Stream_Write_UINT32(irp->output, 0x00000004); /* pvOutBufferPointer (4 bytes) */
- Stream_Write_UINT32(irp->output, ret.cbOutBufferSize); /* pvOutBufferLength (4 bytes) */
-
- if (ret.cbOutBufferSize > 0)
- {
- Stream_Write(irp->output, ret.pvOutBuffer, ret.cbOutBufferSize); /* pvOutBuffer */
- smartcard_output_repos(irp, ret.cbOutBufferSize);
- }
+ smartcard_pack_control_return(smartcard, irp->output, &ret);
smartcard_output_alignment(irp, 8);
{
status = SCARD_E_INSUFFICIENT_BUFFER;
}
+
call.cbAttrLen = cbAttrLen;
+ ret.cbAttrLen = call.cbAttrLen;
if (status != SCARD_S_SUCCESS)
{
Stream_Zero(irp->output, 256);
goto finish;
}
- else
- {
- ret.cbAttrLen = call.cbAttrLen;
- Stream_Write_UINT32(irp->output, ret.cbAttrLen); /* cbAttrLen (4 bytes) */
- Stream_Write_UINT32(irp->output, 0x00020000); /* pbAttrPointer (4 bytes) */
- Stream_Write_UINT32(irp->output, ret.cbAttrLen); /* pbAttrLength (4 bytes) */
-
- if (!ret.pbAttr)
- Stream_Zero(irp->output, ret.cbAttrLen); /* pbAttr */
- else
- Stream_Write(irp->output, ret.pbAttr, ret.cbAttrLen); /* pbAttr */
-
- smartcard_output_repos(irp, ret.cbAttrLen);
- /* align to multiple of 4 */
- Stream_Write_UINT32(irp->output, 0);
- }
+ smartcard_pack_get_attrib_return(smartcard, irp->output, &ret);
smartcard_output_alignment(irp, 8);
return SCARD_S_SUCCESS;
}
+UINT32 smartcard_pack_state_return(SMARTCARD_DEVICE* smartcard, wStream* s, State_Return* ret)
+{
+ Stream_Write_UINT32(s, ret->dwState); /* dwState (4 bytes) */
+ Stream_Write_UINT32(s, ret->dwProtocol); /* dwProtocol (4 bytes) */
+ Stream_Write_UINT32(s, ret->cbAtrLen); /* cbAtrLen (4 bytes) */
+ Stream_Write_UINT32(s, 0x00020020); /* rgAtrNdrPtr (4 bytes) */
+ Stream_Write_UINT32(s, ret->cbAtrLen); /* rgAtrLength (4 bytes) */
+ Stream_Write(s, ret->rgAtr, ret->cbAtrLen); /* rgAtr */
+ smartcard_pack_write_offset_align(smartcard, s, 4);
+
+ return SCARD_S_SUCCESS;
+}
+
UINT32 smartcard_unpack_status_call(SMARTCARD_DEVICE* smartcard, wStream* s, Status_Call* call)
{
UINT32 status;
return SCARD_S_SUCCESS;
}
+UINT32 smartcard_pack_get_attrib_return(SMARTCARD_DEVICE* smartcard, wStream* s, GetAttrib_Return* ret)
+{
+ Stream_Write_UINT32(s, ret->cbAttrLen); /* cbAttrLen (4 bytes) */
+ Stream_Write_UINT32(s, 0x00020080); /* pbAttrPointer (4 bytes) */
+ Stream_Write_UINT32(s, ret->cbAttrLen); /* pbAttrLength (4 bytes) */
+
+ if (!ret->pbAttr)
+ Stream_Zero(s, ret->cbAttrLen); /* pbAttr */
+ else
+ Stream_Write(s, ret->pbAttr, ret->cbAttrLen); /* pbAttr */
+
+ smartcard_pack_write_offset_align(smartcard, s, 4);
+
+ return SCARD_S_SUCCESS;
+}
+
UINT32 smartcard_unpack_control_call(SMARTCARD_DEVICE* smartcard, wStream* s, Control_Call* call)
{
UINT32 status;
return SCARD_S_SUCCESS;
}
+UINT32 smartcard_pack_control_return(SMARTCARD_DEVICE* smartcard, wStream* s, Control_Return* ret)
+{
+ Stream_Write_UINT32(s, ret->cbOutBufferSize); /* cbOutBufferSize (4 bytes) */
+ Stream_Write_UINT32(s, 0x00020040); /* pvOutBufferPointer (4 bytes) */
+ Stream_Write_UINT32(s, ret->cbOutBufferSize); /* pvOutBufferLength (4 bytes) */
+
+ if (ret->cbOutBufferSize > 0)
+ {
+ Stream_Write(s, ret->pvOutBuffer, ret->cbOutBufferSize); /* pvOutBuffer */
+ smartcard_pack_write_offset_align(smartcard, s, 4);
+ }
+
+ return SCARD_S_SUCCESS;
+}
+
UINT32 smartcard_unpack_transmit_call(SMARTCARD_DEVICE* smartcard, wStream* s, Transmit_Call* call)
{
UINT32 status;
DWORD dwState;
DWORD dwProtocol;
/* [range] */ DWORD cbAtrLen;
- /* [size_is][unique] */ BYTE *rgAtr;
+ /* [size_is][unique] */ BYTE rgAtr[36];
} State_Return;
typedef struct _Status_Call
UINT32 smartcard_unpack_get_status_change_w_call(SMARTCARD_DEVICE* smartcard, wStream* s, GetStatusChangeW_Call* call);
UINT32 smartcard_unpack_state_call(SMARTCARD_DEVICE* smartcard, wStream* s, State_Call* call);
+UINT32 smartcard_pack_state_return(SMARTCARD_DEVICE* smartcard, wStream* s, State_Return* ret);
UINT32 smartcard_unpack_status_call(SMARTCARD_DEVICE* smartcard, wStream* s, Status_Call* call);
UINT32 smartcard_pack_status_return(SMARTCARD_DEVICE* smartcard, wStream* s, Status_Return* ret);
UINT32 smartcard_unpack_get_attrib_call(SMARTCARD_DEVICE* smartcard, wStream* s, GetAttrib_Call* call);
+UINT32 smartcard_pack_get_attrib_return(SMARTCARD_DEVICE* smartcard, wStream* s, GetAttrib_Return* ret);
UINT32 smartcard_unpack_control_call(SMARTCARD_DEVICE* smartcard, wStream* s, Control_Call* call);
+UINT32 smartcard_pack_control_return(SMARTCARD_DEVICE* smartcard, wStream* s, Control_Return* ret);
UINT32 smartcard_unpack_transmit_call(SMARTCARD_DEVICE* smartcard, wStream* s, Transmit_Call* call);
UINT32 smartcard_pack_transmit_return(SMARTCARD_DEVICE* smartcard, wStream* s, Transmit_Return* ret);
WINSCARDAPI LONG WINAPI PCSC_SCardState(SCARDHANDLE hCard,
LPDWORD pdwState, LPDWORD pdwProtocol, LPBYTE pbAtr, LPDWORD pcbAtrLen)
{
- return 0;
+ LONG status = SCARD_S_SUCCESS;
+
+ if (g_PCSC.pfnSCardStatus)
+ {
+ SCARDCONTEXT hContext = 0;
+ LPSTR mszReaderNames = NULL;
+ DWORD cchReaderLen = SCARD_AUTOALLOCATE;
+
+ status = g_PCSC.pfnSCardStatus(hCard, (LPSTR) &mszReaderNames, &cchReaderLen,
+ pdwState, pdwProtocol, pbAtr, pcbAtrLen);
+ status = PCSC_MapErrorCodeToWinSCard(status);
+
+ if (mszReaderNames)
+ {
+ if (g_PCSC.pfnSCardFreeMemory)
+ {
+ hContext = PCSC_GetSmartCardContextFromHandle(hCard);
+
+ g_PCSC.pfnSCardFreeMemory(hContext, mszReaderNames);
+ }
+ }
+ }
+
+ return status;
}
WINSCARDAPI LONG WINAPI PCSC_SCardStatusA(SCARDHANDLE hCard,