4 ** Written by Jason Filby (jasonfilby@yahoo.com)
5 ** For ReactOS (www.reactos.com)
7 ** Handles the keyboard and mouse on the PS/2 ports
9 ** TODO: Fix detect_ps2_port(void) so that it works under BOCHs
10 Implement mouse button support
14 #include <ddk/ntddk.h>
15 #include "../include/mouse.h"
20 MouseSynchronizeRoutine(PVOID Context)
22 PIRP Irp = (PIRP)Context;
23 PMOUSE_INPUT_DATA rec = (PMOUSE_INPUT_DATA)Irp->AssociatedIrp.SystemBuffer;
24 PIO_STACK_LOCATION stk = IoGetCurrentIrpStackLocation(Irp);
25 ULONG NrToRead = stk->Parameters.Read.Length/sizeof(MOUSE_INPUT_DATA);
28 if ((stk->Parameters.Read.Length/sizeof(MOUSE_INPUT_DATA))==NrToRead)
33 MouseDataRequired=stk->Parameters.Read.Length/sizeof(MOUSE_INPUT_DATA);
34 MouseDataRead=NrToRead;
41 PS2MouseStartIo(PDEVICE_OBJECT DeviceObject, PIRP Irp)
43 PDEVICE_EXTENSION DeviceExtension = DeviceObject->DeviceExtension;
45 if (KeSynchronizeExecution(DeviceExtension->MouseInterrupt, MouseSynchronizeRoutine, Irp))
47 Irp->IoStatus.Status = STATUS_SUCCESS;
48 Irp->IoStatus.Information = 0;
49 IoCompleteRequest(Irp, IO_NO_INCREMENT);
50 IoStartNextPacket(DeviceObject, FALSE);
55 PS2MouseDispatch(PDEVICE_OBJECT DeviceObject, PIRP Irp)
57 PIO_STACK_LOCATION stk = IoGetCurrentIrpStackLocation(Irp);
60 switch (stk->MajorFunction)
63 if (AlreadyOpened == TRUE)
65 Status = STATUS_SUCCESS;
69 Status = STATUS_SUCCESS;
75 Status = STATUS_SUCCESS;
79 DbgPrint("NOT IMPLEMENTED\n");
80 Status = STATUS_NOT_IMPLEMENTED;
84 if (Status==STATUS_PENDING)
86 IoMarkIrpPending(Irp);
90 Irp->IoStatus.Status = Status;
91 Irp->IoStatus.Information = 0;
92 IoCompleteRequest(Irp,IO_NO_INCREMENT);
97 VOID PS2MouseInitializeDataQueue(PVOID Context)
102 PS2MouseInternalDeviceControl(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
104 PDEVICE_EXTENSION DeviceExtension = DeviceObject->DeviceExtension;
105 PIO_STACK_LOCATION Stack = IoGetCurrentIrpStackLocation(Irp);
108 switch(Stack->Parameters.DeviceIoControl.IoControlCode)
110 case IOCTL_INTERNAL_MOUSE_CONNECT:
112 DeviceExtension->ClassInformation =
113 *((PCLASS_INFORMATION)Stack->Parameters.DeviceIoControl.Type3InputBuffer);
115 // Reinitialize the port input data queue synchronously
116 KeSynchronizeExecution(DeviceExtension->MouseInterrupt,
117 (PKSYNCHRONIZE_ROUTINE)PS2MouseInitializeDataQueue, DeviceExtension);
119 status = STATUS_SUCCESS;
123 status = STATUS_INVALID_DEVICE_REQUEST;
127 Irp->IoStatus.Status = status;
128 if (status == STATUS_PENDING) {
129 IoMarkIrpPending(Irp);
130 IoStartPacket(DeviceObject, Irp, NULL, NULL);
132 IoCompleteRequest(Irp, IO_NO_INCREMENT);
138 VOID PS2MouseIsrDpc(PKDPC Dpc, PDEVICE_OBJECT DeviceObject, PIRP Irp, PVOID Context)
140 PDEVICE_EXTENSION DeviceExtension = DeviceObject->DeviceExtension;
143 Queue = DeviceExtension->ActiveQueue % 2;
144 InterlockedIncrement(&DeviceExtension->ActiveQueue);
145 (*(PSERVICE_CALLBACK_ROUTINE)DeviceExtension->ClassInformation.CallBack)(
146 DeviceExtension->ClassInformation.DeviceObject,
147 DeviceExtension->MouseInputData[Queue],
149 &DeviceExtension->InputDataCount[Queue]);
150 DeviceExtension->InputDataCount[Queue] = 0;
154 DriverEntry(PDRIVER_OBJECT DriverObject, PUNICODE_STRING RegistryPath)
156 PDEVICE_OBJECT DeviceObject;
157 UNICODE_STRING DeviceName;
158 UNICODE_STRING SymlinkName;
159 PDEVICE_EXTENSION DeviceExtension;
161 if(detect_ps2_port() == TRUE)
164 return STATUS_UNSUCCESSFUL;
166 DriverObject->MajorFunction[IRP_MJ_CREATE] = PS2MouseDispatch;
167 DriverObject->MajorFunction[IRP_MJ_CLOSE] = PS2MouseDispatch;
168 DriverObject->MajorFunction[IRP_MJ_INTERNAL_DEVICE_CONTROL] = PS2MouseInternalDeviceControl;
169 DriverObject->DriverStartIo = PS2MouseStartIo;
171 RtlInitUnicodeStringFromLiteral(&DeviceName,
172 L"\\Device\\Mouse"); // FIXME: find correct device name
173 IoCreateDevice(DriverObject,
174 sizeof(DEVICE_EXTENSION),
176 FILE_DEVICE_SERIAL_MOUSE_PORT, // FIXME: this isn't really a serial mouse port driver
180 DeviceObject->Flags = DeviceObject->Flags | DO_BUFFERED_IO;
182 RtlInitUnicodeStringFromLiteral(&SymlinkName,
183 L"\\??\\Mouse"); // FIXME: find correct device name
184 IoCreateSymbolicLink(&SymlinkName, &DeviceName);
186 DeviceExtension = DeviceObject->DeviceExtension;
187 KeInitializeDpc(&DeviceExtension->IsrDpc, (PKDEFERRED_ROUTINE)PS2MouseIsrDpc, DeviceObject);
189 mouse_init(DeviceObject);
191 return(STATUS_SUCCESS);