1 /*
2  * Copyright (c) 1998-2000 Apple Computer, Inc. All rights reserved.
3  *
4  * @APPLE_LICENSE_HEADER_START@
5  *
6  * The contents of this file constitute Original Code as defined in and
7  * are subject to the Apple Public Source License Version 1.1 (the
8  * "License").  You may not use this file except in compliance with the
9  * License.  Please obtain a copy of the License at
10  * http://www.apple.com/publicsource and read it before using this file.
11  *
12  * This Original Code and all software distributed under the License are
13  * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
14  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
15  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
16  * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT.  Please see the
17  * License for the specific language governing rights and limitations
18  * under the License.
19  *
20  * @APPLE_LICENSE_HEADER_END@
21  */
22 /*
23 Copyright (c) 1999 Apple Computer, Inc.  All rights reserved.
24 
25 HISTORY
26     1999-4-15	Godfrey van der Linden(gvdl)
27         Created.
28 */
29 #include <IOKit/IOFilterInterruptEventSource.h>
30 #include <IOKit/IOService.h>
31 #include <IOKit/IOTimeStamp.h>
32 #include <IOKit/IOWorkLoop.h>
33 
34 #if KDEBUG
35 
36 #define IOTimeTypeStampS(t)						\
37 do {									\
38     IOTimeStampStart(IODBG_INTES(t),					\
39                      (unsigned int) this, (unsigned int) owner);	\
40 } while(0)
41 
42 #define IOTimeTypeStampE(t)						\
43 do {									\
44     IOTimeStampEnd(IODBG_INTES(t),					\
45                    (unsigned int) this, (unsigned int) owner);		\
46 } while(0)
47 
48 #define IOTimeStampLatency()						\
49 do {									\
50     IOTimeStampEnd(IODBG_INTES(IOINTES_LAT),				\
51                    (unsigned int) this, (unsigned int) owner);		\
52 } while(0)
53 
54 #else /* !KDEBUG */
55 #define IOTimeTypeStampS(t)
56 #define IOTimeTypeStampE(t)
57 #define IOTimeStampLatency()
58 #endif /* KDEBUG */
59 
60 #define super IOInterruptEventSource
61 
62 OSDefineMetaClassAndStructors
63     (IOFilterInterruptEventSource, IOInterruptEventSource)
64 OSMetaClassDefineReservedUnused(IOFilterInterruptEventSource, 0);
65 OSMetaClassDefineReservedUnused(IOFilterInterruptEventSource, 1);
66 OSMetaClassDefineReservedUnused(IOFilterInterruptEventSource, 2);
67 OSMetaClassDefineReservedUnused(IOFilterInterruptEventSource, 3);
68 OSMetaClassDefineReservedUnused(IOFilterInterruptEventSource, 4);
69 OSMetaClassDefineReservedUnused(IOFilterInterruptEventSource, 5);
70 OSMetaClassDefineReservedUnused(IOFilterInterruptEventSource, 6);
71 OSMetaClassDefineReservedUnused(IOFilterInterruptEventSource, 7);
72 
73 /*
74  * Implement the call throughs for the private protection conversion
75  */
76 bool IOFilterInterruptEventSource::init(OSObject *inOwner,
77                                         Action inAction,
78                                         IOService *inProvider,
79                                         int inIntIndex)
80 {
81     return false;
82 }
83 
84 IOInterruptEventSource *
85 IOFilterInterruptEventSource::interruptEventSource(OSObject *inOwner,
86                                                    Action inAction,
87                                                    IOService *inProvider,
88                                                    int inIntIndex)
89 {
90     return 0;
91 }
92 
93 bool
94 IOFilterInterruptEventSource::init(OSObject *inOwner,
95                                    Action inAction,
96                                    Filter inFilterAction,
97                                    IOService *inProvider,
98                                    int inIntIndex)
99 {
100     if ( !super::init(inOwner, inAction, inProvider, inIntIndex) )
101         return false;
102 
103     if (!inFilterAction)
104         return false;
105 
106     filterAction = inFilterAction;
107     return true;
108 }
109 
110 IOFilterInterruptEventSource *IOFilterInterruptEventSource
111 ::filterInterruptEventSource(OSObject *inOwner,
112                              Action inAction,
113                              Filter inFilterAction,
114                              IOService *inProvider,
115                              int inIntIndex)
116 {
117     IOFilterInterruptEventSource *me = new IOFilterInterruptEventSource;
118 
119     if (me
120     && !me->init(inOwner, inAction, inFilterAction, inProvider, inIntIndex)) {
121         me->release();
122         return 0;
123     }
124 
125     return me;
126 }
127 
128 void IOFilterInterruptEventSource::signalInterrupt()
129 {
130 IOTimeStampLatency();
131 
132     producerCount++;
133 
134 IOTimeTypeStampS(IOINTES_SEMA);
135     signalWorkAvailable();
136 IOTimeTypeStampE(IOINTES_SEMA);
137 }
138 
139 
140 IOFilterInterruptEventSource::Filter
141 IOFilterInterruptEventSource::getFilterAction() const
142 {
143     return filterAction;
144 }
145 
146 
147 
148 
149 void IOFilterInterruptEventSource::normalInterruptOccurred
150     (void */*refcon*/, IOService */*prov*/, int /*source*/)
151 {
152     bool filterRes;
153 
154 IOTimeTypeStampS(IOINTES_INTCTXT);
155 
156 IOTimeTypeStampS(IOINTES_INTFLTR);
157     IOTimeStampConstant(IODBG_INTES(IOINTES_FILTER),
158                         (unsigned int) filterAction, (unsigned int) owner);
159     filterRes = (*filterAction)(owner, this);
160 IOTimeTypeStampE(IOINTES_INTFLTR);
161 
162     if (filterRes)
163         signalInterrupt();
164 
165 IOTimeTypeStampE(IOINTES_INTCTXT);
166 }
167 
168 void IOFilterInterruptEventSource::disableInterruptOccurred
169     (void */*refcon*/, IOService *prov, int source)
170 {
171     bool filterRes;
172 
173 IOTimeTypeStampS(IOINTES_INTCTXT);
174 
175 IOTimeTypeStampS(IOINTES_INTFLTR);
176     IOTimeStampConstant(IODBG_INTES(IOINTES_FILTER),
177                         (unsigned int) filterAction, (unsigned int) owner);
178     filterRes = (*filterAction)(owner, this);
179 IOTimeTypeStampE(IOINTES_INTFLTR);
180 
181     if (filterRes) {
182         prov->disableInterrupt(source);	/* disable the interrupt */
183 
184         signalInterrupt();
185     }
186 IOTimeTypeStampE(IOINTES_INTCTXT);
187 }
188