示例#1
0
_Use_decl_annotations_
NTSTATUS
OvsCleanupDevice(PDEVICE_OBJECT deviceObject,
                 PIRP irp)
{

    PIO_STACK_LOCATION irpSp;
    PFILE_OBJECT fileObject;

    NTSTATUS status = STATUS_SUCCESS;
#ifdef DBG
    POVS_DEVICE_EXTENSION ovsExt =
        (POVS_DEVICE_EXTENSION)NdisGetDeviceReservedExtension(deviceObject);
    if (ovsExt) {
        ASSERT(ovsExt->numberOpenInstance > 0);
    }
#else
    UNREFERENCED_PARAMETER(deviceObject);
#endif
    ASSERT(deviceObject == gOvsDeviceObject);
    irpSp = IoGetCurrentIrpStackLocation(irp);
    fileObject = irpSp->FileObject;

    ASSERT(irpSp->MajorFunction == IRP_MJ_CLEANUP);

    OvsCleanupOpenInstance(fileObject);

    return OvsCompleteIrpRequest(irp, (ULONG_PTR)0, status);
}
示例#2
0
/*
 * --------------------------------------------------------------------------
 * Creates the communication device between user and kernel, and also
 * initializes the data associated data structures.
 * --------------------------------------------------------------------------
 */
