void FillNetwork5Tuple( _In_ const FWPS_INCOMING_VALUES* inFixedValues, _In_ ADDRESS_FAMILY addressFamily, _Inout_ TL_INSPECT_PENDED_PACKET* packet ) { UINT localAddrIndex; UINT remoteAddrIndex; UINT localPortIndex; UINT remotePortIndex; UINT protocolIndex; GetNetwork5TupleIndexesForLayer( inFixedValues->layerId, &localAddrIndex, &remoteAddrIndex, &localPortIndex, &remotePortIndex, &protocolIndex ); if (addressFamily == AF_INET) { packet->ipv4LocalAddr = RtlUlongByteSwap( /* host-order -> network-order conversion */ inFixedValues->incomingValue[localAddrIndex].value.uint32 ); packet->ipv4RemoteAddr = RtlUlongByteSwap( /* host-order -> network-order conversion */ inFixedValues->incomingValue[remoteAddrIndex].value.uint32 ); } else { RtlCopyMemory( (UINT8*)&packet->localAddr, inFixedValues->incomingValue[localAddrIndex].value.byteArray16, sizeof(FWP_BYTE_ARRAY16) ); RtlCopyMemory( (UINT8*)&packet->remoteAddr, inFixedValues->incomingValue[remoteAddrIndex].value.byteArray16, sizeof(FWP_BYTE_ARRAY16) ); } packet->localPort = RtlUshortByteSwap( inFixedValues->incomingValue[localPortIndex].value.uint16 ); packet->remotePort = RtlUshortByteSwap( inFixedValues->incomingValue[remotePortIndex].value.uint16 ); packet->protocol = inFixedValues->incomingValue[protocolIndex].value.uint8; return; }
// Little Endian version ONLY static UINT32 ToeplitsHash(const PHASH_CALC_SG_BUF_ENTRY sgBuff, int sgEntriesNum, PCCHAR fullKey) { #define TOEPLITZ_MAX_BIT_NUM (7) #define TOEPLITZ_BYTE_HAS_BIT(byte, bit) ((byte) & (1 << (TOEPLITZ_MAX_BIT_NUM - (bit)))) #define TOEPLITZ_BYTE_BIT_STATE(byte, bit) (((byte) >> (TOEPLITZ_MAX_BIT_NUM - (bit))) & 1) UINT32 firstKeyWord, res = 0; UINT byte, bit; PHASH_CALC_SG_BUF_ENTRY sgEntry; PCCHAR next_key_byte = fullKey + sizeof(firstKeyWord); firstKeyWord = RtlUlongByteSwap(*(UINT32*)fullKey); for(sgEntry = sgBuff; sgEntry < sgBuff + sgEntriesNum; ++sgEntry) { for (byte = 0; byte < sgEntry->chunkLen; ++byte) { for (bit = 0; bit <= TOEPLITZ_MAX_BIT_NUM; ++bit) { if (TOEPLITZ_BYTE_HAS_BIT(sgEntry->chunkPtr[byte], bit)) { res ^= firstKeyWord; } firstKeyWord = (firstKeyWord << 1) | TOEPLITZ_BYTE_BIT_STATE(*next_key_byte, bit); } ++next_key_byte; } } return res; #undef TOEPLITZ_BYTE_HAS_BIT #undef TOEPLITZ_BYTE_BIT_STATE #undef TOEPLITZ_MAX_BIT_NUM }
/************************************************************************* * SwapPlong@8 (MAPI32.47) * * Swap the bytes in a ULONG array. * * PARAMS * lpData [O] Array to swap bytes in * ulLen [I] Number of ULONG element to swap the bytes of * * RETURNS * Nothing. */ VOID WINAPI SwapPlong(PULONG lpData, ULONG ulLen) { ULONG i; for (i = 0; i < ulLen; i++) lpData[i] = RtlUlongByteSwap(lpData[i]); }
NTSTATUS TLInspectLoadConfig( _In_ const WDFKEY key ) { NTSTATUS status; DECLARE_CONST_UNICODE_STRING(valueName, L"RemoteAddressToInspect"); DECLARE_UNICODE_STRING_SIZE(value, INET6_ADDRSTRLEN); status = WdfRegistryQueryUnicodeString(key, &valueName, NULL, &value); if (NT_SUCCESS(status)) { PWSTR terminator; // Defensively null-terminate the string value.Length = min(value.Length, value.MaximumLength - sizeof(WCHAR)); value.Buffer[value.Length/sizeof(WCHAR)] = UNICODE_NULL; status = RtlIpv4StringToAddressW( value.Buffer, TRUE, &terminator, &remoteAddrStorageV4 ); if (NT_SUCCESS(status)) { remoteAddrStorageV4.S_un.S_addr = RtlUlongByteSwap(remoteAddrStorageV4.S_un.S_addr); configInspectRemoteAddrV4 = &remoteAddrStorageV4.S_un.S_un_b.s_b1; } else { status = RtlIpv6StringToAddressW( value.Buffer, &terminator, &remoteAddrStorageV6 ); if (NT_SUCCESS(status)) { configInspectRemoteAddrV6 = (UINT8*)(&remoteAddrStorageV6.u.Byte[0]); } } } return status; }
NTSTATUS Ext_StartScsiRequest(_In_ PVOID ExtContext, _In_ PEVHD_EXT_SCSI_PACKET pExtPacket) { UNREFERENCED_PARAMETER(ExtContext); UNREFERENCED_PARAMETER(pExtPacket); NTSTATUS Status = STATUS_SUCCESS; UCHAR opCode = pExtPacket->Srb->Cdb[0]; PMDL pMdl = pExtPacket->pMdl; PEXTENSION_CONTEXT Context = ExtContext; USHORT wSectors = RtlUshortByteSwap(*(USHORT *)&(pExtPacket->Srb->Cdb[7])); ULONG dwSectorOffset = RtlUlongByteSwap(*(ULONG *)&(pExtPacket->Srb->Cdb[2])); switch (opCode) { case SCSI_OP_CODE_WRITE_6: case SCSI_OP_CODE_WRITE_10: case SCSI_OP_CODE_WRITE_12: case SCSI_OP_CODE_WRITE_16: if (Context->pCipherEngine) { EXTLOG(LL_VERBOSE, "Write request: %X blocks starting from %X\n", wSectors, dwSectorOffset); pExtPacket->pMdl = Ext_AllocateInnerMdl(pMdl); Status = Ext_CryptBlocks(Context, pMdl, pExtPacket->pMdl, pExtPacket->Srb->DataTransferLength, dwSectorOffset, TRUE); pMdl = pExtPacket->pMdl; if (pMdl->MdlFlags & MDL_MAPPED_TO_SYSTEM_VA) MmUnmapLockedPages(pMdl->MappedSystemVa, pMdl); } break; case SCSI_OP_CODE_READ_6: case SCSI_OP_CODE_READ_10: case SCSI_OP_CODE_READ_12: case SCSI_OP_CODE_READ_16: if (Context->pCipherEngine) { EXTLOG(LL_VERBOSE, "Read request: %X blocks starting from %X\n", wSectors, dwSectorOffset); } break; } return Status; }
NTSTATUS Ext_CompleteScsiRequest(_In_ PVOID ExtContext, _In_ PEVHD_EXT_SCSI_PACKET pExtPacket, _In_ NTSTATUS Status) { UCHAR opCode = pExtPacket->Srb->Cdb[0]; PMDL pMdl = pExtPacket->pMdl; PEXTENSION_CONTEXT Context = ExtContext; USHORT wSectors = RtlUshortByteSwap(*(USHORT *)&(pExtPacket->Srb->Cdb[7])); ULONG dwSectorOffset = RtlUlongByteSwap(*(ULONG *)&(pExtPacket->Srb->Cdb[2])); switch (opCode) { case SCSI_OP_CODE_READ_6: case SCSI_OP_CODE_READ_10: case SCSI_OP_CODE_READ_12: case SCSI_OP_CODE_READ_16: if (Context->pCipherEngine) { EXTLOG(LL_VERBOSE, "Read request completed: %X blocks starting from %X\n", wSectors, dwSectorOffset); if (NT_SUCCESS(Status)) { Ext_CryptBlocks(Context, pMdl, pMdl, pExtPacket->Srb->DataTransferLength, dwSectorOffset, FALSE); } } break; case SCSI_OP_CODE_WRITE_6: case SCSI_OP_CODE_WRITE_10: case SCSI_OP_CODE_WRITE_12: case SCSI_OP_CODE_WRITE_16: if (Context->pCipherEngine) { EXTLOG(LL_VERBOSE, "Write request completed: %X blocks starting from %X\n", wSectors, dwSectorOffset); pExtPacket->pMdl = Ext_FreeInnerMdl(pExtPacket->pMdl); } break; } return Status; }
static inline DWORD get_be_dword(const void *p) { return RtlUlongByteSwap(*(const DWORD*)p); }
void DDProxyLoadConfig( IN PUNICODE_STRING registryPath ) { NTSTATUS status; OBJECT_ATTRIBUTES objectAttributes; HANDLE registryKey; UNICODE_STRING valueName; UCHAR regValueStorage[sizeof(KEY_VALUE_PARTIAL_INFORMATION) + INET6_ADDRSTRLEN * sizeof(WCHAR)]; KEY_VALUE_PARTIAL_INFORMATION* regValue = (KEY_VALUE_PARTIAL_INFORMATION*)regValueStorage; ULONG resultLength; InitializeObjectAttributes( &objectAttributes, registryPath, OBJ_CASE_INSENSITIVE | OBJ_KERNEL_HANDLE, NULL, NULL ); status = ZwOpenKey( ®istryKey, KEY_READ, &objectAttributes ); if (NT_SUCCESS(status)) { RtlInitUnicodeString( &valueName, L"InspectUdp" ); status = ZwQueryValueKey( registryKey, &valueName, KeyValuePartialInformation, regValue, sizeof(regValueStorage), &resultLength ); if (NT_SUCCESS(status)) { if ((*(PULONG)regValue->Data) != 0) { configInspectUdp = TRUE; } else { configInspectUdp = FALSE; } } RtlInitUnicodeString( &valueName, L"DestinationAddressToIntercept" ); status = ZwQueryValueKey( registryKey, &valueName, KeyValuePartialInformation, regValue, sizeof(regValueStorage), &resultLength ); if (NT_SUCCESS(status)) { PWSTR terminator; status = RtlIpv4StringToAddressW( (PCWSTR)(regValue->Data), TRUE, &terminator, &destAddrStorageV4 ); if (NT_SUCCESS(status)) { destAddrStorageV4.S_un.S_addr = RtlUlongByteSwap(destAddrStorageV4.S_un.S_addr); configInspectDestAddrV4 = &destAddrStorageV4.S_un.S_un_b.s_b1; } else { status = RtlIpv6StringToAddressW( (PCWSTR)(regValue->Data), &terminator, &destAddrStorageV6 ); if (NT_SUCCESS(status)) { configInspectDestAddrV6 = (UINT8*)(&destAddrStorageV6.u.Byte[0]); } } } RtlInitUnicodeString( &valueName, L"DestinationPortToIntercept" ); status = ZwQueryValueKey( registryKey, &valueName, KeyValuePartialInformation, regValue, sizeof(regValueStorage), &resultLength ); if (NT_SUCCESS(status)) { configInspectDestPort = (USHORT)(*(PULONG)regValue->Data); } RtlInitUnicodeString( &valueName, L"NewDestinationAddress" ); status = ZwQueryValueKey( registryKey, &valueName, KeyValuePartialInformation, regValue, sizeof(regValueStorage), &resultLength ); if (NT_SUCCESS(status)) { PWSTR terminator; status = RtlIpv4StringToAddressW( (PCWSTR)(regValue->Data), TRUE, &terminator, &newDestAddrStorageV4 ); if (NT_SUCCESS(status)) { newDestAddrStorageV4.S_un.S_addr = RtlUlongByteSwap(newDestAddrStorageV4.S_un.S_addr); configNewDestAddrV4 = &newDestAddrStorageV4.S_un.S_un_b.s_b1; } else { status = RtlIpv6StringToAddressW( (PCWSTR)(regValue->Data), &terminator, &newDestAddrStorageV6 ); if (NT_SUCCESS(status)) { configNewDestAddrV6 = (UINT8*)(&newDestAddrStorageV6.u.Byte[0]); } } } RtlInitUnicodeString( &valueName, L"NewDestinationPort" ); status = ZwQueryValueKey( registryKey, &valueName, KeyValuePartialInformation, regValue, sizeof(regValueStorage), &resultLength ); if (NT_SUCCESS(status)) { configNewDestPort = (USHORT)(*(PULONG)regValue->Data); } ZwClose(registryKey); } }
VOID PrintFtlPkt( IN char *strPrefix, IN FLT_PKT* pFltPkt, IN ULONG uNewIp, IN BOOLEAN bOut ) { TIME_FIELDS TimeFields; char Message[255]; char MessagePart[30]; LARGE_INTEGER time; KeQuerySystemTime(&time); ExSystemTimeToLocalTime(&time, &time); RtlTimeToTimeFields(&time, &TimeFields); RtlStringCbPrintfA(Message, sizeof(Message), "%02d:%02d:%02d.%03d ", TimeFields.Hour, TimeFields.Minute, TimeFields.Second, TimeFields.Milliseconds); if (!bOut) { RtlStringCbCatA(Message, sizeof(Message), "IN "); } else { RtlStringCbCatA(Message, sizeof(Message), "OUT "); } RtlStringCbCatA(Message, sizeof(Message), strPrefix); RtlStringCbCatA(Message, sizeof(Message), " "); if (NULL == pFltPkt->pEth) { goto out; } RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), "%02x-%02x-%02x-%02x-%02x-%02x", pFltPkt->pEth->ether_src[0], pFltPkt->pEth->ether_src[1], pFltPkt->pEth->ether_src[2], pFltPkt->pEth->ether_src[3], pFltPkt->pEth->ether_src[4], pFltPkt->pEth->ether_src[5]); RtlStringCbCatA(Message, sizeof(Message), MessagePart); RtlStringCbCatA(Message, sizeof(Message), "->"); RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), "%02x-%02x-%02x-%02x-%02x-%02x", pFltPkt->pEth->ether_dst[0], pFltPkt->pEth->ether_dst[1], pFltPkt->pEth->ether_dst[2], pFltPkt->pEth->ether_dst[3], pFltPkt->pEth->ether_dst[4], pFltPkt->pEth->ether_dst[5]); RtlStringCbCatA(Message, sizeof(Message), MessagePart); switch (pFltPkt->pEth->ether_type) { case ETHERNET_TYPE_ARP_NET: RtlStringCbCatA(Message, sizeof(Message), " ARP "); if (NULL == pFltPkt->pArp) goto out; if (ARP_REQUEST_CODE == pFltPkt->pArp->ea_hdr.ar_op) { RtlStringCbCatA(Message, sizeof(Message), "Request "); } else if (pFltPkt->pArp->ea_hdr.ar_op == ARP_REPLY_CODE) { RtlStringCbCatA(Message, sizeof(Message), "Reply "); } RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), "%d.%d.%d.%d", pFltPkt->pArp->arp_spa[0], pFltPkt->pArp->arp_spa[1], pFltPkt->pArp->arp_spa[2], pFltPkt->pArp->arp_spa[3]); RtlStringCbCatA(Message, sizeof(Message), MessagePart); RtlStringCbCatA(Message, sizeof(Message), "->"); PRINT_IP(MessagePart, pFltPkt->pArp->arp_tpa); RtlStringCbCatA(Message, sizeof(Message), MessagePart); break; case ETHERNET_TYPE_IP_NET: RtlStringCbCatA(Message, sizeof(Message), " IP "); if (NULL == pFltPkt->pIp) goto out; RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), "ID %04x ", RtlUshortByteSwap(pFltPkt->pIp->ip_id)); RtlStringCbCatA(Message, sizeof(Message), MessagePart); PRINT_IP(MessagePart, &pFltPkt->pIp->ip_src); RtlStringCbCatA(Message, sizeof(Message), MessagePart); if (uNewIp && bOut) { RtlStringCbCatA(Message, sizeof(Message), "["); PRINT_IP(MessagePart, &uNewIp); RtlStringCbCatA(Message, sizeof(Message), MessagePart); RtlStringCbCatA(Message, sizeof(Message), "]"); } RtlStringCbCatA(Message, sizeof(Message), "->"); PRINT_IP(MessagePart, &pFltPkt->pIp->ip_dst); RtlStringCbCatA(Message, sizeof(Message), MessagePart); if (uNewIp && !bOut) { RtlStringCbCatA(Message, sizeof(Message), "["); PRINT_IP(MessagePart, &uNewIp); RtlStringCbCatA(Message, sizeof(Message), MessagePart); RtlStringCbCatA(Message, sizeof(Message), "]"); } switch (pFltPkt->pIp->ip_proto) { case IPPROTO_TCP: RtlStringCbCatA(Message, sizeof(Message), " TCP"); break; case IPPROTO_ICMP: RtlStringCbCatA(Message, sizeof(Message), " ICMP"); break; case IPPROTO_UDP: RtlStringCbCatA(Message, sizeof(Message), " UDP"); break; default: RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), " proto=%04x", pFltPkt->pIp->ip_proto); RtlStringCbCatA(Message, sizeof(Message), MessagePart); break; } if (pFltPkt->pTcp) { RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), " %d->%d ", RtlUshortByteSwap(pFltPkt->pTcp->th_sport), RtlUshortByteSwap(pFltPkt->pTcp->th_dport)); if (pFltPkt->pTcp->th_flags & TCP_FIN_FLAG) RtlStringCbCatA(MessagePart, sizeof(MessagePart), "F"); if (pFltPkt->pTcp->th_flags & TCP_SYN_FLAG) RtlStringCbCatA(MessagePart, sizeof(MessagePart), "S"); if (pFltPkt->pTcp->th_flags & TCP_RST_FLAG) RtlStringCbCatA(MessagePart, sizeof(MessagePart), "R"); if (pFltPkt->pTcp->th_flags & TCP_PSH_FLAG) RtlStringCbCatA(MessagePart, sizeof(MessagePart), "P"); if (pFltPkt->pTcp->th_flags & TCP_URG_FLAG) RtlStringCbCatA(MessagePart, sizeof(MessagePart), "U"); if (pFltPkt->pTcp->th_flags & TCP_ACK_FLAG) RtlStringCbCatA(MessagePart, sizeof(MessagePart), "A"); // https://tools.ietf.org/html/rfc3168 if (pFltPkt->pTcp->th_flags & TCP_ECE_FLAG) RtlStringCbCatA(MessagePart, sizeof(MessagePart), "E"); if (pFltPkt->pTcp->th_flags & TCP_CWR_FLAG) RtlStringCbCatA(MessagePart, sizeof(MessagePart), "C"); RtlStringCbCatA(Message, sizeof(Message), MessagePart); RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), " SEQ:%u", RtlUlongByteSwap(pFltPkt->pTcp->th_seq)); RtlStringCbCatA(Message, sizeof(Message), MessagePart); RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), " ACK:%u", RtlUlongByteSwap(pFltPkt->pTcp->th_ack)); } else if (pFltPkt->pUdp) { RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), " %d->%d", RtlUshortByteSwap(pFltPkt->pUdp->uh_sport), RtlUshortByteSwap(pFltPkt->pUdp->uh_dport)); } else if (pFltPkt->pIcmp) { RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), " %d", RtlUshortByteSwap(pFltPkt->pIcmp->icmp_hun.idseq.id)); } else { MessagePart[0] = 0; } RtlStringCbCatA(Message, sizeof(Message), MessagePart); break; default: RtlStringCbPrintfA(MessagePart, sizeof(MessagePart), " UNK %04x", RtlUshortByteSwap(pFltPkt->pEth->ether_type)); RtlStringCbCatA(Message, sizeof(Message), MessagePart); break; } out: RtlStringCbCatA(Message, sizeof(Message), "\n"); DbgPrint(Message); return; }
NTSTATUS FileDiskQueryPnpID( __in PNDAS_LOGICALUNIT_EXTENSION LogicalUnitExtension, __in BUS_QUERY_ID_TYPE QueryType, __in ULONG Index, __inout PUNICODE_STRING UnicodeStringId) { static CONST WCHAR* HARDWARE_IDS[] = { NDASPORT_ENUMERATOR_GUID_PREFIX L"FileDisk", NDASPORT_ENUMERATOR_NAMED_PREFIX L"FileDisk", L"GenDisk", }; static CONST WCHAR* COMPATIBLE_IDS[] = { L"gendisk" }; WCHAR instanceId[20]; WCHAR* instanceIdList[] = { instanceId }; NTSTATUS status; PFILEDISK_EXTENSION fileDiskExtension; CONST WCHAR** idList; ULONG idListCount; fileDiskExtension = FileDiskGetExtension(LogicalUnitExtension); switch (QueryType) { case BusQueryDeviceID: idList = HARDWARE_IDS; idListCount = 1; break; case BusQueryHardwareIDs: idList = HARDWARE_IDS; idListCount = countof(HARDWARE_IDS); break; case BusQueryCompatibleIDs: idList = COMPATIBLE_IDS; idListCount = countof(COMPATIBLE_IDS); break; case BusQueryInstanceID: idList = (const WCHAR**) instanceIdList; idListCount = 1; status = RtlStringCchPrintfW( instanceId, countof(instanceId), L"%08X", RtlUlongByteSwap(fileDiskExtension->LogicalUnitAddress)); ASSERT(NT_SUCCESS(status)); break; case 4 /*BusQueryDeviceSerialNumber*/: default: return STATUS_NOT_SUPPORTED; } if (Index >= idListCount) { return STATUS_NO_MORE_ENTRIES; } status = RtlUnicodeStringCopyString( UnicodeStringId, idList[Index]); return status; }
PENDED_PACKET* AllocateAndInitializeStreamPendedPacket( IN const FWPS_INCOMING_VALUES0* inFixedValues, IN const FWPS_INCOMING_METADATA_VALUES0* inMetaValues, IN FLOW_DATA* flowContext, IN PLARGE_INTEGER localTime, IN OUT FWPS_STREAM_CALLOUT_IO_PACKET0* packet) { PENDED_PACKET *pendedPacket; UINT index = 0; SIZE_T bytesCopied; ASSERT(packet != NULL && packet->streamData != NULL); // pendedPacket gets deleted in FreePendedPacket #pragma warning( suppress : 803072 ) pendedPacket = ExAllocatePoolWithTag( NonPagedPool, sizeof(PENDED_PACKET), TAG_PENDEDPACKET); if (pendedPacket == NULL) { return NULL; } RtlZeroMemory(pendedPacket, sizeof(PENDED_PACKET)); pendedPacket->flags = packet->streamData->flags; if(pendedPacket->flags & FWPS_STREAM_FLAG_SEND) { index = FWPS_FIELD_STREAM_V4_IP_LOCAL_ADDRESS; pendedPacket->ipv4SrcAddr = RtlUlongByteSwap( /* host-order -> network-order conversion */ inFixedValues->incomingValue[index].value.uint32); index = FWPS_FIELD_STREAM_V4_IP_REMOTE_ADDRESS; pendedPacket->ipv4DstAddr = RtlUlongByteSwap( /* host-order -> network-order conversion */ inFixedValues->incomingValue[index].value.uint32); index = FWPS_FIELD_STREAM_V4_IP_LOCAL_PORT; pendedPacket->srcPort = inFixedValues->incomingValue[index].value.uint16; index = FWPS_FIELD_STREAM_V4_IP_REMOTE_PORT; pendedPacket->dstPort = inFixedValues->incomingValue[index].value.uint16; } else if(pendedPacket->flags & FWPS_STREAM_FLAG_RECEIVE) { index = FWPS_FIELD_STREAM_V4_IP_REMOTE_ADDRESS; pendedPacket->ipv4SrcAddr = RtlUlongByteSwap( /* host-order -> network-order conversion */ inFixedValues->incomingValue[index].value.uint32); index = FWPS_FIELD_STREAM_V4_IP_LOCAL_ADDRESS; pendedPacket->ipv4DstAddr = RtlUlongByteSwap( /* host-order -> network-order conversion */ inFixedValues->incomingValue[index].value.uint32); index = FWPS_FIELD_STREAM_V4_IP_REMOTE_PORT; pendedPacket->srcPort = inFixedValues->incomingValue[index].value.uint16; index = FWPS_FIELD_STREAM_V4_IP_LOCAL_PORT; pendedPacket->dstPort = inFixedValues->incomingValue[index].value.uint16; } pendedPacket->localTime.HighPart = localTime->HighPart; pendedPacket->localTime.LowPart = localTime->LowPart; myRtlTimeToSecondsSince1970(localTime, &pendedPacket->timestamp); // Closing packets are only created at flowDeleteFn pendedPacket->close = FALSE; // Protocol analyzers will change this value if needed pendedPacket->permitted = TRUE; pendedPacket->mdl = NULL; pendedPacket->dataLength = (ULONG) packet->streamData->dataLength; if(pendedPacket->dataLength > 0) { // data gets deleted in FreePendedPacket #pragma warning( suppress : 28197 ) pendedPacket->data = ExAllocatePoolWithTag( NonPagedPool, pendedPacket->dataLength, TAG_PENDEDPACKETDATA); if (pendedPacket->data == NULL) { FreePendedPacket(pendedPacket); return NULL; } RtlZeroMemory(pendedPacket->data, pendedPacket->dataLength); FwpsCopyStreamDataToBuffer0( packet->streamData, pendedPacket->data, pendedPacket->dataLength, &bytesCopied); } if(flowContext != NULL) { pendedPacket->flowContext = flowContext; } return pendedPacket; }
void TLInspectLoadConfig( IN PUNICODE_STRING registryPath ) { NTSTATUS status; OBJECT_ATTRIBUTES objectAttributes; UNICODE_STRING valueName; KEY_VALUE_PARTIAL_INFORMATION* regValue = (KEY_VALUE_PARTIAL_INFORMATION*)gRegValueStorage; ULONG resultLength; InitializeObjectAttributes( &objectAttributes, registryPath, OBJ_CASE_INSENSITIVE | OBJ_KERNEL_HANDLE, NULL, NULL ); status = ZwOpenKey( &gRegistryKey, KEY_READ, &objectAttributes ); if (NT_SUCCESS(status)) { RtlInitUnicodeString( &valueName, L"RemoteAddressToInspect" ); status = ZwQueryValueKey( gRegistryKey, &valueName, KeyValuePartialInformation, regValue, sizeof(gRegValueStorage), &resultLength ); if (NT_SUCCESS(status)) { PWSTR terminator; status = RtlIpv4StringToAddressW( (PCWSTR)(regValue->Data), TRUE, &terminator, &remoteAddrStorageV4 ); if (NT_SUCCESS(status)) { remoteAddrStorageV4.S_un.S_addr = RtlUlongByteSwap(remoteAddrStorageV4.S_un.S_addr); configInspectRemoteAddrV4 = &remoteAddrStorageV4.S_un.S_un_b.s_b1; } else { status = RtlIpv6StringToAddressW( (PCWSTR)(regValue->Data), &terminator, &remoteAddrStorageV6 ); if (NT_SUCCESS(status)) { configInspectRemoteAddrV6 = (UINT8*)(&remoteAddrStorageV6.u.Byte[0]); } } } } }
BOOLEAN IsMatchingConnectPacket( _In_ const FWPS_INCOMING_VALUES* inFixedValues, _In_ ADDRESS_FAMILY addressFamily, _In_ FWP_DIRECTION direction, _Inout_ TL_INSPECT_PENDED_PACKET* pendedPacket ) { UINT localAddrIndex; UINT remoteAddrIndex; UINT localPortIndex; UINT remotePortIndex; UINT protocolIndex; NT_ASSERT(pendedPacket->type == TL_INSPECT_CONNECT_PACKET); GetNetwork5TupleIndexesForLayer( inFixedValues->layerId, &localAddrIndex, &remoteAddrIndex, &localPortIndex, &remotePortIndex, &protocolIndex ); if(localAddrIndex == UINT_MAX) { return FALSE; } if (addressFamily != pendedPacket->addressFamily) { return FALSE; } if (direction != pendedPacket->direction) { return FALSE; } if (inFixedValues->incomingValue[protocolIndex].value.uint8 != pendedPacket->protocol) { return FALSE; } if (RtlUshortByteSwap( inFixedValues->incomingValue[localPortIndex].value.uint16 ) != pendedPacket->localPort) { return FALSE; } if (RtlUshortByteSwap( inFixedValues->incomingValue[remotePortIndex].value.uint16 ) != pendedPacket->remotePort) { return FALSE; } if (addressFamily == AF_INET) { UINT32 ipv4LocalAddr = RtlUlongByteSwap( inFixedValues->incomingValue[localAddrIndex].value.uint32 ); UINT32 ipv4RemoteAddr = // Prefast thinks we are ignoring this return value. // If driver is unloading, we give up and ignore it on purpose. // Otherwise, we put the pointer onto the list, but we make it opaque // by casting it as a UINT64, and this tricks Prefast. RtlUlongByteSwap( /* host-order -> network-order conversion */ inFixedValues->incomingValue[remoteAddrIndex].value.uint32 ); if (ipv4LocalAddr != pendedPacket->ipv4LocalAddr) { return FALSE; } if (ipv4RemoteAddr != pendedPacket->ipv4RemoteAddr) { return FALSE; } } else { if (RtlCompareMemory( inFixedValues->incomingValue[localAddrIndex].value.byteArray16, &pendedPacket->localAddr, sizeof(FWP_BYTE_ARRAY16)) != sizeof(FWP_BYTE_ARRAY16)) { return FALSE; } if (RtlCompareMemory( inFixedValues->incomingValue[remoteAddrIndex].value.byteArray16, &pendedPacket->remoteAddr, sizeof(FWP_BYTE_ARRAY16)) != sizeof(FWP_BYTE_ARRAY16)) { return FALSE; } } return TRUE; }