⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ioctl.c

📁 usb to rs232 虚拟RS232串口驱动程序
💻 C
📖 第 1 页 / 共 3 页
字号:
			ntStatus = SerialStartPurge(
						deviceExtension,
						Irp
						);
			break;
		}
		case IOCTL_SERIAL_CONFIG_SIZE:
		{
			if (outputBufferLength != sizeof(ULONG) || ioBuffer == NULL)
				ntStatus = STATUS_INVALID_PARAMETER;
			else
			{
				*(PULONG)ioBuffer = 0;
				ntStatus = STATUS_SUCCESS;
			}
			break;
		}
		case IOCTL_SERIAL_CLR_DTR:
		{
			ntStatus = STATUS_SUCCESS;//NOT_IMPLEMENTED
			break;
		}
		case IOCTL_SERIAL_SET_DTR:
		{
			ntStatus = STATUS_SUCCESS;//NOT_IMPLEMENTED
			break;
		}
		case IOCTL_SERIAL_CLR_RTS:
		{
			ntStatus = STATUS_SUCCESS;//NOT_IMPLEMENTED
			break;
		}
		case IOCTL_SERIAL_SET_RTS:
		{
			ntStatus = STATUS_SUCCESS;//NOT_IMPLEMENTED
			break;
		}
		case IOCTL_SERIAL_GET_DTRRTS:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_GET_MODEM_CONTROL:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_GET_MODEMSTATUS:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_IMMEDIATE_CHAR:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_LSRMST_INSERT:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_RESET_DEVICE:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_SET_BREAK_OFF:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_SET_BREAK_ON:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_SET_FIFO_CONTROL:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_SET_MODEM_CONTROL:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}

		case IOCTL_SERIAL_SET_XOFF:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_SET_XON:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
		case IOCTL_SERIAL_XOFF_COUNTER:
		{
			ntStatus = STATUS_NOT_IMPLEMENTED;
			break;
		}
	}

    default:

        ntStatus =
            Irp->IoStatus.Status = STATUS_INVALID_PARAMETER;
    }
	Irp->IoStatus.Information = length;
	Irp->IoStatus.Status = ntStatus;
    IoCompleteRequest (Irp,
                       IO_NO_INCREMENT
                       );

    return ntStatus;

}




NTSTATUS
USB2COM_ResetDevice(
    IN PDEVICE_OBJECT DeviceObject
    )
/*++

Routine Description:
        Checks port status; if OK, return success and  do no more;
        If bad, attempt reset

Arguments:

    DeviceObject - pointer to the device object for this instance of the 82930
                    device.


Return Value:

    NT status code

--*/
{
    NTSTATUS ntStatus;
    ULONG portStatus;

    USB2COM_KdPrint(5,("Enter USB2COM_ResetDevice()\n"));
    
    //
    // Check the port state, if it is disabled we will need 
    // to re-enable it
    //
    ntStatus = USB2COM_GetPortStatus(DeviceObject, &portStatus);

    if (NT_SUCCESS(ntStatus) && !(portStatus & USBD_PORT_ENABLED) &&
        portStatus & USBD_PORT_CONNECTED) {
        //
        // port is disabled, attempt reset
        //
                USB2COM_KdPrint( DBGLVL_DEFAULT,("USB2COM_ResetDevice() will reset\n"));
        ntStatus = USB2COM_ResetParentPort(DeviceObject);
    }
        return ntStatus;
}



NTSTATUS
USB2COM_GetPortStatus(
    IN PDEVICE_OBJECT DeviceObject,
    IN PULONG PortStatus
    )
