14 #define IO_METHOD_FROM_CTL_CODE(ctlCode) (ctlCode&0x00000003) 30 *BufferIn = *BufferOut =
Irp->AssociatedIrp.SystemBuffer;
34 *BufferIn =
Irp->AssociatedIrp.SystemBuffer;
39 *BufferOut =
Irp->UserBuffer;
69 TRACE_(SERIAL,
"SerialSetBaudRate(COM%lu, %lu Bauds)\n", DeviceExtension->ComPort, BaudRate);
83 DeviceExtension->BaudRate = BaudRate;
99 TRACE_(SERIAL,
"SerialSetLineControl(COM%lu, Settings { %lu %lu %lu })\n",
100 DeviceExtension->ComPort, NewSettings->StopBits, NewSettings->Parity, NewSettings->WordLength);
103 switch (NewSettings->WordLength)
112 if (NewSettings->WordLength < 5 || NewSettings->WordLength > 8)
115 switch (NewSettings->Parity)
125 switch (NewSettings->StopBits)
131 if (NewSettings->WordLength != 5)
136 if (NewSettings->WordLength < 6 || NewSettings->WordLength > 8)
145 ComPortBase =
ULongToPtr(DeviceExtension->BaseAddress);
156 DeviceExtension->SerialLineControl = *NewSettings;
205 pCommProp->PacketVersion = 2;
207 pCommProp->MaxTxQueue = pCommProp->CurrentTxQueue = DeviceExtension->OutputBuffer.Length - 1;
208 pCommProp->MaxRxQueue = pCommProp->CurrentRxQueue = DeviceExtension->InputBuffer.Length - 1;
222 if (DeviceExtension->UartType >=
Uart16450)
226 if (DeviceExtension->UartType >=
Uart16550)
235 pCommProp->ProvSpec2 = 0;
250 pSerialStatus->Errors = 0;
251 if (DeviceExtension->BreakInterruptErrorCount)
253 if (DeviceExtension->SerialPerfStats.FrameErrorCount)
255 if (DeviceExtension->SerialPerfStats.SerialOverrunErrorCount)
257 if (DeviceExtension->SerialPerfStats.BufferOverrunErrorCount)
259 if (DeviceExtension->SerialPerfStats.ParityErrorCount)
262 pSerialStatus->HoldReasons = 0;
265 pSerialStatus->AmountInInQueue = (DeviceExtension->InputBuffer.WritePosition + DeviceExtension->InputBuffer.Length
266 - DeviceExtension->InputBuffer.ReadPosition) % DeviceExtension->InputBuffer.Length;
270 pSerialStatus->AmountInOutQueue = (DeviceExtension->OutputBuffer.WritePosition + DeviceExtension->OutputBuffer.Length
271 - DeviceExtension->OutputBuffer.ReadPosition) % DeviceExtension->OutputBuffer.Length;
274 pSerialStatus->EofReceived =
FALSE;
275 pSerialStatus->WaitForImmediate =
FALSE;
288 ULONG LengthIn, LengthOut;
290 PVOID BufferIn, BufferOut;
294 TRACE_(SERIAL,
"IRP_MJ_DEVICE_CONTROL dispatch\n");
297 LengthIn =
Stack->Parameters.DeviceIoControl.InputBufferLength;
298 LengthOut =
Stack->Parameters.DeviceIoControl.OutputBufferLength;
310 TRACE_(SERIAL,
"IOCTL_SERIAL_CLEAR_STATS\n");
320 TRACE_(SERIAL,
"IOCTL_SERIAL_CLR_DTR\n");
334 TRACE_(SERIAL,
"IOCTL_SERIAL_CLR_RTS\n");
350 TRACE_(SERIAL,
"IOCTL_SERIAL_CONFIG_SIZE\n");
351 if (LengthOut !=
sizeof(
ULONG) || BufferOut ==
NULL)
355 pConfigSize = (
PULONG)BufferOut;
364 TRACE_(SERIAL,
"IOCTL_SERIAL_GET_BAUD_RATE\n");
367 else if (BufferOut ==
NULL)
381 ERR_(SERIAL,
"IOCTL_SERIAL_GET_CHARS not implemented.\n");
384 else if (BufferOut ==
NULL)
402 TRACE_(SERIAL,
"IOCTL_SERIAL_GET_COMMSTATUS\n");
405 else if (BufferOut ==
NULL)
417 TRACE_(SERIAL,
"IOCTL_SERIAL_GET_DTRRTS\n");
418 if (LengthOut !=
sizeof(
ULONG) || BufferOut ==
NULL)
422 pDtrRts = (
PULONG)BufferOut;
437 ERR_(SERIAL,
"IOCTL_SERIAL_GET_HANDFLOW not implemented.\n");
440 else if (BufferOut ==
NULL)
456 TRACE_(SERIAL,
"IOCTL_SERIAL_GET_LINE_CONTROL\n");
459 else if (BufferOut ==
NULL)
472 TRACE_(SERIAL,
"IOCTL_SERIAL_GET_MODEM_CONTROL\n");
473 if (LengthOut !=
sizeof(
ULONG) || BufferOut ==
NULL)
478 *pMCR = DeviceExtension->
MCR;
487 TRACE_(SERIAL,
"IOCTL_SERIAL_GET_MODEMSTATUS\n");
488 if (LengthOut !=
sizeof(
ULONG) || BufferOut ==
NULL)
493 *pMSR = DeviceExtension->
MSR;
501 TRACE_(SERIAL,
"IOCTL_SERIAL_GET_PROPERTIES\n");
504 else if (BufferOut ==
NULL)
515 TRACE_(SERIAL,
"IOCTL_SERIAL_GET_STATS\n");
518 else if (BufferOut ==
NULL)
531 TRACE_(SERIAL,
"IOCTL_SERIAL_GET_TIMEOUTS\n");
545 TRACE_(SERIAL,
"IOCTL_SERIAL_GET_WAIT_MASK\n");
546 if (LengthOut !=
sizeof(
ULONG) || BufferOut ==
NULL)
550 pWaitMask = (
PULONG)BufferOut;
551 *pWaitMask = DeviceExtension->
WaitMask;
560 ERR_(SERIAL,
"IOCTL_SERIAL_IMMEDIATE_CHAR not implemented.\n");
567 ERR_(SERIAL,
"IOCTL_SERIAL_LSRMST_INSERT not implemented.\n");
574 TRACE_(SERIAL,
"IOCTL_SERIAL_PURGE\n");
577 if (LengthIn !=
sizeof(
ULONG) || BufferIn ==
NULL)
624 ERR_(SERIAL,
"IOCTL_SERIAL_RESET_DEVICE not implemented.\n");
631 TRACE_(SERIAL,
"IOCTL_SERIAL_SET_BAUD_RATE\n");
632 if (LengthIn !=
sizeof(
ULONG) || BufferIn ==
NULL)
636 pNewBaudRate = (
PULONG)BufferIn;
644 ERR_(SERIAL,
"IOCTL_SERIAL_SET_BREAK_OFF not implemented.\n");
651 ERR_(SERIAL,
"IOCTL_SERIAL_SET_BREAK_ON not implemented.\n");
658 ERR_(SERIAL,
"IOCTL_SERIAL_SET_CHARS not implemented.\n");
666 TRACE_(SERIAL,
"IOCTL_SERIAL_SET_DTR\n");
683 TRACE_(SERIAL,
"IOCTL_SERIAL_SET_FIFO_CONTROL\n");
684 if (LengthIn !=
sizeof(
ULONG) || BufferIn ==
NULL)
700 ERR_(SERIAL,
"IOCTL_SERIAL_SET_HANDFLOW not implemented.\n");
706 TRACE_(SERIAL,
"IOCTL_SERIAL_SET_LINE_CONTROL\n");
709 else if (BufferIn ==
NULL)
718 TRACE_(SERIAL,
"IOCTL_SERIAL_SET_MODEM_CONTROL\n");
719 if (LengthIn !=
sizeof(
ULONG) || BufferIn ==
NULL)
727 DeviceExtension->
MCR = (
UCHAR)(*pMCR & 0xff);
738 else if (BufferIn ==
NULL)
764 TRACE_(SERIAL,
"IOCTL_SERIAL_SET_RTS\n");
781 TRACE_(SERIAL,
"IOCTL_SERIAL_SET_TIMEOUTS\n");
794 TRACE_(SERIAL,
"IOCTL_SERIAL_SET_WAIT_MASK\n");
796 if (LengthIn !=
sizeof(
ULONG) || BufferIn ==
NULL)
800 WARN_(SERIAL,
"An IRP is already currently processed\n");
805 DeviceExtension->
WaitMask = *pWaitMask;
813 ERR_(SERIAL,
"IOCTL_SERIAL_SET_XOFF not implemented.\n");
820 ERR_(SERIAL,
"IOCTL_SERIAL_SET_XON not implemented.\n");
827 TRACE_(SERIAL,
"IOCTL_SERIAL_WAIT_ON_MASK\n");
829 if (LengthOut !=
sizeof(
ULONG) || BufferOut ==
NULL)
841 if (WaitingIrp !=
NULL)
844 WARN_(SERIAL,
"Unable to pend a second IRP for IOCTL_SERIAL_WAIT_ON_MASK\n");
845 Irp->IoStatus.Information = 0;
856 ERR_(SERIAL,
"IOCTL_SERIAL_XOFF_COUNTER not implemented.\n");
863 TRACE_(SERIAL,
"Unknown IOCTL code 0x%x\n",
Stack->Parameters.DeviceIoControl.IoControlCode);
#define SERIAL_PURGE_TXCLEAR
NTSTATUS NTAPI SerialSetLineControl(IN PSERIAL_DEVICE_EXTENSION DeviceExtension, IN PSERIAL_LINE_CONTROL NewSettings)
#define SERIAL_PARITY_NONE
struct _SERIAL_HANDFLOW SERIAL_HANDFLOW
#define SERIAL_PURGE_RXCLEAR
#define SERIAL_SP_DATABITS
#define SERIAL_ERROR_PARITY
CIRCULAR_BUFFER OutputBuffer
#define SERIAL_PCF_INTTIMEOUTS
struct _SERIAL_BAUD_RATE * PSERIAL_BAUD_RATE
#define IOCTL_SERIAL_RESET_DEVICE
#define READ_PORT_UCHAR(p)
struct _SERIALPERF_STATS SERIALPERF_STATS
#define IOCTL_SERIAL_SET_BAUD_RATE
#define SERIAL_STOPBITS_15
#define STATUS_INVALID_PARAMETER
#define IOCTL_SERIAL_SET_FIFO_CONTROL
#define SERIAL_PARITY_EVEN
SERIAL_LINE_CONTROL SerialLineControl
#define SERIAL_STOPBITS_20
#define SERIAL_PCF_TOTALTIMEOUTS
#define IoReleaseRemoveLock(_RemoveLock, _Tag)
#define SERIAL_STOPBITS_10
VOID NTAPI KeAcquireSpinLock(PKSPIN_LOCK SpinLock, PKIRQL OldIrql)
struct _SERIAL_LINE_CONTROL * PSERIAL_LINE_CONTROL
#define IOCTL_SERIAL_CLR_RTS
struct _SERIAL_STATUS SERIAL_STATUS
#define SERIAL_BAUD_38400
#define SERIAL_PCF_DTRDSR
#define SERIAL_PCF_SPECIALCHARS
struct _SERIAL_COMMPROP SERIAL_COMMPROP
KSPIN_LOCK InputBufferLock
#define SERIAL_BAUD_134_5
#define MmGetSystemAddressForMdlSafe(_Mdl, _Priority)
#define SERIAL_SP_STOPBITS
_In_ WDFREQUEST _In_ NTSTATUS _In_ ULONG_PTR Information
#define STATUS_BUFFER_TOO_SMALL
#define IOCTL_SERIAL_SET_LINE_CONTROL
SERIAL_TIMEOUTS SerialTimeOuts
#define IOCTL_SERIAL_SET_DTR
_In_ WDFREQUEST _In_ PIO_STACK_LOCATION Stack
_In_ PDEVICE_OBJECT DeviceObject
#define IOCTL_SERIAL_SET_WAIT_MASK
return STATUS_NOT_IMPLEMENTED
KSPIN_LOCK OutputBufferLock
#define IOCTL_SERIAL_GET_LINE_CONTROL
NTSTATUS(* NTAPI)(IN PFILE_FULL_EA_INFORMATION EaBuffer, IN ULONG EaLength, OUT PULONG ErrorOffset)
#define SR_FCR_CLEAR_XMIT
#define SERIAL_ERROR_OVERRUN
NTSTATUS IncreaseCircularBufferSize(IN PCIRCULAR_BUFFER pBuffer, IN ULONG NewBufferSize)
#define IOCTL_SERIAL_GET_MODEMSTATUS
#define IOCTL_SERIAL_PURGE
#define SERIAL_PCF_RTSCTS
struct _SERIAL_LINE_CONTROL SERIAL_LINE_CONTROL
SERIALPERF_STATS SerialPerfStats
#define InterlockedCompareExchangePointer
#define IOCTL_SERIAL_SET_BREAK_ON
#define IoCompleteRequest
static NTSTATUS SerialGetCommProp(OUT PSERIAL_COMMPROP pCommProp, IN PSERIAL_DEVICE_EXTENSION DeviceExtension)
#define IOCTL_SERIAL_SET_XOFF
#define COMMPROP_INITIALIZED
#define SERIAL_ERROR_BREAK
#define IOCTL_SERIAL_XOFF_COUNTER
#define IOCTL_SERIAL_CONFIG_SIZE
ULONG BreakInterruptErrorCount
#define METHOD_OUT_DIRECT
NTSTATUS NTAPI SerialSetBaudRate(IN PSERIAL_DEVICE_EXTENSION DeviceExtension, IN ULONG NewBaudRate)
struct _SERIAL_HANDFLOW * PSERIAL_HANDFLOW
#define SERIAL_BAUD_57600
static NTSTATUS SerialGetCommStatus(OUT PSERIAL_STATUS pSerialStatus, IN PSERIAL_DEVICE_EXTENSION DeviceExtension)
#define NT_SUCCESS(StatCode)
static VOID SerialGetUserBuffers(IN PIRP Irp, IN ULONG IoControlCode, OUT PVOID *BufferIn, OUT PVOID *BufferOut)
#define SERIAL_ERROR_QUEUEOVERRUN
#define SERIAL_BAUD_19200
#define IOCTL_SERIAL_GET_WAIT_MASK
#define SERIAL_SP_SERIALCOMM
struct _SERIAL_TIMEOUTS * PSERIAL_TIMEOUTS
PDEVICE_OBJECT DeviceObject
static BOOLEAN NTAPI SerialClearPerfStats(IN PVOID SynchronizeContext)
static BOOLEAN NTAPI SerialGetPerfStats(IN PVOID SynchronizeContext)
#define SERIAL_PCF_XONXOFF
#define IOCTL_SERIAL_SET_XON
#define SERIAL_PCF_SETXCHAR
#define SERIAL_PARITY_SPACE
#define IOCTL_SERIAL_GET_DTRRTS
#define WRITE_PORT_UCHAR(p, d)
#define IOCTL_SERIAL_GET_CHARS
#define IOCTL_SERIAL_GET_TIMEOUTS
_In_ WDFREQUEST _In_ size_t _In_ size_t _In_ ULONG IoControlCode
#define IOCTL_SERIAL_GET_PROPERTIES
#define IOCTL_SERIAL_LSRMST_INSERT
#define IOCTL_SERIAL_GET_STATS
#define SERIAL_PCF_PARITY_CHECK
#define IOCTL_SERIAL_SET_CHARS
IO_REMOVE_LOCK RemoveLock
#define IOCTL_SERIAL_IMMEDIATE_CHAR
#define SERIAL_ERROR_FRAMING
struct _SERIAL_CHARS SERIAL_CHARS
_In_ PKSYNCHRONIZE_ROUTINE _In_opt_ __drv_aliasesMem PVOID SynchronizeContext
#define IOCTL_SERIAL_GET_HANDFLOW
__drv_aliasesMem FORCEINLINE PIO_STACK_LOCATION IoGetCurrentIrpStackLocation(_In_ PIRP Irp)
#define SR_FCR_CLEAR_RCVR
#define SERIAL_BAUD_14400
#define IOCTL_SERIAL_CLR_DTR
struct _SERIAL_DEVICE_EXTENSION * PSERIAL_DEVICE_EXTENSION
struct _SERIAL_BAUD_RATE SERIAL_BAUD_RATE
#define SERIAL_PARITY_MARK
#define SERIAL_DATABITS_7
#define IOCTL_SERIAL_SET_HANDFLOW
#define IOCTL_SERIAL_GET_COMMSTATUS
NTSTATUS NTAPI IoCallDriver(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
#define KeReleaseSpinLock(sl, irql)
#define IOCTL_SERIAL_SET_MODEM_CONTROL
#define IoSkipCurrentIrpStackLocation(Irp)
#define IOCTL_SERIAL_GET_MODEM_CONTROL
#define SERIAL_PARITY_ODD
#define SERIAL_DATABITS_5
#define IOCTL_SERIAL_WAIT_ON_MASK
#define SERIAL_BAUD_115200
struct _SERIAL_CHARS * PSERIAL_CHARS
#define IOCTL_SERIAL_SET_QUEUE_SIZE
CIRCULAR_BUFFER InputBuffer
#define IOCTL_SERIAL_CLEAR_STATS
#define SERIAL_DATABITS_6
#define RtlZeroMemory(Destination, Length)
BOOLEAN NTAPI KeSynchronizeExecution(IN OUT PKINTERRUPT Interrupt, IN PKSYNCHRONIZE_ROUTINE SynchronizeRoutine, IN PVOID SynchronizeContext OPTIONAL)
#define RtlCopyMemory(Destination, Source, Length)
PDEVICE_OBJECT LowerDevice
#define IOCTL_SERIAL_SET_RTS
#define IOCTL_SERIAL_SET_BREAK_OFF
#define SERIAL_DATABITS_8
struct _NAMED_PIPE_CREATE_PARAMETERS * Parameters
#define SERIAL_SP_PARITY_CHECK
NTSTATUS NTAPI SerialDeviceControl(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
#define IoAcquireRemoveLock(RemoveLock, Tag)
#define IOCTL_SERIAL_GET_BAUD_RATE
struct _SERIAL_QUEUE_SIZE * PSERIAL_QUEUE_SIZE
#define SERIAL_SP_HANDSHAKING
#define IOCTL_SERIAL_SET_TIMEOUTS
#define IO_METHOD_FROM_CTL_CODE(ctlCode)