1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31
32 33 34 35
36 package ti.sysbios.hal;
37
38 import xdc.runtime.Error;
39
40 /*!
41 * ======== Hwi ========
42 * Hardware Interrupt Manager Proxy.
43 *
44 * This module provides APIs for managing hardware interrupts.
45 * These APIs are generic across all supported targets and devices
46 * and should provide sufficient functionality for most applications.
47 *
48 * The actual implementations of the Hwi module APIs are
49 * provided by the Hwi module delegates.
50 * Additional, family-specific Hwi module APIs may also be provided by
51 * the Hwi module delegates.
52 * See the list of
53 * {@link ./../family/doc-files/delegates.html Delegate Mappings}
54 * to determine which Hwi delegate is used
55 * for your target/device.
56 *
57 * You can statically or dynamically assign functions that run when
58 * specific hardware interrupts occur. Dynamic assignment of Hwi
59 * functions to interrupts at run-time is done
60 * using the {@link #create Hwi_create} function.
61 *
62 * Interrupt routines can be written completely in C, completely in
63 * assembly, or in a mix of C and assembly. In order to support interrupt
64 * routines
65 * written completely in C, an interrupt dispatcher is provided that performs
66 * the requisite prolog and epilog for an interrupt routine.
67 *
68 * Some routines are assigned to interrupts by the other SYS/BIOS
69 * modules. For example, the
70 * {@line ti.sysbios.knl.Clock} module configures its own timer interrupt
71 * handler.
72 *
73 * @p(html)
74 * <h3> Calling Context </h3>
75 * <table border="1" cellpadding="3">
76 * <colgroup span="1"></colgroup> <colgroup span="5" align="center">
77 * </colgroup>
78 *
79 * <tr><th> Function </th><th> Hwi </th><th> Swi </th>
80 * <th> Task </th><th> Main </th><th> Startup </th></tr>
81 * <!-- -->
82 * <tr><td> {@link #clearInterrupt} </td><td> Y </td><td> Y </td>
83 * <td> Y </td><td> Y </td><td> Y </td></tr>
84 * <tr><td> {@link #create} </td><td> N </td><td> N </td>
85 * <td> Y </td><td> Y </td><td> N </td></tr>
86 * <tr><td> {@link #disable} </td><td> Y </td><td> Y </td>
87 * <td> Y </td><td> Y </td><td> Y </td></tr>
88 * <tr><td> {@link #disableInterrupt} </td><td> Y </td><td> Y </td>
89 * <td> Y </td><td> Y </td><td> N </td></tr>
90 * <tr><td> {@link #enable} </td><td> Y </td><td> Y </td>
91 * <td> Y </td><td> N </td><td> N </td></tr>
92 * <tr><td> {@link #enableInterrupt} </td><td> Y </td><td> Y </td>
93 * <td> Y </td><td> Y </td><td> N </td></tr>
94 * <tr><td> {@link #Params_init} </td><td> Y </td><td> Y </td>
95 * <td> Y </td><td> Y </td><td> Y </td></tr>
96 * <tr><td> {@link #restore} </td><td> Y </td><td> Y </td>
97 * <td> Y </td><td> Y </td><td> Y </td></tr>
98 * <tr><td> {@link #restoreInterrupt} </td><td> Y </td><td> Y </td>
99 * <td> Y </td><td> Y </td><td> Y </td></tr>
100 * <tr><td> {@link #construct} </td><td> N </td><td> N </td>
101 * <td> Y </td><td> Y </td><td> N </td></tr>
102 * <tr><td> {@link #delete} </td><td> N </td><td> N </td>
103 * <td> Y </td><td> Y </td><td> N </td></tr>
104 * <tr><td> {@link #destruct} </td><td> N </td><td> N </td>
105 * <td> Y </td><td> Y </td><td> N </td></tr>
106 * <tr><td> {@link #getHookContext} </td><td> Y </td><td> Y </td>
107 * <td> Y </td><td> Y </td><td> N </td></tr>
108 * <tr><td> {@link #setFunc} </td><td> Y </td><td> Y </td>
109 * <td> Y </td><td> Y </td><td> N </td></tr>
110 * <tr><td> {@link #setHookContext} </td><td> Y </td><td> Y </td>
111 * <td> Y </td><td> Y </td><td> N </td></tr>
112 * <tr><td colspan="6"> Definitions: <br />
113 * <ul>
114 * <li> <b>Hwi</b>: API is callable from a Hwi thread. </li>
115 * <li> <b>Swi</b>: API is callable from a Swi thread. </li>
116 * <li> <b>Task</b>: API is callable from a Task thread. </li>
117 * <li> <b>Main</b>: API is callable during any of these phases: </li>
118 * <ul>
119 * <li> In your module startup after this module is started
120 * (e.g. Hwi_Module_startupDone() returns TRUE). </li>
121 * <li> During xdc.runtime.Startup.lastFxns. </li>
122 * <li> During main().</li>
123 * <li> During BIOS.startupFxns.</li>
124 * </ul>
125 * <li> <b>Startup</b>: API is callable during any of these phases:</li>
126 * <ul>
127 * <li> During xdc.runtime.Startup.firstFxns.</li>
128 * <li> In your module startup before this module is started
129 * (e.g. Hwi_Module_startupDone() returns FALSE).</li>
130 * </ul>
131 * </ul>
132 * </td></tr>
133 *
134 * </table>
135 * @p
136 *
137 * @a(Runtime Hwi Creation)
138 *
139 * Below is an example that configures an interrupt at runtime.
140 * Typically such code would be placed in main().
141 *
142 * @p(code)
143 * #include <xdc/runtime/Error.h>
144 * #include <ti/sysbios/hal/Hwi.h>
145 *
146 * Hwi_Handle myHwi;
147 *
148 * Int main(Int argc, char* argv[])
149 * {
150 * Hwi_Params hwiParams;
151 * Error_Block eb;
152 *
153 * Hwi_Params_init(&hwiParams);
154 * Error_init(&eb);
155 *
156 * // set the argument you want passed to your ISR function
157 * hwiParams.arg = 1;
158 *
159 * // set the event id of the peripheral assigned to this interrupt
160 * hwiParams.eventId = 10;
161 *
162 * // don't allow this interrupt to nest itself
163 * hwiParams.maskSetting = Hwi_MaskingOption_SELF;
164 *
165 * //
166 * // Configure interrupt 5 to invoke "myIsr".
167 * // Automatically enables interrupt 5 by default
168 * // set params.enableInt = FALSE if you want to control
169 * // when the interrupt is enabled using Hwi_enableInterrupt()
170 * //
171 *
172 * myHwi = Hwi_create(5, myIsr, &hwiParams, &eb);
173 *
174 * if (Error_check(&eb)) {
175 * // handle the error
176 * }
177 * }
178 *
179 * Void myIsr(UArg arg)
180 * {
181 * // this runs when interrupt #5 goes off
182 * }
183 * @p
184 *
185 * @a(Hook Functions)
186 *
187 * Sets of hook functions can be specified for the Hwi module
188 * using the configuration tool. Each set contains these hook
189 * functions:
190 * @p(blist)
191 * -Register: A function called before any statically-created Hwis
192 * are initialized at runtime. The register hook is called at boot time
193 * before main() and before interrupts are enabled.
194 * -Create: A function that is called when a Hwi is created.
195 * This includes hwis that are created statically and those
196 * created dynamically using {@link #create Hwi_create}.
197 * -Begin: A function that is called just prior to running a Hwi.
198 * -End: A function that is called just after a Hwi finishes.
199 * -Delete: A function that is called when a Hwi is deleted at
200 * run-time with {@link #delete Hwi_delete}.
201 * @p
202 *
203 * Register Function
204 *
205 * The Register function is provided to allow a hook set to store its
206 * hookset ID. This id can be passed to
207 * {@link #setHookContext Hwi_setHookContext} and
208 * {@link #getHookContext Hwi_getHookContext} to set or get
209 * hookset-specific context. The
210 * Register function must be specified if the hook implementation
211 * needs to use {@link #setHookContext Hwi_setHookContext} or
212 * {@link #getHookContext Hwi_getHookContext}.
213 * The registerFxn hook function is called during system initialization
214 * before interrupts have been enabled.
215 *
216 * @p(code)
217 * Void myRegisterFxn(Int id);
218 * @p
219 *
220 * Create and Delete Functions
221 *
222 * The create and delete functions are called whenever a Hwi is created
223 * or deleted. They are called with interrupts enabled (unless called
224 * at boot time or from main()).
225 *
226 * @p(code)
227 * Void myCreateFxn(Hwi_Handle hwi, Error_Block *eb);
228 * @p
229 *
230 * @p(code)
231 * Void myDeleteFxn(Hwi_Handle hwi);
232 * @p
233 *
234 * Begin and End Functions
235 *
236 * The beginFxn and endFxn function hooks are called with interrupts
237 * globally disabled, therefore any hook processing function will contribute
238 * to the overall system interrupt response latency. In order to minimize
239 * this impact, carefully consider the processing time spent in an Hwi
240 * beginFxn or endFxn function hook.
241 *
242 * @p(code)
243 * Void myBeginFxn(Hwi_Handle hwi);
244 * @p
245 *
246 * @p(code)
247 * Void myEndFxn(Hwi_Handle hwi);
248 * @p
249 *
250 * Hook functions can only be configured statically.
251 *
252 */
253
254 @ModuleStartup
255
256 @Template("./Hwi.xdt")
257
258 module Hwi inherits ti.sysbios.interfaces.IHwi
259 {
260 /*!
261 * Error raised when a stack overflow (or corruption) is detected.
262 *
263 * This error is raised by kernel's stack checking function. This
264 * function checks the stacks before every task switch to make sure
265 * that reserved word at top of stack has not been modified.
266 *
267 * The stack checking logic is enabled by the {@link #initStackFlag} and
268 * {@link #checkStackFlag} configuration parameters. If both of these
269 * flags are set to true, the kernel will validate the stacks.
270 */
271 config Error.Id E_stackOverflow = {
272 msg: "E_stackOverflow: ISR stack overflow."
273 };
274
275 /*!
276 * Initialize ISR stack with known value for stack checking at runtime
277 *
278 * This is also useful for inspection of stack in debugger or core
279 * dump utilities.
280 *
281 * Default is true.
282 * (see {@link #checkStackFlag}).
283 */
284 metaonly config Bool initStackFlag = true;
285
286 /*!
287 * Check for Hwi stack overrun during Idle loop.
288 *
289 * If true, then an idle function is added to the idle loop
290 * that checks for a Hwi stack overrun condition and raises
291 * an Error if one is detected.
292 *
293 * The check consists of testing the top of stack value against
294 * its initial value (see {@link #initStackFlag}). If it is no
295 * longer at this value, the assumption is that the ISR stack
296 * has been overrun. If the test fails, then the
297 * {@link #E_stackOverflow} error is raised.
298 *
299 * Runtime stack checking is only performed if {@link #initStackFlag} is
300 * also true.
301 *
302 * Default is true.
303 * (see {@link #initStackFlag}).
304 *
305 * To enable or disable full stack checking, you should set both this
306 * flag and the {@link ti.sysbios.knl.Task#checkStackFlag}.
307 */
308 metaonly config Bool checkStackFlag = true;
309
310 /*!
311 * ======== disable ========
312 */
313 @Macro
314 override UInt disable();
315
316 /*!
317 * ======== enable ========
318 */
319 @Macro
320 override UInt enable();
321
322 /*!
323 * ======== restore ========
324 */
325 @Macro
326 override Void restore(UInt key);
327
328 /*!
329 * ======== viewGetHandle ========
330 * @_nodoc
331 * Returns the corresponding hal Hwi handle for a delegate Hwi handle
332 *
333 * @b(returns) hal Hwi handle
334 */
335 metaonly Handle viewGetHandle(Ptr pi);
336
337 instance:
338
339 /*!
340 * ======== create ========
341 * Create a dispatched interrupt.
342 *
343 * To cause a C function to run in response to a particular system
344 * interrupt, you create a Hwi object that encapsulates information
345 * regarding the interrupt required by the Hwi module.
346 *
347 * The standard static and dynamic forms of the "create" function are
348 * supported by the ti.sysbios.hal.Hwi module.
349 * The following C code configures interrupt 5 with the "myIsr"
350 * C function.
351 *
352 * @p(code)
353 * #include <ti/sysbios/hal/Hwi>
354 *
355 * Hwi_create(5, myIsr, NULL, NULL);
356 * @p
357 *
358 * The NULL, NULL arguments are used when the default instance
359 * parameters and generic error handling is satisfactory for creating
360 * a Hwi object.
361 *
362 * A Hwi dispatcher table entry is created and filled with the
363 * function specified by the fxn parameter and the attributes
364 * specified by the params parameter.
365 *
366 * If params is NULL, the Hwi's dispatcher properties are assigned a
367 * default set of values. Otherwise, the following properties
368 * are specified by a structure of type Hwi_Params.
369 *
370 * @p(blist)
371 * - The arg element is a generic argument that is passed to the plugged
372 * function as its only parameter. The default value is 0.
373 * - The enableInt element determines whether the interrupt should be
374 * enabled in the IER by create.
375 * - The maskSetting element defines the dispatcherAutoNestingSupport
376 * behavior of the interrupt.
377 * @p
378 *
379 * Hwi_create returns a pointer to the created Hwi object.
380 *
381 * @param(intNum) interrupt number
382 * @param(hwiFxn) pointer to ISR function
383 */
384 @DirectCall
385 override create(Int intNum, FuncPtr hwiFxn);
386
387 /*!
388 * ======== getHookContext ========
389 * Get hook instance's context for a Hwi.
390 *
391 * The Handle passed to this API must be the handle passed
392 * to any of the Hook functions, not the one returned by
393 * {@link #create Hwi_create}.
394 *
395 * @b(returns) hook instance's context for hwi
396 */
397 @DirectCall
398 override Ptr getHookContext(Int id);
399
400 /*!
401 * ======== setHookContext ========
402 * Set hook instance's context for a Hwi.
403 *
404 * The Handle passed to this API must be the handle passed
405 * to any of the Hook functions, not the one returned by
406 * {@link #create Hwi_create}.
407 *
408 * @param(id) hook instance's ID
409 * @param(hookContext) value to write to context
410 */
411 @DirectCall
412 override Void setHookContext(Int id, Ptr hookContext);
413
414 internal:
415
416
417 metaonly config UInt numHooks = 0;
418
419 /*! target/device-specific Hwi implementation. */
420 proxy HwiProxy inherits ti.sysbios.interfaces.IHwi;
421
422 struct Instance_State {
423 HwiProxy.Handle pi;
424 };
425 }