?? protoutils.cpp
字號:
////////////////////////////////////
// protoutils.cpp文件
#include <windows.h>
#include <winioctl.h>
#include <tchar.h>
#include <ntddndis.h>
#include <stdio.h>
#include "protoutils.h"
/////////////////////////////////////////////////////////////////
// 控制函數
BOOL ProtoStartService()
{
BOOL bRet = FALSE;
SC_HANDLE hSCM = NULL, hService = NULL;
char szLinkName[] = "Packet";
// 打開SCM管理器
hSCM = ::OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
if(hSCM != NULL)
{
hService = ::OpenService(hSCM, szLinkName, SERVICE_ALL_ACCESS);
if(hService != NULL)
{
if(!::StartService(hService, 0, NULL))
{
int nError = ::GetLastError();
if(nError == ERROR_SERVICE_ALREADY_RUNNING)
{
bRet = TRUE;
}
}
else
{
bRet = TRUE;
}
}
}
if(hService != NULL)
::CloseServiceHandle(hService);
if(hSCM != NULL)
::CloseServiceHandle(hSCM);
if(bRet)
::Sleep(50);
return bRet;
}
void ProtoStopService()
{
SC_HANDLE hSCM = NULL, hService = NULL;
char szLinkName[] = "Packet";
// 打開SCM管理器
hSCM = ::OpenSCManager(NULL, NULL, SC_MANAGER_ALL_ACCESS);
if(hSCM != NULL)
{
hService = ::OpenService(hSCM, szLinkName, SERVICE_ALL_ACCESS);
if(hService != NULL)
{
// 等待服務完全停止運行
SERVICE_STATUS ss;
::ControlService(hService, SERVICE_CONTROL_STOP, &ss);
}
}
if(hService != NULL)
::CloseServiceHandle(hService);
if(hSCM != NULL)
::CloseServiceHandle(hSCM);
}
HANDLE ProtoOpenControlDevice()
{
// 打開驅動程序所控制設備的句柄
HANDLE hFile = ::CreateFile(
_T("\\\\.\\Packet"),
GENERIC_READ | GENERIC_WRITE,
0,
NULL,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
NULL);
return hFile;
}
BOOL CPROTOAdapters::EnumAdapters(HANDLE hControlDevice)
{
DWORD dwBufferLength = sizeof(m_buffer);
BOOL bRet = ::DeviceIoControl(hControlDevice, IOCTL_ENUM_ADAPTERS,
NULL, 0, m_buffer, dwBufferLength, &dwBufferLength, NULL);
if(!bRet)
return FALSE;
// 保存適配器數量
m_nAdapters = (ULONG)((ULONG*)m_buffer)[0];
// 下面從m_buffer中獲取適配器名稱和符號連接名稱
// 指向設備名稱
WCHAR *pwsz = (WCHAR *)((ULONG *)m_buffer + 1);
int i = 0;
m_pwszAdapterName[i] = pwsz;
while(*(pwsz++) != NULL)
{
while(*(pwsz++) != NULL)
{ ; }
m_pwszSymbolicLink[i] = pwsz + 12; // pwsz 指向"\DosDevices\Packet_{}", 加12是為了去掉"\DosDevices\"
while(*(pwsz++) != NULL)
{ ; }
if(++i >= MAX_ADAPTERS)
break;
m_pwszAdapterName[i] = pwsz;
}
return TRUE;
}
//////////////////////////////////////////////////////////
CAdapter::CAdapter()
{
m_hAdapter = INVALID_HANDLE_VALUE;
}
CAdapter::~CAdapter()
{
CloseAdapter();
}
BOOL CAdapter::OpenAdapter(LPCWSTR pwszSymbolicLink, BOOL bAsyn)
{
char szFile[1024];
wsprintf(szFile, _T("\\\\.\\%ws"), pwszSymbolicLink);
// 打開到驅動程序所控制設備的句柄
m_hAdapter = ::CreateFile(szFile,
GENERIC_READ | GENERIC_WRITE,
0,
NULL,
OPEN_EXISTING,
bAsyn ? FILE_ATTRIBUTE_NORMAL|FILE_FLAG_OVERLAPPED : FILE_ATTRIBUTE_NORMAL,
NULL);
int n = ::GetLastError();
return m_hAdapter != INVALID_HANDLE_VALUE;
}
void CAdapter::CloseAdapter()
{
if(m_hAdapter != INVALID_HANDLE_VALUE)
{
::CloseHandle(m_hAdapter);
m_hAdapter = INVALID_HANDLE_VALUE;
}
}
BOOL CAdapter::ProtoRequest(PPROTOCOL_OID_DATA pOidData, BOOL bQuery)
{
if(m_hAdapter == INVALID_HANDLE_VALUE)
return FALSE;
DWORD dw;
BOOL bRet = ::DeviceIoControl(
m_hAdapter, bQuery ? IOCTL_PROTOCOL_QUERY_OID : IOCTL_PROTOCOL_SET_OID,
pOidData, sizeof(PROTOCOL_OID_DATA) -1 + pOidData->Length,
pOidData, sizeof(PROTOCOL_OID_DATA) -1 + pOidData->Length, &dw, NULL);
return bRet;
}
BOOL CAdapter::SetFilter(ULONG nFilters)
{
PPROTOCOL_OID_DATA pOidData = (PPROTOCOL_OID_DATA)
::GlobalAlloc(GPTR, (sizeof(PROTOCOL_OID_DATA) + sizeof(ULONG) - 1));
pOidData->Oid = OID_GEN_CURRENT_PACKET_FILTER;
pOidData->Length = sizeof(ULONG);
*((PULONG)pOidData->Data) = nFilters;
BOOL bRet = ProtoRequest(pOidData, FALSE);
::GlobalFree(pOidData);
return bRet;
}
BOOL CAdapter::ResetAdapter()
{
DWORD dw;
BOOL bRet = ::DeviceIoControl(m_hAdapter, IOCTL_PROTOCOL_RESET, NULL, 0, NULL, 0, &dw, NULL);
return bRet;
}
int CAdapter::RecieveData(PVOID pBuffer, int nLen, LPOVERLAPPED lpOverlapped)
{
DWORD dwRead;
if(::ReadFile(m_hAdapter, pBuffer, nLen, &dwRead, lpOverlapped))
return dwRead;
else
return -1;
}
int CAdapter::SendData(PVOID pBuffer, int nLen, LPOVERLAPPED lpOverlapped)
{
DWORD dwWrite;
if(::WriteFile(m_hAdapter, pBuffer, nLen, &dwWrite, lpOverlapped))
return dwWrite;
else
return -1;
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -