Esempio n. 1
0
NTSTATUS WallRegisterCallouts()
{
	NTSTATUS    status = STATUS_SUCCESS;
	BOOLEAN     bInTransaction = FALSE;
	BOOLEAN     bEngineOpened = FALSE;
	FWPM_SESSION session = {0};
	session.flags = FWPM_SESSION_FLAG_DYNAMIC;
	//开启WFP引擎
	status = FwpmEngineOpen( NULL,
	                         RPC_C_AUTHN_WINNT,
	                         NULL,
	                         &session,
	                         &gEngineHandle );
	if( !NT_SUCCESS(status))
		goto exit;
	bEngineOpened = TRUE;
	//确认过滤权限
	status = FwpmTransactionBegin( gEngineHandle,0 );
	if( !NT_SUCCESS(status))
		goto exit;
	bInTransaction = TRUE;
	//注册回调函数
	status = RegisterCalloutForLayer(
	             &FWPM_LAYER_ALE_AUTH_CONNECT_V4,
	             &GUID_ALE_AUTH_CONNECT_CALLOUT_V4,
	             WallALEConnectClassify,
	             WallNotifyFn,
	             WallFlowDeleteFn,
	             &gAleConnectCalloutId,
	             &gAleConnectFilterId);
	if( !NT_SUCCESS(status))
	{
		DbgPrint("RegisterCalloutForLayer-FWPM_LAYER_ALE_AUTH_CONNECT_V4 failed!\n");
		goto exit;
	}
	//确认所有内容并提交,让回调函数正式发挥作用
	status = FwpmTransactionCommit(gEngineHandle );
	if( !NT_SUCCESS(status))
		goto exit;
	bInTransaction = FALSE;
exit:
	if( !NT_SUCCESS(status))
	{
		if( bInTransaction)
		{
			FwpmTransactionAbort( gEngineHandle );
		}
		if( bEngineOpened )
		{
			FwpmEngineClose( gEngineHandle );
			gEngineHandle = 0;
		}
	}
	return status;
}
NTSTATUS
StreamEditRegisterCallout(
   const STREAM_EDITOR* streamEditor,
   _Inout_ void* deviceObject
   )
/* ++

   This function registers dynamic callouts and filters that intercept
   TCP traffic at WFP FWPM_LAYER_STREAM_V4 and FWPM_LAYER_STREAM_V6 
   layer.

   Callouts and filters will be removed during DriverUnload.

-- */
{
   NTSTATUS status = STATUS_SUCCESS;

   BOOLEAN engineOpened = FALSE;
   BOOLEAN inTransaction = FALSE;

   FWPM_SESSION session = {0};

   UNREFERENCED_PARAMETER(streamEditor);

   session.flags = FWPM_SESSION_FLAG_DYNAMIC;

   status = FwpmEngineOpen(
                NULL,
                RPC_C_AUTHN_WINNT,
                NULL,
                &session,
                &gEngineHandle
                );
   if (!NT_SUCCESS(status))
   {
      goto Exit;
   }
   engineOpened = TRUE;

   status = FwpmTransactionBegin(gEngineHandle, 0);
   if (!NT_SUCCESS(status))
   {
      goto Exit;
   }
   inTransaction = TRUE;

   status = RegisterCalloutForLayer(
               &FWPM_LAYER_STREAM_V4,
               &STREAM_EDITOR_STREAM_CALLOUT_V4,
               deviceObject,
               &gCalloutIdV4
               );
   if (!NT_SUCCESS(status))
   {
      goto Exit;
   }

   status = RegisterCalloutForLayer(
               &FWPM_LAYER_STREAM_V6,
               &STREAM_EDITOR_STREAM_CALLOUT_V6,
               deviceObject,
               &gCalloutIdV6
               );
   if (!NT_SUCCESS(status))
   {
      goto Exit;
   }

   status = FwpmTransactionCommit(gEngineHandle);
   if (!NT_SUCCESS(status))
   {
      goto Exit;
   }
   inTransaction = FALSE;

Exit:

   if (!NT_SUCCESS(status))
   {
      if (inTransaction)
      {
         NTSTATUS abortStatus;
         abortStatus = FwpmTransactionAbort(gEngineHandle);
         _Analysis_assume_(NT_SUCCESS(abortStatus));
      }
      if (engineOpened)
      {
         FwpmEngineClose(gEngineHandle);
         gEngineHandle = NULL;
      }
   }

   return status;
}