You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
148 lines
4.5 KiB
148 lines
4.5 KiB
|
|
#include "precomp.h" // Precompiled header
|
|
|
|
/************************************************************************/
|
|
/* */
|
|
/* Title : Dispatch Entry for INTERNAL IOCTLs */
|
|
/* */
|
|
/* Author : N.P.Vassallo */
|
|
/* */
|
|
/* Creation : 14th October 1998 */
|
|
/* */
|
|
/* Version : 1.0.0 */
|
|
/* */
|
|
/* Description : Internal IOCTLs support the SERENUM */
|
|
/* attached serial device enumerator: */
|
|
/* IOCTL_SERIAL_INTERNAL_BASIC_SETTINGS */
|
|
/* IOCTL_SERIAL_INTERNAL_RESTORE_SETTINGS */
|
|
/* */
|
|
/************************************************************************/
|
|
|
|
/* History...
|
|
|
|
1.0.0 14/20/98 NPV Creation.
|
|
|
|
*/
|
|
|
|
#define FILE_ID SPX_IIOC_C // File ID for Event Logging see SPX_DEFS.H for values.
|
|
|
|
|
|
|
|
/*****************************************************************************
|
|
********************** ***********************
|
|
********************** Spx_SerialInternalIoControl ***********************
|
|
********************** ***********************
|
|
******************************************************************************
|
|
|
|
prototype: NTSTATUS Spx_SerialInternalIoControl(IN PDEVICE_OBJECT pDevObj, IN PIRP pIrp)
|
|
|
|
description: Internal IOCTL dipatch routine.
|
|
These IOCTLs are only issued from know trusted system components such as
|
|
the SERENUM.SYS attached serial device enumerator and the mouse driver:
|
|
|
|
parameters: pDevObj points to the device object structure
|
|
pIrp points to the IOCTL Irp packet
|
|
|
|
returns: STATUS_SUCCESS
|
|
|
|
*/
|
|
|
|
NTSTATUS Spx_SerialInternalIoControl(IN PDEVICE_OBJECT pDevObj, IN PIRP pIrp)
|
|
{
|
|
NTSTATUS status;
|
|
PIO_STACK_LOCATION pIrpStack;
|
|
PPORT_DEVICE_EXTENSION pPort = pDevObj->DeviceExtension;
|
|
KIRQL OldIrql;
|
|
|
|
SpxDbgMsg(SPX_TRACE_IRP_PATH,("%s[card=%d,port=%d]: Internal IOCTL Dispatch Entry\n",
|
|
PRODUCT_NAME, pPort->pParentCardExt->CardNumber, pPort->PortNumber));
|
|
|
|
if(SerialCompleteIfError(pDevObj, pIrp) != STATUS_SUCCESS)
|
|
return(STATUS_CANCELLED);
|
|
|
|
pIrpStack = IoGetCurrentIrpStackLocation(pIrp);
|
|
pIrp->IoStatus.Information = 0L;
|
|
status = STATUS_SUCCESS;
|
|
|
|
switch(pIrpStack->Parameters.DeviceIoControl.IoControlCode)
|
|
{
|
|
case IOCTL_SERIAL_INTERNAL_BASIC_SETTINGS:
|
|
case IOCTL_SERIAL_INTERNAL_RESTORE_SETTINGS:
|
|
{
|
|
SERIAL_BASIC_SETTINGS Basic;
|
|
PSERIAL_BASIC_SETTINGS pBasic;
|
|
SERIAL_IOCTL_SYNC S;
|
|
|
|
if (pIrpStack->Parameters.DeviceIoControl.IoControlCode
|
|
== IOCTL_SERIAL_INTERNAL_BASIC_SETTINGS)
|
|
{
|
|
|
|
/* Check the buffer size... */
|
|
|
|
if(pIrpStack->Parameters.DeviceIoControl.OutputBufferLength
|
|
< sizeof(SERIAL_BASIC_SETTINGS))
|
|
{
|
|
status = STATUS_BUFFER_TOO_SMALL;
|
|
break;
|
|
}
|
|
|
|
/* Everything is 0 -- timeouts and flow control. */
|
|
/* If we add additional features, this zero memory method may not work. */
|
|
|
|
RtlZeroMemory(&Basic,sizeof(SERIAL_BASIC_SETTINGS));
|
|
pIrp->IoStatus.Information = sizeof(SERIAL_BASIC_SETTINGS);
|
|
pBasic = (PSERIAL_BASIC_SETTINGS)pIrp->AssociatedIrp.SystemBuffer;
|
|
|
|
/* Save off the old settings... */
|
|
|
|
RtlCopyMemory(&pBasic->Timeouts, &pPort->Timeouts, sizeof(SERIAL_TIMEOUTS));
|
|
RtlCopyMemory(&pBasic->HandFlow, &pPort->HandFlow, sizeof(SERIAL_HANDFLOW));
|
|
|
|
/* Point to our new settings... */
|
|
|
|
pBasic = &Basic;
|
|
}
|
|
else
|
|
{
|
|
if(pIrpStack->Parameters.DeviceIoControl.InputBufferLength < sizeof(SERIAL_BASIC_SETTINGS))
|
|
{
|
|
status = STATUS_BUFFER_TOO_SMALL;
|
|
break;
|
|
}
|
|
|
|
pBasic = (PSERIAL_BASIC_SETTINGS)pIrp->AssociatedIrp.SystemBuffer;
|
|
}
|
|
|
|
KeAcquireSpinLock(&pPort->ControlLock,&OldIrql);
|
|
|
|
/* Set the timeouts... */
|
|
|
|
RtlCopyMemory(&pPort->Timeouts, &pBasic->Timeouts, sizeof(SERIAL_TIMEOUTS));
|
|
|
|
/* Set flowcontrol... */
|
|
|
|
S.pPort = pPort;
|
|
S.Data = &pBasic->HandFlow;
|
|
XXX_SetHandFlow(pPort, &S); /* Set the handflow for specific hardware */
|
|
|
|
KeReleaseSpinLock(&pPort->ControlLock, OldIrql);
|
|
break;
|
|
}
|
|
|
|
default:
|
|
status = STATUS_INVALID_PARAMETER;
|
|
break;
|
|
}
|
|
|
|
pIrp->IoStatus.Status = status;
|
|
|
|
SpxDbgMsg(SPX_TRACE_IRP_PATH,("%s[card=%d,port=%d]: Internal IOCTL Dispatch Complete\n",
|
|
PRODUCT_NAME, pPort->pParentCardExt->CardNumber, pPort->PortNumber));
|
|
|
|
IoCompleteRequest(pIrp,0);
|
|
|
|
return(status);
|
|
|
|
} /* Spx_SerialInternalIoControl */
|
|
|
|
/* End of SPX_IIOC.C */
|