FreeProvider(pProtoInfo);
return TRUE;
}
BOOL RemoveProvider()
{
LPWSAPROTOCOL_INFOW pProtoInfo;
int nProtocols;
DWORD dwLayeredCatalogId;
// 根据Guid取得分层协议的目录ID号
pProtoInfo = GetProvider(&nProtocols);
int nError;
for(int i=0; i<nProtocols; i++)
{
if(memcmp(&ProviderGuid, &pProtoInfo[i].ProviderId, sizeof(ProviderGuid)) == 0)
{
dwLayeredCatalogId = pProtoInfo[i].dwCatalogEntryId;
break;
}
}
if(i < nProtocols)
{
// 移除协议链
for(i=0; i<nProtocols; i++)
{
if((pProtoInfo[i].ProtocolChain.ChainLen > 1) &&
(pProtoInfo[i].ProtocolChain.ChainEntries[0] == dwLayeredCatalogId))
{
::WSCDeinstallProvider(&pProtoInfo[i].ProviderId, &nError);
}
}
// 移除分层协议
::WSCDeinstallProvider(&ProviderGuid, &nError);
}
return TRUE;
}
void main(int argc, char *argv[])
{
if(argc==2)
{
if(strcmp(argv , "-install")==0)
{
TCHAR szPathName[256];
TCHAR* p;
if(::GetFullPathName(L"LSP.dll", 256, szPathName, &p) != 0)
{
if(InstallProvider(szPathName))
{
printf(" Install successully. \n");
return;
}
}
printf(" Install failed. \n");
return;
}
else if(strcmp(argv ,"-remove")==0)
{
if(RemoveProvider())
printf(" Deinstall successully. \n");
else
printf(" Deinstall failed. \n");
return;
}
}
printf(" Usage: Instlsp [ -install │ -remove ] \n");
}
LSP实现代码如下
[cpp]
//////////////////////////////////////////////////
// LSP.cpp文件
// 声明要使用UNICODE字符串
#define UNICODE
#define _UNICODE
#include <Winsock2.h>
#include <Ws2spi.h>
#include <Windows.h>
#include <tchar.h>
#include "Debug.h"
#pragma comment(lib, "Ws2_32.lib")
WSPUPCALLTABLE g_pUpCallTable; // 上层函数列表。如果LSP创建了自己的伪句柄,才使用这个函数列表
WSPPROC_TABLE g_NextProcTable; // 下层函数列表
TCHAR g_szCurrentApp[MAX_PATH]; // 当前调用本DLL的程序的名称
BOOL APIENTRY DllMain( HANDLE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
{
// 取得主模块的名称
::GetModuleFileName(NULL, g_szCurrentApp, MAX_PATH);
}
break;
}
return TRUE;
}
LPWSAPROTOCOL_INFOW GetProvider(LPINT lpnTotalProtocols)
{
DWORD dwSize = 0;
int nError;
LPWSAPROTOCOL_INFOW pProtoInfo = NULL;
// 取得需要的长度
if(::WSCEnumProtocols(NULL, pProtoInfo, &dwSize, &nError) == SOCKET_ERROR)
{
if(nError != WSAENOBUFS)
return NULL;
}
pProtoInfo = (LPWSAPROTOCOL_INFOW)::GlobalAlloc(GPTR, dwSize);
*lpnTotalProtocols = ::WSCEnumProtocols(NULL, pProtoInfo, &dwSize, &nError);
return pProtoInfo;
}
void FreeProvider(LPWSAPROTOCOL_INFOW pProtoInfo)
{
::GlobalFree(pProtoInfo);
}
int WSPAPI WSPSendTo(
SOCKET s,
LPWSABUF lpBuffers,
DWORD dwBufferCount,
LPDWORD lpNumberOfBytesSent,
DWORD dwFlags,
const struct sockaddr FAR * lpTo,
int iTolen,
LPWSAOVERLAPPED lpOverlapped,
LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine,
LPWSATHREADID lpThreadId,
LPINT lpErrno
)
{
ODS1(L" query send to... %s", g_szCurrentApp);
// 拒绝所有目的端口为4567的UDP封包
SOCKADDR_IN sa = *(SOCKADDR_IN*)lpTo;
if(sa.sin_port == htons(4567))
{