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

📄 adinfo.c

📁 Windows XP下的抓包程序实现
💻 C
📖 第 1 页 / 共 5 页
字号:
		{
			
			// Allocate a buffer to get the vendor description from the driver
			OidData = GlobalAllocPtr(GMEM_MOVEABLE | GMEM_ZEROINIT,512);
			if (OidData == NULL) 
			{
				TRACE_PRINT("PacketAddAdapterNPF: GlobalAlloc Failed allocating the buffer for the OID request to obtain the NIC description. Returning."); 				
				PacketCloseAdapter(adapter);
				ReleaseMutex(g_AdaptersInfoMutex);
				TRACE_EXIT("PacketAddAdapterNPF");
				return FALSE;
			}
		}
		else
		{
			TRACE_PRINT("NPF Adapter not available, do not add it to the global list");
			// We are not able to open this adapter. Skip to the next one.
			ReleaseMutex(g_AdaptersInfoMutex);
			TRACE_EXIT("AddAdapter");
			return FALSE;
		}			
	}

	
	//
	// PacketOpenAdapter was succesful. Consider this a valid adapter and allocate an entry for it
	// In the adapter list
	//
	
	TmpAdInfo = GlobalAllocPtr(GMEM_MOVEABLE | GMEM_ZEROINIT, sizeof(ADAPTER_INFO));
	if (TmpAdInfo == NULL) 
	{
		TRACE_PRINT("AddAdapter: GlobalAlloc Failed");
	
		if(flags != INFO_FLAG_DONT_EXPORT)
		{ 
	 		TRACE_PRINT("AddAdapter: GlobalAlloc Failed allocating the buffer for the AdInfo to be added to the global list. Returning.");
			if (OidData != NULL) GlobalFreePtr(OidData);
			PacketCloseAdapter(adapter);
		}		
		
		ReleaseMutex(g_AdaptersInfoMutex);
 		TRACE_EXIT("AddAdapter");
		return FALSE;
	}
	
	// Copy the device name
	strncpy(TmpAdInfo->Name, AdName, sizeof(TmpAdInfo->Name)/ sizeof(TmpAdInfo->Name[0]) - 1);

	//we do not need to terminate the string TmpAdInfo->Name, since we have left a char at the end, and
	//the memory for TmpAdInfo was zeroed upon allocation

	if(flags != INFO_FLAG_DONT_EXPORT)
	{
		// Retrieve the adapter description querying the NIC driver
		OidData->Oid = OID_GEN_VENDOR_DESCRIPTION;
		OidData->Length = 256;
		ZeroMemory(OidData->Data, 256);
		
		Status = PacketRequest(adapter, FALSE, OidData);
		
		if(Status==0 || ((char*)OidData->Data)[0]==0)
		{
			TRACE_PRINT("AddAdapter: unable to get a valid adapter description from the NIC driver");
		}
		
		TRACE_PRINT1("Adapter Description = %s",OidData->Data);
		
		// Copy the description
		strncpy(TmpAdInfo->Description, (PCHAR)OidData->Data, sizeof(TmpAdInfo->Description)/ sizeof(TmpAdInfo->Description[0]) - 1);
		//we do not need to terminate the string TmpAdInfo->Description, since we have left a char at the end, and
		//the memory for TmpAdInfo was zeroed upon allocation
		
		Status = PacketGetLinkLayerFromRegistry(adapter, &(TmpAdInfo->LinkLayer));

		if (Status == FALSE)
		{
			TRACE_PRINT("AddAdapter: PacketGetLinkLayerFromRegistry failed. Returning.");
			PacketCloseAdapter(adapter);
			GlobalFreePtr(OidData);
			GlobalFreePtr(TmpAdInfo);
			ReleaseMutex(g_AdaptersInfoMutex);
			TRACE_EXIT("AddAdapter");
			return FALSE;
		}
		
		// Retrieve the adapter MAC address querying the NIC driver
		OidData->Oid = OID_802_3_CURRENT_ADDRESS;	// XXX At the moment only Ethernet is supported.
													// Waiting a patch to support other Link Layers
		OidData->Length = 256;
		ZeroMemory(OidData->Data, 256);
		
		TRACE_PRINT("Trying to obtain the MAC address for the NIC...");
		Status = PacketRequest(adapter, FALSE, OidData);
		if(Status)
		{
			memcpy(TmpAdInfo->MacAddress, OidData->Data, 6);
			TmpAdInfo->MacAddressLen = 6;

			TRACE_PRINT6("Successfully obtained the MAC address, it's "
				"%.02x:%.02x:%.02x:%.02x:%.02x:%.02x",
				TmpAdInfo->MacAddress[0],
				TmpAdInfo->MacAddress[1],
				TmpAdInfo->MacAddress[2],
				TmpAdInfo->MacAddress[3],
				TmpAdInfo->MacAddress[4],
				TmpAdInfo->MacAddress[5]);


		}
		else
		{
			TRACE_PRINT("Failed obtaining the MAC address, put a fake 00:00:00:00:00:00");
			memset(TmpAdInfo->MacAddress, 0, 6);
			TmpAdInfo->MacAddressLen = 0;
		}
		
		// Retrieve IP addresses
		TmpAdInfo->NetworkAddresses = GlobalAllocPtr(GMEM_MOVEABLE | GMEM_ZEROINIT, MAX_NETWORK_ADDRESSES * sizeof(npf_if_addr));
		if (TmpAdInfo->NetworkAddresses == NULL) {
			TRACE_PRINT("AddAdapter: GlobalAlloc Failed to allocate the buffer for the IP addresses in the AdInfo structure. Returning.");
			PacketCloseAdapter(adapter);
			GlobalFreePtr(OidData);
			GlobalFreePtr(TmpAdInfo);
			ReleaseMutex(g_AdaptersInfoMutex);
			TRACE_EXIT("AddAdapter");
			return FALSE;
		}
		
		TmpAdInfo->NNetworkAddresses = MAX_NETWORK_ADDRESSES;
		if(!PacketGetAddressesFromRegistry(TmpAdInfo->Name, TmpAdInfo->NetworkAddresses, (long*)&TmpAdInfo->NNetworkAddresses))
		{
#ifdef HAVE_IPHELPER_API
			// Try to see if the interface has some IPv6 addresses
			TmpAdInfo->NNetworkAddresses = 0; // We have no addresses because PacketGetAddressesFromRegistry() failed
			
			if(!PacketAddIP6Addresses(TmpAdInfo))
			{
#endif // HAVE_IPHELPER_API
				GlobalFreePtr(TmpAdInfo->NetworkAddresses);
				TmpAdInfo->NetworkAddresses = NULL;
				TmpAdInfo->NNetworkAddresses = 0;
#ifdef HAVE_IPHELPER_API
			}
#endif // HAVE_IPHELPER_API
		}
		
#ifdef HAVE_IPHELPER_API
		// Now Add IPv6 Addresses
		PacketAddIP6Addresses(TmpAdInfo);
#endif // HAVE_IPHELPER_API
		
		TmpAdInfo->Flags = INFO_FLAG_NDIS_ADAPTER;	// NdisWan adapters are not exported by the NPF driver,
													// therefore it's impossible to see them here
		
		// Free storage
		PacketCloseAdapter(adapter);
		GlobalFreePtr(OidData);
	}
	else
	{
		// Write in the flags that this adapter is firewire
		// This will block it in all successive calls
		TmpAdInfo->Flags = INFO_FLAG_DONT_EXPORT;
	}
	
	// Update the AdaptersInfo list
	TmpAdInfo->Next = g_AdaptersInfoList;
	g_AdaptersInfoList = TmpAdInfo;
	
	ReleaseMutex(g_AdaptersInfoMutex);

	TRACE_EXIT("AddAdapter");
	return TRUE;
}