NDIS_STATUS
OvsCreateDeviceObject(NDIS_HANDLE ovsExtDriverHandle)
{
    NDIS_STATUS status = NDIS_STATUS_SUCCESS;
    UNICODE_STRING deviceName;
    UNICODE_STRING symbolicDeviceName;
    PDRIVER_DISPATCH dispatchTable[IRP_MJ_MAXIMUM_FUNCTION+1];
    NDIS_DEVICE_OBJECT_ATTRIBUTES deviceAttributes;
    OVS_LOG_TRACE("ovsExtDriverHandle: %p", ovsExtDriverHandle);

    RtlZeroMemory(dispatchTable,
                  (IRP_MJ_MAXIMUM_FUNCTION + 1) * sizeof (PDRIVER_DISPATCH));
    dispatchTable[IRP_MJ_CREATE] = OvsOpenCloseDevice;
    dispatchTable[IRP_MJ_CLOSE] = OvsOpenCloseDevice;
    dispatchTable[IRP_MJ_CLEANUP] = OvsCleanupDevice;
    dispatchTable[IRP_MJ_DEVICE_CONTROL] = OvsDeviceControl;

    NdisInitUnicodeString(&deviceName, OVS_DEVICE_NAME_NT);
    NdisInitUnicodeString(&symbolicDeviceName, OVS_DEVICE_NAME_DOS);

    RtlZeroMemory(&deviceAttributes, sizeof (NDIS_DEVICE_OBJECT_ATTRIBUTES));

    OVS_INIT_OBJECT_HEADER(&deviceAttributes.Header,
                           NDIS_OBJECT_TYPE_DEVICE_OBJECT_ATTRIBUTES,
                           NDIS_DEVICE_OBJECT_ATTRIBUTES_REVISION_1,
                           sizeof (NDIS_DEVICE_OBJECT_ATTRIBUTES));

    deviceAttributes.DeviceName = &deviceName;
    deviceAttributes.SymbolicName = &symbolicDeviceName;
    deviceAttributes.MajorFunctions = dispatchTable;
    deviceAttributes.ExtensionSize = sizeof (OVS_DEVICE_EXTENSION);

    status = NdisRegisterDeviceEx(ovsExtDriverHandle,
                                  &deviceAttributes,
                                  &gOvsDeviceObject,
                                  &gOvsDeviceHandle);
    if (status != NDIS_STATUS_SUCCESS) {
        POVS_DEVICE_EXTENSION ovsExt =
            (POVS_DEVICE_EXTENSION)NdisGetDeviceReservedExtension(gOvsDeviceObject);
        ASSERT(gOvsDeviceObject != NULL);
        ASSERT(gOvsDeviceHandle != NULL);

        if (ovsExt) {
            ovsExt->numberOpenInstance = 0;
        }
    } else {
        /* Initialize the associated data structures. */
        OvsInit();
    }
    OVS_LOG_TRACE("DeviceObject: %p", gOvsDeviceObject);
    return status;
}
示例#3
0
VOID
OvsDeleteDeviceObject()
{
    if (gOvsDeviceHandle) {
#ifdef DBG
        POVS_DEVICE_EXTENSION ovsExt = (POVS_DEVICE_EXTENSION)
                    NdisGetDeviceReservedExtension(gOvsDeviceObject);
        if (ovsExt) {
            ASSERT(ovsExt->numberOpenInstance == 0);
        }
#endif

        ASSERT(gOvsDeviceObject);
        NdisDeregisterDeviceEx(gOvsDeviceHandle);
        gOvsDeviceHandle = NULL;
        gOvsDeviceObject = NULL;
    }
    OvsCleanup();
}
示例#4
0
文件: device.c 项目: 09zwcbupt/nimbus
_Use_decl_annotations_
NTSTATUS
FilterDeviceIoControl(
PDEVICE_OBJECT        DeviceObject,
PIRP                  Irp
)
{
	PIO_STACK_LOCATION          IrpSp;
	//NTSTATUS                    Status = STATUS_SUCCESS;
	PFILTER_DEVICE_EXTENSION    FilterDeviceExtension;
	//PUCHAR                      InputBuffer;
	//PUCHAR                      OutputBuffer;
	//ULONG                       InputBufferLength, OutputBufferLength;
	//PLIST_ENTRY                 Link;
	//PUCHAR                      pInfo;
	//ULONG                       InfoLength = 0;
	//PMS_FILTER                  pFilter = NULL;
	//BOOLEAN                     bFalse = FALSE;


	UNREFERENCED_PARAMETER(DeviceObject);


	IrpSp = IoGetCurrentIrpStackLocation(Irp);

	if (IrpSp->FileObject == NULL)
	{
		return(STATUS_UNSUCCESSFUL);
	}


	FilterDeviceExtension = (PFILTER_DEVICE_EXTENSION)NdisGetDeviceReservedExtension(DeviceObject);

	ASSERT(FilterDeviceExtension->Signature == 'FTDR');
	
	return FlowTableIoControl(Irp);

}
示例#5
0
NTSTATUS
OvsOpenCloseDevice(PDEVICE_OBJECT deviceObject,
                   PIRP irp)
{
    PIO_STACK_LOCATION irpSp;
    NTSTATUS status = STATUS_SUCCESS;
    PFILE_OBJECT fileObject;
    POVS_DEVICE_EXTENSION ovsExt =
        (POVS_DEVICE_EXTENSION)NdisGetDeviceReservedExtension(deviceObject);

    ASSERT(deviceObject == gOvsDeviceObject);
    ASSERT(ovsExt != NULL);

    irpSp = IoGetCurrentIrpStackLocation(irp);
    fileObject = irpSp->FileObject;
    OVS_LOG_TRACE("DeviceObject: %p, fileObject:%p, instance: %u",
                  deviceObject, fileObject,
                  ovsExt->numberOpenInstance);

    switch (irpSp->MajorFunction) {
    case IRP_MJ_CREATE:
        status = OvsAddOpenInstance(ovsExt, fileObject);
        if (STATUS_SUCCESS == status) {
            InterlockedIncrement((LONG volatile *)&ovsExt->numberOpenInstance);
        }
        break;
    case IRP_MJ_CLOSE:
        ASSERT(ovsExt->numberOpenInstance > 0);
        OvsRemoveOpenInstance(fileObject);
        InterlockedDecrement((LONG volatile *)&ovsExt->numberOpenInstance);
        break;
    default:
        ASSERT(0);
    }
    return OvsCompleteIrpRequest(irp, (ULONG_PTR)0, status);
}
示例#6
0
文件: device.c 项目: AlexeyAB/netmap
_Use_decl_annotations_
NTSTATUS
FilterDeviceIoControl(
    PDEVICE_OBJECT        DeviceObject,
    PIRP                  Irp
    )
{
    PIO_STACK_LOCATION          IrpSp;
    NTSTATUS                    Status = STATUS_SUCCESS;
    PFILTER_DEVICE_EXTENSION    FilterDeviceExtension;
    PUCHAR                      InputBuffer;
    PUCHAR                      OutputBuffer;
    ULONG                       InputBufferLength, OutputBufferLength;
    PLIST_ENTRY                 Link;
    PUCHAR                      pInfo;
    ULONG                       InfoLength = 0;
    PMS_FILTER                  pFilter = NULL;
    BOOLEAN                     bFalse = FALSE;


    UNREFERENCED_PARAMETER(DeviceObject);

    DbgPrint("------------------FilterDeviceIoControl!\n");

    IrpSp = IoGetCurrentIrpStackLocation(Irp);

    if (IrpSp->FileObject == NULL)
    {
        return(STATUS_UNSUCCESSFUL);
    }


    FilterDeviceExtension = (PFILTER_DEVICE_EXTENSION)NdisGetDeviceReservedExtension(DeviceObject);

    ASSERT(FilterDeviceExtension->Signature == 'FTDR');

    Irp->IoStatus.Information = 0;

    switch (IrpSp->Parameters.DeviceIoControl.IoControlCode)
    {

        case IOCTL_FILTER_RESTART_ALL:
            break;

        case IOCTL_FILTER_RESTART_ONE_INSTANCE:
            InputBuffer = OutputBuffer = (PUCHAR)Irp->AssociatedIrp.SystemBuffer;
            InputBufferLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;

            pFilter = filterFindFilterModule (InputBuffer, InputBufferLength);

            if (pFilter == NULL)
            {

                break;
            }

            NdisFRestartFilter(pFilter->FilterHandle);

            break;

        case IOCTL_FILTER_ENUERATE_ALL_INSTANCES:

            InputBuffer = OutputBuffer = (PUCHAR)Irp->AssociatedIrp.SystemBuffer;
            InputBufferLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;
            OutputBufferLength = IrpSp->Parameters.DeviceIoControl.OutputBufferLength;


            pInfo = OutputBuffer;

            FILTER_ACQUIRE_LOCK(&FilterListLock, bFalse);

            Link = FilterModuleList.Flink;

            while (Link != &FilterModuleList)
            {
                pFilter = CONTAINING_RECORD(Link, MS_FILTER, FilterModuleLink);


                InfoLength += (pFilter->FilterModuleName.Length + sizeof(USHORT));

                if (InfoLength <= OutputBufferLength)
                {
                    *(PUSHORT)pInfo = pFilter->FilterModuleName.Length;
                    NdisMoveMemory(pInfo + sizeof(USHORT),
                                   (PUCHAR)(pFilter->FilterModuleName.Buffer),
                                   pFilter->FilterModuleName.Length);

                    pInfo += (pFilter->FilterModuleName.Length + sizeof(USHORT));
                }

                Link = Link->Flink;
            }

            FILTER_RELEASE_LOCK(&FilterListLock, bFalse);
            if (InfoLength <= OutputBufferLength)
            {

                Status = NDIS_STATUS_SUCCESS;
            }
            //
            // Buffer is small
            //
            else
            {
                Status = STATUS_BUFFER_TOO_SMALL;
            }
            break;


        default:
	    DbgPrint("WRONG request received!\n");
            break;
    }

    Irp->IoStatus.Status = Status;
    Irp->IoStatus.Information = InfoLength;

    IoCompleteRequest(Irp, IO_NO_INCREMENT);

    return Status;


}
示例#7
0
文件: device.c 项目: AlexeyAB/netmap
NDIS_STATUS
FilterRegisterDevice(
    VOID
    )
{
    NDIS_STATUS            Status = NDIS_STATUS_SUCCESS;
    UNICODE_STRING         DeviceName;
    UNICODE_STRING         DeviceLinkUnicodeString;
    PDRIVER_DISPATCH       DispatchTable[IRP_MJ_MAXIMUM_FUNCTION+1];
    NDIS_DEVICE_OBJECT_ATTRIBUTES   DeviceAttribute;
    PFILTER_DEVICE_EXTENSION        FilterDeviceExtension;

    DEBUGP(DL_TRACE, "==>FilterRegisterDevice\n");

    NdisZeroMemory(DispatchTable, (IRP_MJ_MAXIMUM_FUNCTION+1) * sizeof(PDRIVER_DISPATCH));

    DispatchTable[IRP_MJ_CREATE] = FilterDispatch;
    DispatchTable[IRP_MJ_CLEANUP] = FilterDispatch;
    DispatchTable[IRP_MJ_CLOSE] = FilterDispatch;
    DispatchTable[IRP_MJ_DEVICE_CONTROL] = FilterDeviceIoControl;
    DispatchTable[IRP_MJ_INTERNAL_DEVICE_CONTROL] = FilterInternalDeviceIoControl;

    NdisInitUnicodeString(&DeviceName, NETMAP_NDIS_NTDEVICE_STRING);
    NdisInitUnicodeString(&DeviceLinkUnicodeString, NETMAP_NDIS_LINKNAME_STRING);

    //
    // Create a device object and register our dispatch handlers
    //
    NdisZeroMemory(&DeviceAttribute, sizeof(NDIS_DEVICE_OBJECT_ATTRIBUTES));

    DeviceAttribute.Header.Type = NDIS_OBJECT_TYPE_DEVICE_OBJECT_ATTRIBUTES;
    DeviceAttribute.Header.Revision = NDIS_DEVICE_OBJECT_ATTRIBUTES_REVISION_1;
    DeviceAttribute.Header.Size = sizeof(NDIS_DEVICE_OBJECT_ATTRIBUTES);

    DeviceAttribute.DeviceName = &DeviceName;
    DeviceAttribute.SymbolicName = &DeviceLinkUnicodeString;
    DeviceAttribute.MajorFunctions = &DispatchTable[0];
    DeviceAttribute.ExtensionSize = sizeof(FILTER_DEVICE_EXTENSION);

    Status = NdisRegisterDeviceEx(
                FilterDriverHandle,
                &DeviceAttribute,
                &DeviceObject,
                &NdisFilterDeviceHandle
                );


    if (Status == NDIS_STATUS_SUCCESS)
    {
        FilterDeviceExtension = NdisGetDeviceReservedExtension(DeviceObject);

        FilterDeviceExtension->Signature = 'FTDR';
        FilterDeviceExtension->Handle = FilterDriverHandle;
    }


    DEBUGP(DL_TRACE, "<==FilterRegisterDevice: %x\n", Status);

    return (Status);

}
示例#8
0
/*
 * --------------------------------------------------------------------------
 * IOCTL function handler for the device.
 * --------------------------------------------------------------------------
 */
