I have following question: I'm trying to implement (as for now) printing with KdPrint in debugger all TCP connections that are appearing since the launching of a driver. I'm using Stream V4 Layer for it without any filter (because it's already TCP, yes?) and with functions declared in a callout I intercept every packet and KdPrint info about Local IP, Local Port, Remote IP and Remote Port. Unfortunately nothing appears in the debugger, only messages with "nothing to do I/O".
Here is the code:
Initialize Callout:
static NTSTATUS InitializeCallout(PDEVICE_OBJECT deviceObject)
{
FWPM_SUBLAYER subLayer = {};
subLayer.displayData.name = const_cast<wchar_t*>(L"TcpInterception Sub-Layer");
subLayer.subLayerKey = TCP_INTERCEPTION_SUBLAYER;
NTSTATUS status = FwpmSubLayerAdd(g_engineHandle, &subLayer, nullptr);
if (!NT_SUCCESS(status))
{
return status;
}
FWPS_CALLOUT0 sCallout =
{
TCP_INTERCEPTION_TRANSPORT_V4_CALLOUT,
0,
CalloutConnectClassifyFn,
CalloutNotifyFn,
nullptr
};
status = FwpsCalloutRegister0(deviceObject, &sCallout, &g_id);
if (!NT_SUCCESS(status))
{
return status;
}
FWPM_CALLOUT mCallout = {};
mCallout.calloutKey = TCP_INTERCEPTION_TRANSPORT_V4_CALLOUT;
mCallout.applicableLayer = FWPM_LAYER_STREAM_V4;
mCallout.displayData.name = const_cast<wchar_t*>(g_displayName);
status = FwpmCalloutAdd(g_engineHandle, &mCallout, nullptr, nullptr);
if (!NT_SUCCESS(status))
{
return status;
}
if (!NT_SUCCESS(status))
{
return status;
}
return status;
}
And the crucial CalloutConnectClassifyFn:
static void CalloutConnectClassifyFn(
const FWPS_INCOMING_VALUES0* inFixedValues,
const FWPS_INCOMING_METADATA_VALUES0* inMetaValues,
void* layerData,
const FWPS_FILTER0* filter,
UINT64 /*flowContext*/,
FWPS_CLASSIFY_OUT0* classifyOut)
{
// Allowing the traffic for another filter to make a final decision.
if (FlagOn(classifyOut->rights, FWPS_RIGHT_ACTION_WRITE))
{
classifyOut->actionType = FWP_ACTION_CONTINUE;
}
if (layerData)
{
ProcessTransportData(inFixedValues, inMetaValues, layerData, classifyOut);
}
// Callout function should clear the FWPS_RIGHT_ACTION_WRITE flag when it returns FWP_ACTION_BLOCK for the suggested action
// and if FWPS_FILTER_FLAG_CLEAR_ACTION_RIGHT flag is set
if (FWP_ACTION_BLOCK == classifyOut->actionType || FlagOn(filter->flags, FWPS_FILTER_FLAG_CLEAR_ACTION_RIGHT))
{
ClearFlag(classifyOut->rights, FWPS_RIGHT_ACTION_WRITE);
}
}
And finally ProcessTransportData:
static void ProcessTransportData(const FWPS_INCOMING_VALUES0* inFixedValues,
const FWPS_INCOMING_METADATA_VALUES0* inMetaValues,
void* layerData,
FWPS_CLASSIFY_OUT0* classifyOut)
{
UINT32 localAddress = inFixedValues->incomingValue[FWPS_FIELD_OUTBOUND_TRANSPORT_V4_IP_LOCAL_ADDRESS].value.uint32;
UINT32 remoteAddress = inFixedValues->incomingValue[FWPS_FIELD_OUTBOUND_TRANSPORT_V4_IP_REMOTE_ADDRESS].value.uint32;
UINT16 localPort = inFixedValues->incomingValue[FWPS_FIELD_OUTBOUND_TRANSPORT_V4_IP_LOCAL_PORT].value.uint16;
UINT16 remotePort = inFixedValues->incomingValue[FWPS_FIELD_OUTBOUND_TRANSPORT_V4_IP_REMOTE_PORT].value.uint16;
if (inFixedValues->incomingValue[FWPS_FIELD_STREAM_V4_DIRECTION].value.uint32 == FWP_DIRECTION_INBOUND)
{
KdPrint(("Inbound connection\n"));
}
else
{
KdPrint(("Outbound connection\n"));
}
KdPrint(("Local IP: %d.%d.%d.%d\n", localAddress & 0xFF, (localAddress >> 8) & 0xFF, (localAddress >> 16) & 0xFF, (localAddress >> 24) & 0xFF));
KdPrint(("Remote IP: %d.%d.%d.%d\n", remoteAddress & 0xFF, (remoteAddress >> 8) & 0xFF, (remoteAddress >> 16) & 0xFF, (remoteAddress >> 24) & 0xFF));
KdPrint(("Local Port: %d\n", localPort));
KdPrint(("Remote Port: %d\n", remotePort));
}
Do you have any suggestions, solutions to this problem? Thanks for helping