/*!
  \brief Updates the list of the adapters querying the registry.
  \return If the function succeeds, the return value is nonzero.

  This function populates the list of adapter descriptions, retrieving the information from the registry. 
*/
static BOOLEAN PacketGetAdaptersNPF()
{
	HKEY		LinkageKey,AdapKey, OneAdapKey;
	DWORD		RegKeySize=0;
	LONG		Status;
	ULONG		Result;
	INT			i;
	DWORD		dim;
	DWORD		RegType;
	WCHAR		TName[256];
	CHAR		TAName[256];
	TCHAR		AdapName[256];
	CHAR		*TcpBindingsMultiString;
	UINT		FireWireFlag;
//  
//	Old registry based WinPcap names
//
//	CHAR		npfCompleteDriverPrefix[MAX_WINPCAP_KEY_CHARS];
//	UINT		RegQueryLen;

	CHAR		npfCompleteDriverPrefix[MAX_WINPCAP_KEY_CHARS] = NPF_DRIVER_COMPLETE_DEVICE_PREFIX;
	CHAR		DeviceGuidName[256];

	TRACE_ENTER("PacketGetAdaptersNPF");
	
//  
//	Old registry based WinPcap names
//
//	// Get device prefixes from the registry
//	RegQueryLen = sizeof(npfCompleteDriverPrefix)/sizeof(npfCompleteDriverPrefix[0]);
//	
//	if (QueryWinPcapRegistryStringA(NPF_DRIVER_COMPLETE_DEVICE_PREFIX_REG_KEY, npfCompleteDriverPrefix, &RegQueryLen, NPF_DRIVER_COMPLETE_DEVICE_PREFIX) == FALSE && RegQueryLen == 0)
//		return FALSE;

	Status=RegOpenKeyEx(HKEY_LOCAL_MACHINE,
		TEXT("SYSTEM\\CurrentControlSet\\Control\\Class\\{4D36E972-E325-11CE-BFC1-08002BE10318}"),
		0,
		KEY_READ,
		&AdapKey);
	
	if ( Status != ERROR_SUCCESS ){
		TRACE_PRINT("PacketGetAdaptersNPF: RegOpenKeyEx ( Class\\{networkclassguid} ) Failed");
		goto tcpip_linkage;
	}

	i = 0;

	TRACE_PRINT("PacketGetAdaptersNPF: RegOpenKeyEx ( Class\\{networkclassguid} ) was successful");
	TRACE_PRINT("PacketGetAdaptersNPF: Cycling through the adapters in the registry:");

	// 
	// Cycle through the entries inside the {4D36E972-E325-11CE-BFC1-08002BE10318} key
	// To get the names of the adapters
	//
	while((Result = RegEnumKey(AdapKey, i, AdapName, sizeof(AdapName)/2)) == ERROR_SUCCESS)
	{
		i++;
		FireWireFlag = 0;

		// 
		// Get the adapter name from the registry key
		//
		Status=RegOpenKeyEx(AdapKey, AdapName, 0, KEY_READ, &OneAdapKey);
		if ( Status != ERROR_SUCCESS )
		{
			TRACE_PRINT1("%d) RegOpenKey( OneAdapKey ) Failed, skipping the adapter.",i);
			continue;			
		}

		//
		//
		// Check if this is a FireWire adapter, looking for "1394" in its ComponentId string. 
		// We prevent listing FireWire adapters because winpcap can open them, but their interface
		// with the OS is broken and they can cause blue screens.
		//
		dim = sizeof(TName);
        Status = RegQueryValueEx(OneAdapKey, 
			TEXT("ComponentId"),
			NULL,
			NULL,
			(PBYTE)TName, 
			&dim);

		if(Status == ERROR_SUCCESS)
		{
			if(IsFireWire(TName))
			{
				FireWireFlag = INFO_FLAG_DONT_EXPORT;
			}
		}

		Status=RegOpenKeyEx(OneAdapKey, TEXT("Linkage"), 0, KEY_READ, &LinkageKey);
		if (Status != ERROR_SUCCESS)
		{
			RegCloseKey(OneAdapKey);
			TRACE_PRINT1("%d) RegOpenKeyEx ( LinkageKey ) Failed, skipping the adapter",i);
			continue;
		}
		
		dim = sizeof(DeviceGuidName);
        Status=RegQueryValueExA(LinkageKey, 
			"Export", 
			NULL, 
			NULL, 
			(PBYTE)DeviceGuidName, 
			&dim);

		if(Status != ERROR_SUCCESS)
		{
			RegCloseKey(OneAdapKey);
			RegCloseKey(LinkageKey);
			TRACE_PRINT1("%d) Name = SKIPPED (error reading the key)", i);
			continue;
		}

		if (strlen(DeviceGuidName) >= strlen("\\Device\\"))
		{
			// Put the \Device\NPF_ string at the beginning of the name
			StringCchPrintfA(TAName, sizeof(TAName), "%s%s",
			npfCompleteDriverPrefix,
			DeviceGuidName + strlen("\\Device\\"));
		}
		else
			continue;

		//terminate the string, just in case
		TAName[sizeof(TAName) - 1] = '\0';

		TRACE_PRINT2("%d) Successfully retrieved info for adapter %s, trying to add it to the global list...", i, TAName);
		// If the adapter is valid, add it to the list.
		PacketAddAdapterNPF(TAName, FireWireFlag);

		RegCloseKey(OneAdapKey);
		RegCloseKey(LinkageKey);
		
	} // while enum reg keys

	RegCloseKey(AdapKey);

tcpip_linkage:
	//
	// no adapters were found under {4D36E972-E325-11CE-BFC1-08002BE10318}. This means with great probability
	// that we are under Windows NT 4, so we try to look under the tcpip bindings.
	//
	
	TRACE_PRINT("Adapters not found under SYSTEM\\CurrentControlSet\\Control\\Class. Using the TCP/IP bindings.");
		
	Status = RegOpenKeyEx(HKEY_LOCAL_MACHINE,
		TEXT("SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Linkage"),
		0,
		KEY_READ,
		&LinkageKey);

	if (Status == ERROR_SUCCESS)
	{
		// Retrieve the length of th binde key
		// This key contains the name of the devices as \device\foo
		//in ASCII, separated by a single '\0'. The list is terminated
		//by another '\0'
		Status=RegQueryValueExA(LinkageKey,
			"bind",
			NULL,
			&RegType,
			NULL,
			&RegKeySize);

		// Allocate the buffer
		TcpBindingsMultiString = GlobalAllocPtr(GMEM_MOVEABLE | GMEM_ZEROINIT, RegKeySize + 2);

		if (TcpBindingsMultiString == NULL)
		{
			TRACE_PRINT("GlobalAlloc failed allocating memory for the registry key, returning.");
			TRACE_EXIT("PacketGetAdaptersNPF");
			return FALSE;
		}
		
		// Query the key again to get its content		
		Status = RegQueryValueExA(LinkageKey,
			"bind",
			NULL,
			&RegType,
			(LPBYTE)TcpBindingsMultiString,
			&RegKeySize);
		
		RegCloseKey(LinkageKey);

		// Scan the buffer with the device names
		for(i = 0;;)
		{
			if (TcpBindingsMultiString[i] == '\0')
				break;
			
			StringCchPrintfA(TAName, sizeof(TAName), "%s%s", 
				npfCompleteDriverPrefix,
				TcpBindingsMultiString + i + strlen("\\Device\\"));

			//
			// TODO GV: this cast to avoid a compilation warning is
			//			actually stupid. We shouls check not to go over the buffer boundary!
			// 
			i += (INT)strlen(&TcpBindingsMultiString[i]) + 1;

			TRACE_PRINT1("Successfully retrieved info for adapter %s, trying to add it to the global list...", TAName);

			
			// If the adapter is valid, add it to the list.
			PacketAddAdapterNPF(TAName, 0);
		}
	
 		GlobalFreePtr(TcpBindingsMultiString);
	}
	
	else{
#ifdef _WINNT4
		MessageBox(NULL,TEXT("Can not find TCP/IP bindings.\nIn order to run the packet capture driver you must install TCP/IP."),szWindowTitle,MB_OK);
		TRACE_PRINT("Cannot find the TCP/IP bindings on NT4, no adapters.");
		TRACE_EXIT("PacketGetAdaptersNPF");
		return FALSE;
#endif		
	}
	
	TRACE_EXIT("PacketGetAdaptersNPF");
	return TRUE;
}

#ifdef HAVE_AIRPCAP_API
/*!
  \brief Add an airpcap adapter to the adapters info list, gathering information from the airpcap dll
  \param name Name of the adapter.
  \param description description of the adapter.
  \return If the function succeeds, the return value is nonzero.
*/
static BOOLEAN PacketAddAdapterAirpcap(PCHAR name, PCHAR description)
{
	//this function should acquire the g_AdaptersInfoMutex, since it's NOT called with an ADAPTER_INFO as parameter
	CHAR ebuf[AIRPCAP_ERRBUF_SIZE];
	PADAPTER_INFO TmpAdInfo;
	PAirpcapHandle AirpcapAdapter;
	BOOL GllRes;
	AirpcapLinkType AirpcapLinkLayer;
	BOOLEAN Result = TRUE;

	TRACE_ENTER("PacketAddAdapterAirpcap");
	//XXX what about checking if the adapter already exists???
	
	WaitForSingleObject(g_AdaptersInfoMutex, INFINITE);

	do
	{

⌨️ 快捷键说明

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