NTSTATUS
OvsDeviceControl(PDEVICE_OBJECT deviceObject,
                 PIRP irp)
{

    PIO_STACK_LOCATION irpSp;
    NTSTATUS status = STATUS_SUCCESS;
    PFILE_OBJECT fileObject;
    PVOID inputBuffer = NULL;
    PVOID outputBuffer = NULL;
    UINT32 inputBufferLen, outputBufferLen;
    UINT32 code, replyLen = 0;
    POVS_OPEN_INSTANCE instance;
    UINT32 devOp;
    OVS_MESSAGE ovsMsgReadOp;
    POVS_MESSAGE ovsMsg;
    NETLINK_FAMILY *nlFamilyOps;

#ifdef DBG
    POVS_DEVICE_EXTENSION ovsExt =
        (POVS_DEVICE_EXTENSION)NdisGetDeviceReservedExtension(deviceObject);
    ASSERT(deviceObject == gOvsDeviceObject);
    ASSERT(ovsExt);
    ASSERT(ovsExt->numberOpenInstance > 0);
#else
    UNREFERENCED_PARAMETER(deviceObject);
#endif

    irpSp = IoGetCurrentIrpStackLocation(irp);

    ASSERT(irpSp->MajorFunction == IRP_MJ_DEVICE_CONTROL);
    ASSERT(irpSp->FileObject != NULL);

    fileObject = irpSp->FileObject;
    instance = (POVS_OPEN_INSTANCE)fileObject->FsContext;
    code = irpSp->Parameters.DeviceIoControl.IoControlCode;
    inputBufferLen = irpSp->Parameters.DeviceIoControl.InputBufferLength;
    outputBufferLen = irpSp->Parameters.DeviceIoControl.OutputBufferLength;
    inputBuffer = irp->AssociatedIrp.SystemBuffer;

    /* Concurrent netlink operations are not supported. */
    if (InterlockedCompareExchange((LONG volatile *)&instance->inUse, 1, 0)) {
        status = STATUS_RESOURCE_IN_USE;
        goto done;
    }

    /*
     * Validate the input/output buffer arguments depending on the type of the
     * operation.
     */
    switch (code) {
    case OVS_IOCTL_TRANSACT:
        /* Input buffer is mandatory, output buffer is optional. */
        if (outputBufferLen != 0) {
            status = MapIrpOutputBuffer(irp, outputBufferLen,
                                        sizeof *ovsMsg, &outputBuffer);
            if (status != STATUS_SUCCESS) {
                goto done;
            }
            ASSERT(outputBuffer);
        }

        if (inputBufferLen < sizeof (*ovsMsg)) {
            status = STATUS_NDIS_INVALID_LENGTH;
            goto done;
        }

        ovsMsg = inputBuffer;
        devOp = OVS_TRANSACTION_DEV_OP;
        break;

    case OVS_IOCTL_READ:
        /* Output buffer is mandatory. */
        if (outputBufferLen != 0) {
            status = MapIrpOutputBuffer(irp, outputBufferLen,
                                        sizeof *ovsMsg, &outputBuffer);
            if (status != STATUS_SUCCESS) {
                goto done;
            }
            ASSERT(outputBuffer);
        } else {
            status = STATUS_NDIS_INVALID_LENGTH;
            goto done;
        }

        /*
         * Operate in the mode that read ioctl is similar to ReadFile(). This
         * might change as the userspace code gets implemented.
         */
        inputBuffer = NULL;
        inputBufferLen = 0;
        /* Create an NL message for consumption. */
        ovsMsg = &ovsMsgReadOp;
        devOp = OVS_READ_DEV_OP;

        /*
         * For implementing read (ioctl or otherwise), we need to store some
         * state in the instance to indicate the previous command. The state can
         * setup 'ovsMsgReadOp' appropriately.
         *
         * XXX: Support for that will be added as the userspace code evolves.
         */
        status = STATUS_NOT_IMPLEMENTED;
        goto done;

        break;

    case OVS_IOCTL_WRITE:
        /* Input buffer is mandatory. */
        if (inputBufferLen < sizeof (*ovsMsg)) {
            status = STATUS_NDIS_INVALID_LENGTH;
            goto done;
        }

        ovsMsg = inputBuffer;
        devOp = OVS_WRITE_DEV_OP;
        break;

    default:
        status = STATUS_INVALID_DEVICE_REQUEST;
        goto done;
    }

    ASSERT(ovsMsg);
    switch (ovsMsg->nlMsg.nlmsgType) {
    case OVS_WIN_NL_CTRL_FAMILY_ID:
        nlFamilyOps = &nlControlFamilyOps;
        break;
    case OVS_WIN_NL_PACKET_FAMILY_ID:
    case OVS_WIN_NL_DATAPATH_FAMILY_ID:
    case OVS_WIN_NL_FLOW_FAMILY_ID:
    case OVS_WIN_NL_VPORT_FAMILY_ID:
        status = STATUS_NOT_IMPLEMENTED;
        goto done;

    default:
        status = STATUS_INVALID_PARAMETER;
        goto done;
    }

    /*
     * For read operation, the netlink command has already been validated
     * previously.
     */
    if (devOp != OVS_READ_DEV_OP) {
        status = ValidateNetlinkCmd(devOp, ovsMsg, nlFamilyOps);
        if (status != STATUS_SUCCESS) {
            goto done;
        }
    }

    status = InvokeNetlinkCmdHandler(irp, fileObject, devOp,
                                     ovsMsg, nlFamilyOps,
                                     inputBuffer, inputBufferLen,
                                     outputBuffer, outputBufferLen,
                                     &replyLen);

done:
    KeMemoryBarrier();
    instance->inUse = 0;
    return OvsCompleteIrpRequest(irp, (ULONG_PTR)replyLen, status);
}
示例#9
0
文件: OvsIoctl.c 项目: timfallmk/ovs
NTSTATUS
OvsDeviceControl(PDEVICE_OBJECT deviceObject,
                 PIRP irp)
{

    PIO_STACK_LOCATION irpSp;
    NTSTATUS status = STATUS_SUCCESS;
    PFILE_OBJECT fileObject;
    PVOID inputBuffer;
    PVOID outputBuffer;
    UINT32 inputBufferLen, outputBufferLen, mdlBufferLen;
    UINT32 code, replyLen = 0;
#ifdef DBG
    POVS_DEVICE_EXTENSION ovsExt =
        (POVS_DEVICE_EXTENSION)NdisGetDeviceReservedExtension(deviceObject);
    ASSERT(deviceObject == gOvsDeviceObject);
    ASSERT(ovsExt);
    ASSERT(ovsExt->numberOpenInstance > 0);
#else
    UNREFERENCED_PARAMETER(deviceObject);
#endif

    irpSp = IoGetCurrentIrpStackLocation(irp);


    ASSERT(irpSp->MajorFunction == IRP_MJ_DEVICE_CONTROL);
    ASSERT(irpSp->FileObject != NULL);

    fileObject = irpSp->FileObject;
    code = irpSp->Parameters.DeviceIoControl.IoControlCode;
    inputBufferLen = irpSp->Parameters.DeviceIoControl.InputBufferLength;
    outputBufferLen = irpSp->Parameters.DeviceIoControl.OutputBufferLength;
    /*
     * In case of an IRP with METHOD_IN_DIRECT or METHOD_OUT_DIRECT, the size
     * of the MDL is stored in Parameters.DeviceIoControl.OutputBufferLength.
     */
    mdlBufferLen = outputBufferLen;
    outputBuffer = inputBuffer = irp->AssociatedIrp.SystemBuffer;

    switch(code) {
    case OVS_IOCTL_VERSION_GET:
        status = OvsGetVersionIoctl(outputBuffer, outputBufferLen,
                                    &replyLen);
        break;
    case OVS_IOCTL_DP_DUMP:
        status = OvsDpDumpIoctl(outputBuffer, outputBufferLen, &replyLen);
        break;
    case OVS_IOCTL_DP_GET:
        if (irp->MdlAddress == NULL) {
            status = STATUS_INVALID_PARAMETER;
            break;
        }
        outputBuffer = MmGetSystemAddressForMdlSafe(irp->MdlAddress,
                                                    NormalPagePriority);
        if (outputBuffer == NULL) {
            status = STATUS_INSUFFICIENT_RESOURCES;
        } else {
            status = OvsDpGetIoctl(inputBuffer, inputBufferLen,
                                   outputBuffer, outputBufferLen, &replyLen);
        }
        break;
    case OVS_IOCTL_DP_SET:
        status = STATUS_NOT_IMPLEMENTED;
        break;
    case OVS_IOCTL_VPORT_DUMP:
        if (irp->MdlAddress == NULL) {
            status = STATUS_INVALID_PARAMETER;
            break;
        }
        outputBuffer = MmGetSystemAddressForMdlSafe(irp->MdlAddress,
                                                    NormalPagePriority);
        if (outputBuffer) {
            status = OvsDumpVportIoctl(inputBuffer, inputBufferLen,
                                       outputBuffer, outputBufferLen,
                                       &replyLen);
        } else {
            status = STATUS_INSUFFICIENT_RESOURCES;
        }
        break;
    case OVS_IOCTL_VPORT_GET:
        if (irp->MdlAddress == NULL) {
            status = STATUS_INVALID_PARAMETER;
            break;
        }
        outputBuffer = MmGetSystemAddressForMdlSafe(irp->MdlAddress,
                                                    NormalPagePriority);
        if (outputBuffer) {
            status = OvsGetVportIoctl(inputBuffer, inputBufferLen,
                                      outputBuffer, outputBufferLen,
                                      &replyLen);
        } else {
            status =  STATUS_INSUFFICIENT_RESOURCES;
        }
        break;
    case OVS_IOCTL_VPORT_SET:
        status = STATUS_NOT_IMPLEMENTED;
        break;
    case OVS_IOCTL_VPORT_ADD:
        if (irp->MdlAddress == NULL) {
            status = STATUS_INVALID_PARAMETER;
            break;
        }
        outputBuffer = MmGetSystemAddressForMdlSafe(irp->MdlAddress,
                                                    NormalPagePriority);
        if (outputBuffer) {
            status = OvsAddVportIoctl(inputBuffer, inputBufferLen,
                                      outputBuffer, outputBufferLen,
                                      &replyLen);
        }  else {
            status = STATUS_INSUFFICIENT_RESOURCES;
        }
        break;
    case OVS_IOCTL_VPORT_DEL:
        status = OvsDelVportIoctl(inputBuffer, inputBufferLen,
                                  &replyLen);
        break;
    case OVS_IOCTL_VPORT_EXT_INFO:
        if (irp->MdlAddress == NULL) {
            status = STATUS_INVALID_PARAMETER;
            break;
        }
        outputBuffer = MmGetSystemAddressForMdlSafe(irp->MdlAddress,
                                                    NormalPagePriority);
        if (outputBuffer) {
            status = OvsGetExtInfoIoctl(inputBuffer, inputBufferLen,
                                          outputBuffer, outputBufferLen,
                                          &replyLen);
        } else {
            OVS_LOG_INFO("ExtInfo: fail to get outputBuffer address");
            status = STATUS_INSUFFICIENT_RESOURCES;
        }
        break;
    case OVS_IOCTL_FLOW_DUMP:
        if (irp->MdlAddress == NULL) {
            status = STATUS_INVALID_PARAMETER;
            break;
        }
        outputBuffer = MmGetSystemAddressForMdlSafe(irp->MdlAddress,
                                                    NormalPagePriority);
        if (outputBuffer) {
            status = OvsDumpFlowIoctl(inputBuffer, inputBufferLen,
                                      outputBuffer, outputBufferLen,
                                      &replyLen);
        } else {
            status = STATUS_INSUFFICIENT_RESOURCES;
        }
        break;
    case OVS_IOCTL_FLOW_GET:
        if (irp->MdlAddress == NULL) {
            status = STATUS_INVALID_PARAMETER;
            break;
        }
        outputBuffer = MmGetSystemAddressForMdlSafe(irp->MdlAddress,
                                                    NormalPagePriority);
        if (outputBuffer) {
            status = OvsGetFlowIoctl(inputBuffer, inputBufferLen,
                                     outputBuffer, outputBufferLen,
                                     &replyLen);
        } else {
            status = STATUS_INSUFFICIENT_RESOURCES;
        }
        break;
    case OVS_IOCTL_FLOW_PUT:
        // XXX: This is not really working - mapping the input buffer
        // XXX: inputBufferLen = mdlBufferLen;
        // inputBuffer = MmGetSystemAddressForMdlSafe(irp->MdlAddress,
                                                   // NormalPagePriority);
        status = OvsPutFlowIoctl(inputBuffer, inputBufferLen,
                                 outputBuffer, outputBufferLen,
                                 &replyLen);
        break;
    case OVS_IOCTL_FLOW_FLUSH:
        status = OvsFlushFlowIoctl(inputBuffer, inputBufferLen);
        break;
    case OVS_IOCTL_QOS_QUEUE_DUMP:
    case OVS_IOCTL_QOS_QUEUE_GET:
    case OVS_IOCTL_QOS_QUEUE_SET:
        status = STATUS_NOT_IMPLEMENTED;
        break;
    case OVS_IOCTL_DATAPATH_SUBSCRIBE:
        status = OvsSubscribeDpIoctl(fileObject, inputBuffer,
                                           inputBufferLen);
        break;
    case OVS_IOCTL_DATAPATH_READ:
        if (irp->MdlAddress == NULL) {
            status = STATUS_INVALID_PARAMETER;
            break;
        }
        outputBuffer = MmGetSystemAddressForMdlSafe(irp->MdlAddress,
                                                    NormalPagePriority);
        if (outputBuffer) {
            status = OvsReadDpIoctl(fileObject, outputBuffer,
                                          outputBufferLen, &replyLen);
        } else {
            status = STATUS_INSUFFICIENT_RESOURCES;
        }
        break;
    case OVS_IOCTL_DATAPATH_OPERATE:
        status = STATUS_NOT_IMPLEMENTED;
        break;
    case OVS_IOCTL_DATAPATH_EXECUTE:
        // XXX: need to make the input direct
        status = OvsExecuteDpIoctl(inputBuffer, inputBufferLen,
                                         outputBufferLen);
        break;
    case OVS_IOCTL_DATAPATH_PURGE:
        status = OvsPurgeDpIoctl(fileObject);
        break;
    case OVS_IOCTL_DATAPATH_WAIT:
        status = OvsWaitDpIoctl(irp, fileObject);
        break;
    case OVS_IOCTL_EVENT_SUBSCRIBE:
        status = OvsSubscribeEventIoctl(fileObject, inputBuffer,
                                        inputBufferLen);
        break;
    case OVS_IOCTL_EVENT_POLL:
        if (irp->MdlAddress == NULL) {
            status = STATUS_INVALID_PARAMETER;
            break;
        }
        outputBuffer = MmGetSystemAddressForMdlSafe(irp->MdlAddress,
                                                    NormalPagePriority);
        if (outputBuffer == NULL) {
            status = STATUS_INSUFFICIENT_RESOURCES;
        } else {
            status = OvsPollEventIoctl(fileObject, inputBuffer,
                                       inputBufferLen, outputBuffer,
                                       outputBufferLen, &replyLen);
        }
        break;
    case OVS_IOCTL_EVENT_WAIT:
        status = OvsWaitEventIoctl(irp, fileObject,
                                   inputBuffer, inputBufferLen);
        break;
    case OVS_IOCTL_DP_TIMESTAMP_SET:
        if (inputBufferLen != sizeof (ovsUserTimestampDelta)) {
            status = STATUS_INFO_LENGTH_MISMATCH;
        } else {
            int64 currentUserTS = *(int64 *)inputBuffer;
            LARGE_INTEGER tickCount;

            /* So many ticks since system booted. */
            KeQueryTickCount(&tickCount);
            ovsUserTimestampDelta = currentUserTS -
                                    (tickCount.QuadPart * ovsTimeIncrementPerTick);
            status = STATUS_SUCCESS;
        }
        break;
    default:
        status = STATUS_INVALID_DEVICE_REQUEST;
        break;
    }

    if (status == STATUS_PENDING) {
        return status;
    } else {
        /*
         * When the system-address-space mapping that is returned by
         * MmGetSystemAddressForMdlSafe is no longer needed, it must be
         * released.
         * http://msdn.microsoft.com/en-us/library/windows/hardware/ff554559(v=vs.85).aspx
         *
         * We might have to release the MDL here.
         */
        return OvsCompleteIrpRequest(irp, (ULONG_PTR)replyLen, status);
    }
}
示例#10
0
_Use_decl_annotations_
NTSTATUS
FilterDeviceIoControl(
    PDEVICE_OBJECT        DeviceObject,
    PIRP                  Irp
    )
{
    PIO_STACK_LOCATION          irp_sp;
    NTSTATUS                    status = STATUS_SUCCESS;
    PFILTER_DEVICE_EXTENSION    filter_device_extension;
    PUCHAR                      input_buffer;
    PUCHAR                      output_buffer;
    ULONG                       input_buffer_length, output_buffer_length;
    PLIST_ENTRY                 link;
    PUCHAR                      info;
    ULONG                       InfoLength = 0;
    PLCXL_FILTER                filter = NULL;
    BOOLEAN                     bFalse = FALSE;


    UNREFERENCED_PARAMETER(DeviceObject);


    irp_sp = IoGetCurrentIrpStackLocation(Irp);

    if (irp_sp->FileObject == NULL) {
        return(STATUS_UNSUCCESSFUL);
    }


    filter_device_extension = (PFILTER_DEVICE_EXTENSION)NdisGetDeviceReservedExtension(DeviceObject);

    ASSERT(filter_device_extension->Signature == 'FTDR');

    Irp->IoStatus.Information = 0;

	input_buffer = output_buffer = (PUCHAR)Irp->AssociatedIrp.SystemBuffer;
	input_buffer_length = output_buffer_length = irp_sp->Parameters.DeviceIoControl.InputBufferLength;

    switch (irp_sp->Parameters.DeviceIoControl.IoControlCode) {

        case IOCTL_FILTER_RESTART_ALL:
            break;

        case IOCTL_FILTER_RESTART_ONE_INSTANCE:
            filter = filterFindFilterModule (input_buffer, input_buffer_length);

            if (filter == NULL) {

                break;
            }
            NdisFRestartFilter(filter->filter_handle);
            break;

        case IOCTL_FILTER_ENUERATE_ALL_INSTANCES:

            info = output_buffer;
			LockLCXLLockList(&g_filter_list);
            
            link = GetListofLCXLLockList(&g_filter_list)->Flink;
			//遍历列表
			while (link != GetListofLCXLLockList(&g_filter_list)) {
                filter = CONTAINING_RECORD(link, LCXL_FILTER, filter_module_link);

                InfoLength += (filter->module_setting->filter_module_name->Length + sizeof(USHORT));

                if (InfoLength <= output_buffer_length) {
					*(PUSHORT)info = filter->module_setting->filter_module_name->Length;
                    NdisMoveMemory(info + sizeof(USHORT),
						(PUCHAR)(filter->module_setting->filter_module_name->Buffer),
						filter->module_setting->filter_module_name->Length);

					info += (filter->module_setting->filter_module_name->Length + sizeof(USHORT));
                }
                link = link->Flink;
            }
			UnlockLCXLLockList(&g_filter_list);
            if (InfoLength <= output_buffer_length) {
                status = NDIS_STATUS_SUCCESS;
            }
            //
            // Buffer is small
            //
            else {
                status = STATUS_BUFFER_TOO_SMALL;
            }
            break;
		//添加代码
		case IOCTL_LOADER_ALL_APP_MODULE:
		{
			PAPP_MODULE_INFO cur_buf;
			PLCXL_MODULE_SETTING_LIST_ENTRY module;

			cur_buf = (PAPP_MODULE_INFO)output_buffer;
			LockLCXLLockList(&g_setting.module_list);
			module = CONTAINING_RECORD(GetListofLCXLLockList(&g_setting.module_list)->Flink, LCXL_MODULE_SETTING_LIST_ENTRY, list_entry);
			while (&module->list_entry != GetListofLCXLLockList(&g_setting.module_list)) {
				//先判断缓冲区是否足够
				if (output_buffer_length - (ULONG)((LONG_PTR)cur_buf - (LONG_PTR)output_buffer) < sizeof(APP_MODULE_INFO)) {
					status = STATUS_BUFFER_TOO_SMALL;
					break;
				}
				cur_buf->app_module_status = module->ref_count == 0 ? AMS_NO_FILTER : AMS_NORMAL;
				FILTER_ACQUIRE_LOCK(&module->lock, bFalse);
				cur_buf->real_addr = module->real_addr;
				cur_buf->virtual_ipv4 = module->virtual_ipv4;
				cur_buf->virtual_ipv6 = module->virtual_ipv6;
				LockLCXLLockList(&module->server_list);
				cur_buf->server_count = GetListCountofLCXLLockList(&module->server_list);
				UnlockLCXLLockList(&module->server_list);
				FILTER_RELEASE_LOCK(&module->lock, bFalse);
				cur_buf->miniport_net_luid = module->miniport_net_luid;

				cur_buf->filter_module_name_len = (sizeof(cur_buf->filter_module_name) < module->filter_module_name->Length) ? sizeof(cur_buf->filter_module_name) : module->filter_module_name->Length;
				RtlCopyMemory(cur_buf->filter_module_name, module->filter_module_name->Buffer, cur_buf->filter_module_name_len);

				cur_buf->miniport_friendly_name_len = (sizeof(cur_buf->miniport_friendly_name) < module->miniport_friendly_name->Length) ? sizeof(cur_buf->miniport_friendly_name) : module->miniport_friendly_name->Length;
				RtlCopyMemory(cur_buf->miniport_friendly_name, module->miniport_friendly_name->Buffer, cur_buf->miniport_friendly_name_len);

				cur_buf->miniport_name_len = (sizeof(cur_buf->miniport_name) < module->miniport_name->Length) ? sizeof(cur_buf->miniport_name) : module->miniport_name->Length;
				RtlCopyMemory(cur_buf->miniport_name, module->miniport_name->Buffer, cur_buf->miniport_name_len);

				cur_buf++;
				module = CONTAINING_RECORD(module->list_entry.Flink, LCXL_MODULE_SETTING_LIST_ENTRY, list_entry);
			}
			UnlockLCXLLockList(&g_setting.module_list);
			InfoLength = (ULONG)((ULONG_PTR)cur_buf - (ULONG_PTR)output_buffer);
		}
			break;
		case IOCTL_LOADER_SET_VIRTUAL_IP:
			if (input_buffer_length == sizeof(APP_IP)) {
				PAPP_IP ip;
				PLCXL_FILTER pFilter;

				ip = (PAPP_IP)input_buffer;
				LockLCXLLockList(&g_filter_list);
				pFilter = FindFilter(ip->miniport_net_luid);
				if (pFilter != NULL) {
					NdisAcquireSpinLock(&pFilter->module_setting->lock);
					switch (ip->ip.ip_mode) {
						//IPv4模式
					case IM_IPV4:
						pFilter->module_setting->virtual_ipv4 = ip->ip.addr.ip_4;
						break;
						//IPv6模式
					case IM_IPV6:
						pFilter->module_setting->virtual_ipv6 = ip->ip.addr.ip_6;
						break;
					default:
						status = STATUS_INVALID_PARAMETER;
						break;
					}
					NdisReleaseSpinLock(&pFilter->module_setting->lock);
				}
				
				UnlockLCXLLockList(&g_filter_list);
			} else {
				status = STATUS_INFO_LENGTH_MISMATCH;
			}
			break;
		case IOCTL_LOADER_GET_SERVER_LIST:
			if (input_buffer_length == sizeof(NET_LUID)) {
				PLCXL_FILTER pFilter;

				LockLCXLLockList(&g_filter_list); 
				pFilter = FindFilter(*(PNET_LUID)input_buffer);
				if (pFilter != NULL) {
					if (pFilter->module_setting != NULL && (pFilter->module_setting->flag & MSF_DELETE_AFTER_RESTART) == 0) {
						
					} else {
						status = STATUS_NOT_FOUND;
					}
				} else {
					status = STATUS_NOT_FOUND;
				}
				UnlockLCXLLockList(&g_filter_list);
			} else {
				status = STATUS_INFO_LENGTH_MISMATCH;
			}
			break;
		case IOCTL_LOADER_ADD_SERVER:
			if (sizeof(APP_ADD_SERVER) == input_buffer_length) {
				PAPP_ADD_SERVER app_add_server;
				PLCXL_FILTER pFilter;
				
				app_add_server = (PAPP_ADD_SERVER)input_buffer;
				LockLCXLLockList(&g_filter_list);
				pFilter = FindFilter(app_add_server->miniport_net_luid);
				if (pFilter != NULL) {
					
					LockLCXLLockList(&pFilter->module_setting->server_list);
					
					
					UnlockLCXLLockList(&pFilter->module_setting->server_list);
				}
				UnlockLCXLLockList(&g_filter_list);
			} else {
				status = STATUS_INFO_LENGTH_MISMATCH;
			}
			break;
		case IOCTL_LOADER_DEL_SERVER:
			if (sizeof(APP_DEL_SERVER) == input_buffer_length) {
				PAPP_DEL_SERVER app_del_server = (PAPP_DEL_SERVER)input_buffer;
				PLCXL_FILTER pFilter;

				LockLCXLLockList(&g_filter_list);
				pFilter = FindFilter(app_del_server->miniport_net_luid);
				UnlockLCXLLockList(&g_filter_list);
				
			} else {
				status = STATUS_INFO_LENGTH_MISMATCH;
			}
			break;
		//!添加代码!
        default:
			status = STATUS_INVALID_PARAMETER;
            break;
    }

    Irp->IoStatus.Status = status;
    Irp->IoStatus.Information = InfoLength;

    IoCompleteRequest(Irp, IO_NO_INCREMENT);

    return status;
}
示例#11
0
NDIS_STATUS
NDISFilterDriverRegisterDevice(OUT PFILTER_DEVICE_EXTENSION *Extension)
{
    NDIS_STATUS            Status = NDIS_STATUS_SUCCESS;
    UNICODE_STRING         DeviceName;
    UNICODE_STRING         DeviceLinkUnicodeString;
    PDRIVER_DISPATCH       DispatchTable[IRP_MJ_MAXIMUM_FUNCTION+1];
    NDIS_DEVICE_OBJECT_ATTRIBUTES   DeviceAttribute;
    PFILTER_DEVICE_EXTENSION        FilterDeviceExtension;
    PDRIVER_OBJECT                  DriverObject;
   
    DEBUGP(DL_TRACE, "==>NDISFilterDriverRegisterDevice\n");
   
    
    NdisZeroMemory(DispatchTable, (IRP_MJ_MAXIMUM_FUNCTION+1) * sizeof(PDRIVER_DISPATCH));
    
    DispatchTable[IRP_MJ_CREATE] = NDISFilterDriverDispatch;
    DispatchTable[IRP_MJ_CLEANUP] = NDISFilterDriverDispatch;
    DispatchTable[IRP_MJ_CLOSE] = NDISFilterDriverDispatch;
    DispatchTable[IRP_MJ_DEVICE_CONTROL] = NDISFilterDriverDeviceIoControl;
    
    
    NdisInitUnicodeString(&DeviceName, NTDEVICE_STRING);
    NdisInitUnicodeString(&DeviceLinkUnicodeString, LINKNAME_STRING);
    
    //
    // Create a device object and register our dispatch handlers
    //
    NdisZeroMemory(&DeviceAttribute, sizeof(NDIS_DEVICE_OBJECT_ATTRIBUTES));
    
    DeviceAttribute.Header.Type = NDIS_OBJECT_TYPE_DEVICE_OBJECT_ATTRIBUTES;
    DeviceAttribute.Header.Revision = NDIS_DEVICE_OBJECT_ATTRIBUTES_REVISION_1;
    DeviceAttribute.Header.Size = sizeof(NDIS_DEVICE_OBJECT_ATTRIBUTES);
    
    DeviceAttribute.DeviceName = &DeviceName;
    DeviceAttribute.SymbolicName = &DeviceLinkUnicodeString;
    DeviceAttribute.MajorFunctions = &DispatchTable[0];
    DeviceAttribute.ExtensionSize = sizeof(FILTER_DEVICE_EXTENSION);
    
    Status = NdisRegisterDeviceEx(
                FilterDriverHandle,
                &DeviceAttribute,
                &DeviceObject,
                &NdisFilterDeviceHandle
                );
   
   
    if (Status == NDIS_STATUS_SUCCESS)
    {
		*Extension = FilterDeviceExtension = NdisGetDeviceReservedExtension(DeviceObject);
   
        FilterDeviceExtension->Signature = 'FTDR';
        FilterDeviceExtension->Handle = FilterDriverHandle;
		KeInitializeSpinLock(&FilterDeviceExtension->QLock);
		PRULES_LISTS FilterRules = ExAllocatePool(PagedPool, sizeof(RULES_LISTS));
		FilterRules->IsActive = FALSE;
		FilterRules->FirstRuleIPv4 = NULL;
		FilterRules->FirstRuleIPv6 = NULL;
		FilterDeviceExtension->FilterRules = FilterRules;

        //
        // Workaround NDIS bug
        //
        DriverObject = (PDRIVER_OBJECT)FilterDriverObject;
    }
              
        
    DEBUGP(DL_TRACE, "<==NDISFilterDriverRegisterDevice: %x\n", Status);
        
    return (Status);
        
}
示例#12
0
_Use_decl_annotations_                
NTSTATUS
NDISFilterDriverDeviceIoControl(
    PDEVICE_OBJECT        DeviceObject,
    PIRP                  Irp
    )
{
	DbgPrint("NDISFilterDriverDeviceIoControl\n");
    PIO_STACK_LOCATION          IrpSp;
    NTSTATUS                    Status = STATUS_SUCCESS;
    PFILTER_DEVICE_EXTENSION    FilterDeviceExtension;
    PUCHAR                      InputBuffer;
    PUCHAR                      OutputBuffer;
    ULONG                       InputBufferLength, OutputBufferLength;
    PLIST_ENTRY                 Link;
    PUCHAR                      pInfo;
    ULONG                       InfoLength = 0;
    PMS_FILTER                  pFilter = NULL;
    BOOLEAN                     bFalse = FALSE;


    UNREFERENCED_PARAMETER(DeviceObject);

	KIRQL OldIrql;

    IrpSp = IoGetCurrentIrpStackLocation(Irp);

    if (IrpSp->FileObject == NULL)
    {
        return(STATUS_UNSUCCESSFUL);
    }


    FilterDeviceExtension = (PFILTER_DEVICE_EXTENSION)NdisGetDeviceReservedExtension(DeviceObject);

    ASSERT(FilterDeviceExtension->Signature == 'FTDR');
    
    Irp->IoStatus.Information = 0;

	KeAcquireSpinLock(&FilterDeviceExtension->QLock, &OldIrql);
    switch (IrpSp->Parameters.DeviceIoControl.IoControlCode)
    {
		case IOCTL_ADD_IPV4_RULE:
			DbgPrint("IOCTL_ADD_IPV4_RULE BEGIN\n");
			InputBuffer = Irp->UserBuffer;
			InputBufferLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;
			if (InputBufferLength != sizeof(RULE_IPV4))
			{
				Status = NDIS_STATUS_FAILURE;
				break;
			}
			PRULE_IPV4 pRuleIPv4 = ExAllocatePool(NonPagedPool, sizeof(RULE_IPV4));
			RtlCopyMemory(pRuleIPv4, InputBuffer, InputBufferLength);
			AddIPv4Rule(FilterDeviceExtension, pRuleIPv4);
			DbgPrint("IOCTL_ADD_IPV4_RULE END\n");
			break;
		case IOCTL_DEL_IPV4_RULE:
			DbgPrint("IOCTL_DEL_IPV4_RULE BEGIN\n");
			InputBuffer = Irp->UserBuffer;
			InputBufferLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;
			if (InputBufferLength != sizeof(ULONG))
			{
				Status = NDIS_STATUS_FAILURE;
				break;
			}
			ULONG IdIPv4 = *((PULONG)(InputBuffer));
			DelIPv4Rule(FilterDeviceExtension, IdIPv4);
			DbgPrint("IOCTL_DEL_IPV4_RULE END\n");
			break;
		case IOCTL_ADD_IPV6_RULE:
			DbgPrint("IOCTL_ADD_IPV6_RULE BEGIN\n");
			InputBuffer = Irp->UserBuffer;
			InputBufferLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;
			if (InputBufferLength != sizeof(RULE_IPV6))
			{
				Status = NDIS_STATUS_FAILURE;
				break;
			}
			PRULE_IPV6 pRuleIPv6 = ExAllocatePool(NonPagedPool, sizeof(RULE_IPV6));
			RtlCopyMemory(pRuleIPv6, InputBuffer, InputBufferLength);
			AddIPv6Rule(FilterDeviceExtension, pRuleIPv6);
			DbgPrint("IOCTL_ADD_IPV6_RULE END\n");
			break;
		case IOCTL_DEL_IPV6_RULE:
			DbgPrint("IOCTL_DEL_IPV6_RULE BEGIN\n");
			InputBuffer = Irp->UserBuffer;
			InputBufferLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;
			if (InputBufferLength != sizeof(ULONG))
			{
				Status = NDIS_STATUS_FAILURE;
				break;
			}
			ULONG IdIPv6 = *((PULONG)(InputBuffer));
			DelIPv6Rule(FilterDeviceExtension, IdIPv6);
			DbgPrint("IOCTL_END_IPV6_RULE END\n");
			break;
		case IOCTL_ACTIVATE_FILTER:
			DbgPrint("IOCTL_ACTIVATE_FILTER BEGIN\n");
			InputBuffer = Irp->UserBuffer;
			InputBufferLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;
			if (InputBufferLength != 0)
			{
				Status = NDIS_STATUS_FAILURE;
				break;
			}
			ActivateRules(FilterDeviceExtension);
			DbgPrint("IOCTL_ACTIVATE_FILTER END\n");
			break;
		case IOCTL_DEACTIVATE_FILTER:
			DbgPrint("IOCTL_DEACTIVATE_FILTER BEGIN\n");
			InputBuffer = Irp->UserBuffer;
			InputBufferLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;
			if (InputBufferLength != 0)
			{
				Status = NDIS_STATUS_FAILURE;
				break;
			}
			DeactivateRules(FilterDeviceExtension);
			DbgPrint("IOCTL_DEACTIVATE_FILTER END\n");
			break;
        case IOCTL_FILTER_RESTART_ALL:
            break;

        case IOCTL_FILTER_RESTART_ONE_INSTANCE:
            InputBuffer = OutputBuffer = (PUCHAR)Irp->AssociatedIrp.SystemBuffer;
            InputBufferLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;

            pFilter = filterFindFilterModule (InputBuffer, InputBufferLength);

            if (pFilter == NULL)
            {
                
                break;
            }

            NdisFRestartFilter(pFilter->FilterHandle);

            break;

        case IOCTL_FILTER_ENUERATE_ALL_INSTANCES:
            
            InputBuffer = OutputBuffer = (PUCHAR)Irp->AssociatedIrp.SystemBuffer;
            InputBufferLength = IrpSp->Parameters.DeviceIoControl.InputBufferLength;
            OutputBufferLength = IrpSp->Parameters.DeviceIoControl.OutputBufferLength;
            
            
            pInfo = OutputBuffer;
            
            FILTER_ACQUIRE_LOCK(&FilterListLock, bFalse);
            
            Link = FilterModuleList.Flink;
            
            while (Link != &FilterModuleList)
            {
                pFilter = CONTAINING_RECORD(Link, MS_FILTER, FilterModuleLink);

                
                InfoLength += (pFilter->FilterModuleName.Length + sizeof(USHORT));
                        
                if (InfoLength <= OutputBufferLength)
                {
                    *(PUSHORT)pInfo = pFilter->FilterModuleName.Length;
                    NdisMoveMemory(pInfo + sizeof(USHORT), 
                                   (PUCHAR)(pFilter->FilterModuleName.Buffer),
                                   pFilter->FilterModuleName.Length);
                            
                    pInfo += (pFilter->FilterModuleName.Length + sizeof(USHORT));
                }
                
                Link = Link->Flink;
            }
               
            FILTER_RELEASE_LOCK(&FilterListLock, bFalse);
            if (InfoLength <= OutputBufferLength)
            {
       
                Status = NDIS_STATUS_SUCCESS;
            }
            //
            // Buffer is small
            //
            else
            {
                Status = STATUS_BUFFER_TOO_SMALL;
            }
            break;

             
        default:
            break;
    }
	KeReleaseSpinLock(&FilterDeviceExtension->QLock, OldIrql);
    Irp->IoStatus.Status = Status;
    Irp->IoStatus.Information = InfoLength;

    IoCompleteRequest(Irp, IO_NO_INCREMENT);

    return Status;
            

}