/*++

Routine Description:

    returns the port status for our device

Arguments:

Return Value:

    STATUS_SUCCESS if successful,
    STATUS_UNSUCCESSFUL otherwise

--*/
{
    NTSTATUS ntStatus, status = STATUS_SUCCESS;
    PIRP irp;
    KEVENT event;
    IO_STATUS_BLOCK ioStatus;
    PIO_STACK_LOCATION nextStack;
    PDEVICE_EXTENSION deviceExtension;

    USB2COM_KdPrint( DBGLVL_DEFAULT,("enter USB2COM_GetPortStatus\n"));

    deviceExtension = DeviceObject->DeviceExtension;

    *PortStatus = 0;

    //
    // issue a synchronous request
    //

    KeInitializeEvent(&event, NotificationEvent, FALSE);

    // IoBuildDeviceIoControlRequest allocates and sets up an IRP for a device control request
    irp = IoBuildDeviceIoControlRequest(
                IOCTL_INTERNAL_USB_GET_PORT_STATUS,
                deviceExtension->TopOfStackDeviceObject, //next-lower driver's device object, representing the target device.
                NULL, // no input or output buffers
                0,
                NULL,
                0,
                TRUE, // internal ( use IRP_MJ_INTERNAL_DEVICE_CONTROL )
                &event, // event to be signalled on completion ( we wait for it below )
                &ioStatus);

    //
    // Call the class driver to perform the operation.  If the returned status
    // is PENDING, wait for the request to complete.
    //

    // IoGetNextIrpStackLocation gives a higher level driver access to the next-lower 
    // driver's I/O stack location in an IRP so the caller can set it up for the lower driver.
    nextStack = IoGetNextIrpStackLocation(irp);
    USB2COM_ASSERT(nextStack != NULL);

    nextStack->Parameters.Others.Argument1 = PortStatus;

    USB2COM_KdPrint( DBGLVL_DEFAULT,("USB2COM_GetPortStatus() calling USBD port status api\n"));

    ntStatus = IoCallDriver(deviceExtension->TopOfStackDeviceObject,
                            irp);

    USB2COM_KdPrint( DBGLVL_DEFAULT,("USB2COM_GetPortStatus() return from IoCallDriver USBD %x\n", ntStatus));

    if (ntStatus == STATUS_PENDING) {

        USB2COM_KdPrint( DBGLVL_DEFAULT,("Wait for single object\n"));

        status = KeWaitForSingleObject(
                       &event,
                       Suspended,
                       KernelMode,
                       FALSE,
                       NULL);

        USB2COM_KdPrint( DBGLVL_DEFAULT,("USB2COM_GetPortStatus() Wait for single object, returned %x\n", status));
        
    } else {
        ioStatus.Status = ntStatus;
    }

    USB2COM_KdPrint( DBGLVL_DEFAULT,("USB2COM_GetPortStatus() Port status = %x\n", *PortStatus));

    //
    // USBD maps the error code for us
    //
    ntStatus = ioStatus.Status;

    USB2COM_KdPrint( DBGLVL_DEFAULT,("Exit USB2COM_GetPortStatus (%x)\n", ntStatus));


    return ntStatus;
}


NTSTATUS
USB2COM_ResetParentPort(
    IN IN PDEVICE_OBJECT DeviceObject
    )
/*++

Routine Description:

    Reset the our parent port

Arguments:

Return Value:

    STATUS_SUCCESS if successful,
    STATUS_UNSUCCESSFUL otherwise

--*/
{
    NTSTATUS ntStatus, status = STATUS_SUCCESS;
    PIRP irp;
    KEVENT event;
    IO_STATUS_BLOCK ioStatus;
    PIO_STACK_LOCATION nextStack;
    PDEVICE_EXTENSION deviceExtension;

    USB2COM_KdPrint( DBGLVL_DEFAULT,("enter USB2COM_ResetParentPort\n"));

    deviceExtension = DeviceObject->DeviceExtension;

    //
    // issue a synchronous request
    //

    KeInitializeEvent(&event, NotificationEvent, FALSE);

    irp = IoBuildDeviceIoControlRequest(
                IOCTL_INTERNAL_USB_RESET_PORT,
                deviceExtension->TopOfStackDeviceObject,
                NULL,
                0,
                NULL,
                0,
                TRUE, // internal ( use IRP_MJ_INTERNAL_DEVICE_CONTROL )
                &event,
                &ioStatus);

    //
    // Call the class driver to perform the operation.  If the returned status
    // is PENDING, wait for the request to complete.
    //

    nextStack = IoGetNextIrpStackLocation(irp);
    USB2COM_ASSERT(nextStack != NULL);

    USB2COM_KdPrint( DBGLVL_DEFAULT,("USB2COM_ResetParentPort() calling USBD enable port api\n"));

    ntStatus = IoCallDriver(deviceExtension->TopOfStackDeviceObject,
                            irp);
                            
    USB2COM_KdPrint( DBGLVL_DEFAULT,("USB2COM_ResetParentPort() return from IoCallDriver USBD %x\n", ntStatus));

    if (ntStatus == STATUS_PENDING) {

        USB2COM_KdPrint( DBGLVL_DEFAULT,("USB2COM_ResetParentPort() Wait for single object\n"));

        status = KeWaitForSingleObject(
                       &event,
                       Suspended,
                       KernelMode,
                       FALSE,
                       NULL);

        USB2COM_KdPrint( DBGLVL_DEFAULT,("USB2COM_ResetParentPort() Wait for single object, returned %x\n", status));
        
    } else {
        ioStatus.Status = ntStatus;
    }

    //
    // USBD maps the error code for us
    //
    ntStatus = ioStatus.Status;

    USB2COM_KdPrint( DBGLVL_DEFAULT,("Exit USB2COM_ResetPort (%x)\n", ntStatus));

    return ntStatus;
}





⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -