Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I check if TCP port is available from TDI filter driver?

My TDI filter driver is intercepting IRP_MJ_CREATE requests, and assigning the source port of each opened TCP/UDP connection according to my needs. The driver is internally maintaining a table with the connections (including socket open/close and TCP grace-period), but I still see rare cases where the driver is not getting notifications of specific events, leading to incorrectly assuming that specific TCP source port is free, while it's in use.

I was looking into the option of sending a TDI_QUERY_INFORMATION request before assigning this port, but I don't see an option to query for any address - I can only query for an open address object, but not for general address.

Is there any (efficient) option to query for a specific source port and see if it's in use?

like image 893
user3428991 Avatar asked Mar 17 '14 13:03

user3428991


1 Answers

There must be a reason why notifications are not being delivered or handled. I would focus there first. However without having the source, that is difficult to determine.

Otherwise, pertaining to TDI_QUERY_INFORMATION:

Use the TdiBuildQueryInformation macro passing in the QType TDI_QUERY_ADDRESS_INFO. TDI_ADDRESS_INFO defines the format in which the transport returns the requested information.

TDI_ADDRESS_INFO contains a TRANSPORT_ADDRESS which contain 1 or more TA_ADDRESS structures.

Each of the TA_ADDRESS structures specify the transport address of a particular TDI_ADDRESS_TYPE_XXX. Pass in a TA_IP_ADDRESS structure, and specify the type as TDI_ADDRESS_TYPE_IP.

// From Tdi.h or TdiKrnl.h
#define TDI_ADDRESS_TYPE_IP        ((USHORT)2)  // internetwork: UDP, TCP, etc.

Inside the TA_IP_ADDRESS structure, there is a TDI_ADDRESS_IP, which contains the port.

typedef struct _TA_ADDRESS_IP {
  LONG           TAAddressCount;
  struct _AddrIp {
    USHORT         AddressLength;
    USHORT         AddressType;
    TDI_ADDRESS_IP Address[1];
  } Address[1];
} TA_IP_ADDRESS, *PTA_IP_ADDRESS;

// =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=

typedef struct _TDI_ADDRESS_IP {
  USHORT sin_port;
  ULONG  in_addr;
  UCHAR  sin_zero[8];
} TDI_ADDRESS_IP, *PTDI_ADDRESS_IP;

It looks like that most TDI features are deprecated and will be removed in future versions of Windows. As a result, they point you to either the Winsock Kernel (WSK) or Windows Filtering Platform (WFP).

Winsock Kernel

http://msdn.microsoft.com/en-us/library/windows/hardware/ff571083(v=vs.85).aspx

Windows Filtering Platform

http://msdn.microsoft.com/en-us/library/windows/hardware/ff571068(v=vs.85).aspx

Hope this helps.

like image 183
Jeff Avatar answered Sep 27 '22 18:09

Jeff