54a5b9566cb35152f55029fab433b230b42d468c
[reactos.git] / reactos / drivers / video / videoprt / interrupt.c
1 /*
2 * VideoPort driver
3 *
4 * Copyright (C) 2002, 2003, 2004 ReactOS Team
5 *
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10 *
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19 *
20 */
21
22 #include "videoprt.h"
23
24 /* PRIVATE FUNCTIONS **********************************************************/
25
26 BOOLEAN NTAPI
27 IntVideoPortInterruptRoutine(
28 IN struct _KINTERRUPT *Interrupt,
29 IN PVOID ServiceContext)
30 {
31 PVIDEO_PORT_DEVICE_EXTENSION DeviceExtension = ServiceContext;
32
33 ASSERT(DeviceExtension->DriverExtension->InitializationData.HwInterrupt != NULL);
34
35 return DeviceExtension->DriverExtension->InitializationData.HwInterrupt(
36 &DeviceExtension->MiniPortDeviceExtension);
37 }
38
39 BOOLEAN NTAPI
40 IntVideoPortSetupInterrupt(
41 IN PDEVICE_OBJECT DeviceObject,
42 IN PVIDEO_PORT_DRIVER_EXTENSION DriverExtension,
43 IN PVIDEO_PORT_CONFIG_INFO ConfigInfo)
44 {
45 NTSTATUS Status;
46 PVIDEO_PORT_DEVICE_EXTENSION DeviceExtension;
47
48 DeviceExtension = (PVIDEO_PORT_DEVICE_EXTENSION)DeviceObject->DeviceExtension;
49
50 /*
51 * MSDN documentation for VIDEO_PORT_CONFIG_INFO states: "If a miniport driver's
52 * HwVidFindAdapter function finds that the video adapter does not generate
53 * interrupts or that it cannot determine a valid interrupt vector/level for
54 * the adapter, HwVidFindAdapter should set both BusInterruptVector and
55 * BusInterruptLevel to zero.
56 */
57
58 if (DriverExtension->InitializationData.HwInterrupt != NULL &&
59 (ConfigInfo->BusInterruptLevel != 0 ||
60 ConfigInfo->BusInterruptVector != 0))
61 {
62 ULONG InterruptVector;
63 KIRQL Irql;
64 KAFFINITY Affinity;
65
66 InterruptVector = HalGetInterruptVector(
67 ConfigInfo->AdapterInterfaceType,
68 ConfigInfo->SystemIoBusNumber,
69 ConfigInfo->BusInterruptLevel,
70 ConfigInfo->BusInterruptVector,
71 &Irql,
72 &Affinity);
73
74 if (InterruptVector == 0)
75 {
76 WARN_(VIDEOPRT, "HalGetInterruptVector failed\n");
77 return FALSE;
78 }
79
80 KeInitializeSpinLock(&DeviceExtension->InterruptSpinLock);
81 Status = IoConnectInterrupt(
82 &DeviceExtension->InterruptObject,
83 IntVideoPortInterruptRoutine,
84 DeviceExtension,
85 &DeviceExtension->InterruptSpinLock,
86 InterruptVector,
87 Irql,
88 Irql,
89 ConfigInfo->InterruptMode,
90 DeviceExtension->InterruptShared,
91 Affinity,
92 FALSE);
93
94 if (!NT_SUCCESS(Status))
95 {
96 WARN_(VIDEOPRT, "IoConnectInterrupt failed with status 0x%08x\n", Status);
97 return FALSE;
98 }
99 }
100
101 return TRUE;
102 }
103
104 /* PUBLIC FUNCTIONS ***********************************************************/
105
106 /*
107 * @implemented
108 */
109 VP_STATUS
110 NTAPI
111 VideoPortEnableInterrupt(IN PVOID HwDeviceExtension)
112 {
113 PVIDEO_PORT_DEVICE_EXTENSION DeviceExtension;
114 BOOLEAN InterruptValid;
115
116 /* Get the device extension */
117 DeviceExtension = VIDEO_PORT_GET_DEVICE_EXTENSION(HwDeviceExtension);
118
119 /* Fail if the driver didn't register an ISR */
120 if (!DeviceExtension->DriverExtension->InitializationData.HwInterrupt)
121 {
122 /* No ISR, no interrupts */
123 return ERROR_INVALID_FUNCTION;
124 }
125
126 /* Re-enable the interrupt and return */
127 InterruptValid = HalEnableSystemInterrupt(DeviceExtension->InterruptVector,
128 0,
129 DeviceExtension->InterruptLevel);
130
131 /* Make sure the interrupt was valid */
132 ASSERT(InterruptValid == TRUE);
133
134 /* Return to caller */
135 return NO_ERROR;
136 }
137
138 /*
139 * @implemented
140 */
141 VP_STATUS
142 NTAPI
143 VideoPortDisableInterrupt(IN PVOID HwDeviceExtension)
144 {
145 PVIDEO_PORT_DEVICE_EXTENSION DeviceExtension;
146
147 /* Get the device extension */
148 DeviceExtension = VIDEO_PORT_GET_DEVICE_EXTENSION(HwDeviceExtension);
149
150 /* Fail if the driver didn't register an ISR */
151 if (!DeviceExtension->DriverExtension->InitializationData.HwInterrupt)
152 {
153 /* No ISR, no interrupts */
154 return ERROR_INVALID_FUNCTION;
155 }
156
157 /* Disable the interrupt and return */
158 HalDisableSystemInterrupt(DeviceExtension->InterruptVector,
159 0);
160 return NO_ERROR;
161 }