📄 driverloader.cpp
字号:
/*++
Module name:
DriverLoader.cpp
Author:
Tom
Mode:
User mode
Declarations:
implementation of class DriverLoader
--*/
#include "stdafx.h"
#include "DriverLoader.h"
//#include "string.h"
//
// Static class member variables defined/initialized here
//
//Operating system information
OSTYPE DriverLoader::OsType = INVALIDOS;
DWORD DriverLoader::OsVersion = 0L;
TCHAR DriverLoader::systemRoot[] = _T("");
//Error control
#ifdef _DEBUG
TCHAR DriverLoader::ErrorBuf[] = _T("");
DWORD DriverLoader::dwErrorCode = 0L;
#endif
DriverLoader::DriverLoader():DriverLinkName(NULL),DriverFileName(NULL),
DrvHandle(HANDLE(-1)),m_bInitializeOk(FALSE),m_nDriverState(STOPPED)
/*++
Routine description:
Default constructor, it's a private member function. that's to say, caller can not create
an instance via this class unless create a sub-class that delivered from this class
Argument:
NONE
Return:
NONE
--*/
{
ZeroMemory( CurDir, sizeof(CurDir) );
ZeroMemory( driverPath, sizeof(driverPath) );
}
DriverLoader::DriverLoader(const TCHAR * DrvName)
/*++
Routine description:
Constructor that takes a parameter that represents the symbol link of the specified driver
Argument:
DrvName : symblic link name of the specified driver.
Return:
NONE
--*/
{
DriverLinkName = new TCHAR[ _tcslen(DrvName)+1 ];
DriverFileName = new TCHAR[ _tcslen(DrvName)+5 ];
_tcscpy( DriverLinkName, DrvName );
_stprintf( DriverFileName, _T("%s%s"), DriverLinkName, _T(".sys") );
ZeroMemory( driverPath,sizeof(driverPath) );
ZeroMemory( CurDir, sizeof(CurDir) );
m_bInitializeOk = FALSE;
DrvHandle = INVALID_HANDLE_VALUE; //-1
m_nDriverState = STOPPED;
}
DriverLoader::DriverLoader(const DriverLoader & drv)
/*++
Routine description:
Copy constructor
--*/
{
DriverLinkName = new TCHAR[ _tcslen(drv.DriverLinkName)+1 ];
DriverFileName = new TCHAR[ _tcslen(drv.DriverFileName)+1 ];
_tcscpy( DriverLinkName, drv.DriverLinkName );
_tcscpy( DriverFileName, drv.DriverFileName );
_tcscpy( CurDir, drv.CurDir );
_tcscpy( driverPath, drv.driverPath );
DrvHandle = drv.DrvHandle;
m_bInitializeOk = drv.m_bInitializeOk;
m_nDriverState = drv.m_nDriverState;
}
DriverLoader & DriverLoader::operator =(const DriverLoader & dvl)
/*++
Routine description:
operator =
--*/
{
if(this==&dvl)
return * this;
if(DriverLinkName)
delete[] DriverLinkName;
DriverLinkName = new TCHAR[ _tcslen(dvl.DriverLinkName)+1 ];
_tcscpy( DriverLinkName, dvl.DriverLinkName );
if(DriverFileName)
delete[] DriverFileName;
DriverFileName = new TCHAR[ _tcslen(dvl.DriverFileName)+1 ];
_tcscpy( DriverFileName, dvl.DriverFileName );
m_bInitializeOk = dvl.m_bInitializeOk;
DrvHandle = dvl.DrvHandle;
_tcscpy( CurDir, dvl.CurDir );
_tcscpy( driverPath, dvl.driverPath );
return * this;
}
DriverLoader::~DriverLoader()
/*++
Routine description:
Desctructor
--*/
{
if(DriverLinkName)
delete[] DriverLinkName;
if(DriverFileName)
delete[] DriverFileName;
}
BOOL DriverLoader::SetDriverInfo()
/*++
Routine discription:
set member variables associated with the driver
Return:
TRUE on successful
FALSE on failure
--*/
{
//
// Get current(work) directory of the driver files stays.
// The user must copy his driver file into this file.
//
// if( !GetCurrentDirectory(sizeof(CurDir), CurDir) )
if( !GetModuleFileName(NULL, CurDir, MAX_PATH) )
{
ERROR_DUMP( _T("DriverLoader::SetDriverInfo()"), _T("") );
return FALSE;
}
//
// construct the full path name of the device driver
// Source directory
//
TCHAR * pch;
pch = _tcsrchr( CurDir, _T('\\') );
*pch = _T('\0');
_stprintf( CurDir+_tcslen(CurDir),_T("\\%s"),DriverFileName );
//
// construct the full path name of the device driver
// in system directory,it is systemroot\drivername.sys
//
_stprintf( driverPath, _T("%s\\drivers\\%s"), systemRoot, DriverFileName );
return TRUE;
}
BOOL DriverLoader::Initialize()
/*++
Routine description:
After the caller created the instance,he can do only call this
function to initialize all necessary information,otherwise,all the
access to the instance will be denied.
Return:
TRUE on successful
FALSE on failure.
--*/
{
m_bInitializeOk = SetDriverInfo();
return m_bInitializeOk;
}
BOOL DriverLoader::QueryOsInfo()
/*++
Set some private variables related with the Operating System
It's a static member function,it access only static variables.
--*/
{
OSVERSIONINFOEX osvi; //OSVERSIONINOFEX is a structure valid only in 2K
BOOL bOsVersionInfoEx;
//
// Set system root
//
GetSystemDirectory( systemRoot, sizeof(systemRoot) );
//
// Try calling GetVersionEx using the OSVERSIONINFOEX structure,
// which is supported on Windows 2000.
//
// If that fails, try using the OSVERSIONINFO structure.
//
ZeroMemory( &osvi, sizeof(OSVERSIONINFOEX) );
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFOEX);
if( !(bOsVersionInfoEx = GetVersionEx((OSVERSIONINFO *)&osvi)) )
{
osvi.dwOSVersionInfoSize = sizeof (OSVERSIONINFO);
if (!GetVersionEx((OSVERSIONINFO *) &osvi) )
{
OsType = INVALIDOS; // not supported OS
ERROR_DUMP( _T("DriverLoader::QueryOsInfo"), _T("GetVersionEx error") );
return FALSE;
}
}
switch (osvi.dwPlatformId)
{
case VER_PLATFORM_WIN32_NT:
/*
//-------------------------------------------------------
// Test for the product
//-------------------------------------------------------
if ( osvi.dwMajorVersion <= 4 )
{
OsType = WINNT;
}
// printf( "Microsoft Windows NT ");
if ( osvi.dwMajorVersion == 5 )
{
OsType = WIN2K;
// printf ("Microsoft Windows 2000 ");
}
*/
//-------------------------------------------------------
// Test for workstation versus server.
//-------------------------------------------------------
if( bOsVersionInfoEx ) //2000
{
if ( osvi.wProductType == VER_NT_WORKSTATION )
{
OsType = WIN2KP; //Profesisonal edition
}
if ( osvi.wProductType == VER_NT_SERVER )
{
OsType = WIN2KS;
}
}
else //Not 2000,but NT
{
HKEY hKey;
TCHAR szProductType[80];
DWORD dwBufLen;
RegOpenKeyEx( HKEY_LOCAL_MACHINE,
_T("SYSTEM\\CurrentControlSet\\Control\\ProductOptions"),
0,
KEY_QUERY_VALUE,
&hKey
);
RegQueryValueEx( hKey,
_T("ProductType"),
NULL,
NULL,
(LPBYTE) szProductType,
&dwBufLen
);
RegCloseKey( hKey );
if ( lstrcmpi( _T("WINNT"), szProductType) == 0 ) //not case sensitive compare
{
OsType = WINNTW; //NT workstation
}
if ( lstrcmpi( _T("SERVERNT"), szProductType) == 0 )
{
OsType = WINNTS; //NT Server
}
}
break;
case VER_PLATFORM_WIN32_WINDOWS: //win 9x series
if ((osvi.dwMajorVersion > 4) ||
((osvi.dwMajorVersion == 4) && (osvi.dwMinorVersion > 0)))
{//Win98
OsType = WIN98;
}
else //win 95
OsType = WIN95;
break;
case VER_PLATFORM_WIN32s:
OsType = WIN32s;
break;
}
OsVersion = osvi.dwMajorVersion;
if( OsType == INVALIDOS )
{
DWORD dwVersion = 0L;
dwVersion = GetVersion();
if( dwVersion >= 0x80000000 )
{
ERROR_DUMP( _T("DriverLoader::QueryOsInfo"), _T("Not supported OS") );
return FALSE;
}
else OsType = WINNTW;
}
return TRUE;
}
//
//
// This function remove the legacy driver in the system directory in considering
// of incompatibility
// It will call some services offered by Win2000 SCM
//
// Maybe I should use Structured Exception Handling (SEH) here and related functions
//
// Arguments:
// SchSCManager: SCM handle
// DriverLinkName : symbolic link name of device driver like "\\.\XXX"
// Return :
// TRUE on success
// FALSE on failure
// I don't care the return of the function. so maybe no need to make error string.
//
BOOL DriverLoader::RemoveDriver( IN SC_HANDLE SchSCManager,IN LPCTSTR DriverLinkName )
{
CheckRight();
SC_HANDLE schService;
BOOL ret;
schService = OpenService( SchSCManager, //passed by OpenSCManager routine
DriverLinkName, //symbolic link name
SERVICE_ALL_ACCESS );
if( !schService ) //not found the existing service in registry
{
CloseServiceHandle( schService );
return FALSE;
}
//--------------------------------------------------------------------------
// The DeleteService function marks the specified service for deletion
// from the SCM database
//
// Syntax:
// BOOL DeleteService(
// SC_HANDLE hService
// );
//
//--------------------------------------------------------------------------
ret = DeleteService( schService ); //delete the legacy samename service from SCM
CloseServiceHandle( schService );
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -