📄 pcsc_drv.cpp
字号:
// =====[pcsc_drv.cpp]====================================================================
// Description: Source file (pcsc_drv.cpp)
// Compiled: MS-VC++
// Version: .NET
// Revisions:
// REV DATE BY DESCRIPTION
// ------ -------------- ---------- --------------------------------------
// 1.01 2001/01/01 BDS Initial version.
// 1.02 2003/06/09 BDS IoDeleteSymbolicLink was added
//
// This source file (pcsc_drv.cpp) is Copyright(c) 2001 Dmitry Basko.
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that:
// 1. source code distributions retain the above copyright notice and this
// paragraph in its entirety;
// 2. distributions including binary code include the above copyright notice
// and this paragraph in its entirety in the documentation or other materials
// provided with the distribution;
// 3. all advertising materials mentioning features or use of this software
// display the following acknowledgement;
// "This product includes software developed by Dmitry Basko."
// THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
// WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
// =========================================================================================
#pragma once
#ifndef DRIVER_CPP
#define DRIVER_CPP
// This programm is compiled ONLY for WIN32 and M_IX86 processor
#if defined(_WIN32) && defined(_M_IX86)
#include "pcsc_drv.h"
#pragma warning(push, 3)
#pragma warning(disable : 4514)
BYTE bATR[13] = {0x3b, 0x89, 0x40, 0x14, 0x47, 0x47, 0x32, 0x34, 0x4d, 0x35, 0x32, 0x38, 0x30};
UCHAR ATRLength = 13;
static ULONG dataRatesSupported[] = { 9600, 19200, 38400, 57600, 115200 };
//<summary>
// ======================================================================
//<newpara> Author :BD Date : 01-01-2001 </newpara>
// ======================================================================
//<newpara> Function : DriverEntry</newpara>
//<newpara> Comments : </newpara>
//</summary>
//Parameters :
// <param name="DriverObject"> </param>
// <param name="RegistryPath"> </param>
//<returns> </returns>
// ======================================================================
NTSTATUS DriverEntry(PDRIVER_OBJECT DriverObject, PUNICODE_STRING RegistryPath)
{
NTSTATUS status = STATUS_SUCCESS;
PDEVICE_OBJECT pDeviceObject = NULL;
PDEVICE_EXTENSION pDeviceExtension = NULL;
KdPrint(("%sDriverEntry\n",HEAD));
#ifdef MAX_DEBUG_LEVEL
SmartcardSetDebugLevel(0x7FFFFFFF);
#endif
#ifdef USE_EVENT_LOG
InitializeEventLog(DriverObject);
#endif
// tell the system our entry points
DriverObject->MajorFunction[IRP_MJ_CREATE] = VdCreate;
DriverObject->MajorFunction[IRP_MJ_CLOSE] = VdClose;
DriverObject->MajorFunction[IRP_MJ_CLEANUP] = VdCleanUp;
DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = VdDeviceControl;
DriverObject->DriverUnload = VdDriverUnload;
if ((status = VdCreateDevice(DriverObject)) == STATUS_SUCCESS)
{
#ifdef USE_SYSTEM_THREAD
pDeviceObject = (PDEVICE_OBJECT)DriverObject->DeviceObject;
pDeviceExtension = (PDEVICE_EXTENSION)pDeviceObject->DeviceExtension;
// Let's prepare for launch SYSTEM THREAD
if ((pDeviceExtension->_PIO_WORKITEM = (PIO_WORKITEM) IoAllocateWorkItem(pDeviceObject)) != NULL)
{
if ((pDeviceExtension->pMemory_Buf = (PUCHAR)ExAllocatePool(NonPagedPool, MEMORY_BUF_SIZE)) != NULL)
{
RtlFillMemory(pDeviceExtension->pMemory_Buf, MEMORY_BUF_SIZE, 0xAA);
pDeviceExtension->uSizeOfData = MEMORY_BUF_SIZE;
// Let's read memory from file
IoQueueWorkItem(pDeviceExtension->_PIO_WORKITEM, (PIO_WORKITEM_ROUTINE)Work_SystemThread,
DelayedWorkQueue , pDeviceExtension->pMemory_Buf);
}
else
{
KdPrint(("\t%sMEMORY BUF was not allocated\n",HEAD));
#ifdef REGISTER_INTERFACE
if (pDeviceExtension->DeviceName.Buffer != NULL)
// disable our device so no one can open it
IoSetDeviceInterfaceState(&pDeviceExtension->DeviceName, FALSE);
#endif
// Wait until we can safely unload the device
SmartcardExit(&pDeviceExtension->SmartcardExtension);
#ifdef REGISTER_INTERFACE
// delete the symbolic link
if (pDeviceExtension->DeviceName.Buffer != NULL)
{
RtlFreeUnicodeString(&pDeviceExtension->DeviceName);
SET_NULL(pDeviceExtension->DeviceName.Buffer)
}
#endif
if (pDeviceExtension->SmartcardExtension.ReaderExtension != NULL)
{
ExFreePool(pDeviceExtension->SmartcardExtension.ReaderExtension);
SET_NULL(pDeviceExtension->SmartcardExtension.ReaderExtension)
}
// delete the device object
IoDeleteDevice(pDeviceObject);
SET_NULL(pDeviceObject)
status = (STATUS_INSUFFICIENT_RESOURCES);
}
}
else
{
KdPrint(("\t%sPIO_WORKITEM was not allocated\n",HEAD));
#ifdef REGISTER_INTERFACE
if (pDeviceExtension->DeviceName.Buffer != NULL)
// disable our device so no one can open it
IoSetDeviceInterfaceState(&DeviceExtension->DeviceName, FALSE);
#endif
// Wait until we can safely unload the device
SmartcardExit(&pDeviceExtension->SmartcardExtension);
#ifdef REGISTER_INTERFACE
if (pDeviceExtension->DeviceName.Buffer != NULL)
{
RtlFreeUnicodeString(&pDeviceExtension->DeviceName);
SET_NULL(pDeviceExtension->DeviceName.Buffer)
}
#endif
if (pDeviceExtension->SmartcardExtension.ReaderExtension != NULL)
{
ExFreePool(pDeviceExtension->SmartcardExtension.ReaderExtension);
SET_NULL(pDeviceExtension->SmartcardExtension.ReaderExtension)
}
// delete the device object
IoDeleteDevice(pDeviceObject);
SET_NULL(pDeviceObject)
status = (STATUS_INSUFFICIENT_RESOURCES);
}
#endif
}
#ifdef USE_EVENT_LOG
(!status)? (ReportEvent(LOG_LEVEL_DEBUG,MSG_DRIVER_STARTING,ERRORLOG_DRIVERENTRY,(PVOID)DriverObject,
NULL,NULL, 0,NULL, 0 )):(ReportEvent(LOG_LEVEL_DEBUG,MSG_DRIVER_STARTING_FAULT,ERRORLOG_DRIVERENTRY_FAULT,(PVOID)DriverObject,
NULL,(ULONG*)status, 1,NULL, 0 ));
#endif
return status;
}
//<summary>
// ======================================================================
//<newpara> Author :BD Date : 01-01-2001 </newpara>
// ======================================================================
//<newpara> Function : VdCreateDevice</newpara>
//<newpara> Comments : </newpara>
//</summary>
//Parameters :
// <param name="DriverObject"> </param>
//<returns> </returns>
// ======================================================================
NTSTATUS VdCreateDevice(IN PDRIVER_OBJECT DriverObject)
{
PDEVICE_OBJECT pDeviceObject = NULL;
NTSTATUS status = STATUS_SUCCESS;
PDEVICE_EXTENSION pDeviceExtension = NULL;
PSMARTCARD_EXTENSION pSmartcardExtension = NULL;
PREADER_EXTENSION pReaderExtension = NULL;
UNICODE_STRING UniDeviceName;
KdPrint(("%sVdCreateDevice\n",HEAD));
RtlInitUnicodeString(&UniDeviceName, L"\\Device\\InesSUDP");
// Create the device object
if ((status = IoCreateDevice(DriverObject, sizeof(DEVICE_EXTENSION), &UniDeviceName, FILE_DEVICE_SMARTCARD,
0, FALSE, &pDeviceObject)) == STATUS_SUCCESS)
{
pDeviceExtension = (PDEVICE_EXTENSION)pDeviceObject->DeviceExtension;
RtlZeroMemory(pDeviceExtension, sizeof(DEVICE_EXTENSION));
pSmartcardExtension = &pDeviceExtension->SmartcardExtension;;
// allocate the reader extension
if ((pReaderExtension = (PREADER_EXTENSION)ExAllocatePool(NonPagedPool, sizeof(READER_EXTENSION))) != NULL)
{
RtlZeroMemory(pReaderExtension, sizeof(READER_EXTENSION));
pSmartcardExtension->ReaderExtension = pReaderExtension;
// Let's keep callback address to pDeviceExtension
pSmartcardExtension->ReaderExtension->pDeviceExtension = pDeviceExtension;
pSmartcardExtension->Version = SMCLIB_VERSION;
pSmartcardExtension->SmartcardRequest.BufferSize = MIN_BUFFER_SIZE;
pSmartcardExtension->SmartcardReply.BufferSize = MIN_BUFFER_SIZE;
if ((status = SmartcardInitialize(pSmartcardExtension)) == STATUS_SUCCESS)
{
DEVICE_READER_EXTENSION(uStateOfCard) = true; // the card is inserted
pSmartcardExtension->ReaderFunction[RDF_CARD_POWER] = VdPowerReader;
pSmartcardExtension->ReaderFunction[RDF_SET_PROTOCOL] = VdSetProtocol;
pSmartcardExtension->ReaderFunction[RDF_TRANSMIT] = VdTransmit;
pSmartcardExtension->ReaderFunction[RDF_CARD_TRACKING] = VdCardTracking;
pSmartcardExtension->ReaderFunction[RDF_IOCTL_VENDOR] = VdVendorIOCTL;
strcpy((char *)pSmartcardExtension->VendorAttr.VendorName.Buffer, (char *) "COMRAD");
pSmartcardExtension->VendorAttr.VendorName.Length =
(USHORT) strlen((char*)pSmartcardExtension->VendorAttr.VendorName.Buffer);
strcpy((char *)pSmartcardExtension->VendorAttr.IfdType.Buffer, (char *) "000001");
pSmartcardExtension->VendorAttr.IfdType.Length =
(USHORT)strlen((char *)pSmartcardExtension->VendorAttr.IfdType.Buffer);
pSmartcardExtension->VendorAttr.UnitNo = 0;
pSmartcardExtension->VendorAttr.IfdVersion.BuildNumber = 1;
pSmartcardExtension->VendorAttr.IfdVersion.VersionMinor = 2;
pSmartcardExtension->VendorAttr.IfdVersion.VersionMajor = 3;
pSmartcardExtension->VendorAttr.IfdSerialNo.Length = 0;
// Set the reader capabilities
// Clk frequency in KHz encoded as little endian integer
pSmartcardExtension->ReaderCapabilities.CLKFrequency.Default = 3571;
pSmartcardExtension->ReaderCapabilities.CLKFrequency.Max = 3571;
// 4000;
pSmartcardExtension->ReaderCapabilities.DataRate.Default =
pSmartcardExtension->ReaderCapabilities.DataRate.Max = // 10750;
dataRatesSupported[0];
// reader could support higher data rates
pSmartcardExtension->ReaderCapabilities.DataRatesSupported.List = dataRatesSupported;
pSmartcardExtension->ReaderCapabilities.DataRatesSupported.Entries =
sizeof(dataRatesSupported) / sizeof(dataRatesSupported[0]);
pSmartcardExtension->ReaderCapabilities.MaxIFSD = 254;
// This reader supports T0 and T1
pSmartcardExtension->ReaderCapabilities.SupportedProtocols = SCARD_PROTOCOL_T0 | SCARD_PROTOCOL_T1;
//************************************************************************************
//this place must be corrected ! I do not remember exactly what ATR reports, but later
//any attempts to communicate with SC, using T1 protocol will be rejected by driver
//************************************************************************************
pSmartcardExtension->ReaderCapabilities.MechProperties = 0;
pSmartcardExtension->ReaderCapabilities.Channel = 0;
// Reader type
pSmartcardExtension->ReaderCapabilities.ReaderType = SCARD_READER_TYPE_VENDOR;
// Now setup information in our deviceExtension
pSmartcardExtension->ReaderCapabilities.CurrentState = SCARD_PRESENT;
// SCARD_ABSENT;
if ((status = SmartcardCreateLink(&pDeviceExtension->LinkName, &UniDeviceName)) == STATUS_SUCCESS)
{
pSmartcardExtension->OsData->DeviceObject = (pDeviceObject);
pDeviceObject->Flags |= DO_BUFFERED_IO;
pDeviceObject->Flags &= ~DO_DEVICE_INITIALIZING;
//KdPrint(("SmartcardUpdateCardCapabilities %#X\n",SmartcardUpdateCardCapabilities(pSmartcardExtension)));
}
else
{
KdPrint(("\t%sCreateDevice SmartCardCreateLink FAILED\n",HEAD, (ULONG) status));
IoDeleteDevice(pDeviceObject);
KdPrint(("%sLink was not created\n",HEAD));
}
}
else
{
KdPrint(("\t%sCreateDevice SMARTCARDINITIALISE FAILED\n",HEAD, (ULONG) status));
IoDeleteDevice(pDeviceObject);
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -