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
37
38 package ti.sysbios.timers.dmtimer;
39
40 import xdc.rov.ViewInfo;
41
42 import xdc.runtime.Assert;
43 import xdc.runtime.Error;
44 import xdc.runtime.Types;
45 import ti.sysbios.interfaces.ITimer;
46 import ti.sysbios.hal.Hwi;
47
48 /*!
49 * ======== Timer ========
50 * Timer Peripheral Manager.
51 *
52 * This Timer module manages the Dual Mode timer (dmtimer) peripherals
53 * available on the ARM and C6000 devices (see
54 * {@link ./doc-files/TimerTables.html Timer Mapping Tables} for supported
55 * device information).
56 *
57 * The dmtimer Timer module supports the timer in 'one shot', 'continuous',
58 * and 'dynamic' modes.
59 *
60 * In 'one shot' mode, a timer function will "fire" (run) when the timer period
61 * expires (counts up to zero). In 'one shot' mode this will only happen
62 * once.
63 *
64 * In 'continuous' mode, the specified timer function will "fire" every
65 * time the period expires, throughout the lifetime of the program. When the
66 * period expires in 'continuous mode', the period is then reset to its
67 * original value and then begins counting up to zero again. At this point
68 * the timer function will fire again and the cycle repeats itself.
69 *
70 * In 'dynamic' mode, the specified timer function will "fire" every
71 * time the period expires. But the period of the timer can be changed
72 * dynamically, to correspond to the next tick interrupt needed from the
73 * timer. The timer will continually count upwards, and the timer's compare
74 * mode is used to generate an interrupt when a specific threshold count is
75 * reached. This mode is used by the SYS/BIOS Clock module, for implementing
76 * dynamic tick suppression, which reduces the number of interrupts from the
77 * timer to the minimum required for currently scheduled timeouts.
78 *
79 * @p(html)
80 * <h3> Calling Context </h3>
81 * <table border="1" cellpadding="3">
82 * <colgroup span="1"></colgroup> <colgroup span="5" align="center">
83 * </colgroup>
84 *
85 * <tr><th> Function </th><th> Hwi </th><th> Swi </th>
86 * <th> Task </th><th> Main </th><th> Startup </th></tr>
87 * <!-- -->
88 * <tr><td> {@link #getNumTimers} </td><td> Y </td>
89 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
90 * <tr><td> {@link #getStatus} </td><td> Y </td>
91 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
92 * <tr><td> {@link #Params_init} </td><td> Y </td>
93 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
94 * <tr><td> {@link #construct} </td><td> Y </td>
95 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
96 * <tr><td> {@link #create} </td><td> N </td>
97 * <td> N </td><td> Y </td><td> Y </td><td> N </td></tr>
98 * <tr><td> {@link #delete} </td><td> N </td>
99 * <td> N </td><td> Y </td><td> Y </td><td> N </td></tr>
100 * <tr><td> {@link #destruct} </td><td> Y </td>
101 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
102 * <tr><td> {@link #getCount} </td><td> Y </td>
103 * <td> Y </td><td> Y </td><td> N </td><td> N </td></tr>
104 * <tr><td> {@link #getFreq} </td><td> Y </td>
105 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
106 * <tr><td> {@link #getFunc} </td><td> Y </td>
107 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
108 * <tr><td> {@link #getPeriod} </td><td> Y </td>
109 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
110 * <tr><td> {@link #reconfig} </td><td> Y </td>
111 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
112 * <tr><td> {@link #setFunc} </td><td> Y </td>
113 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
114 * <tr><td> {@link #setPeriod} </td><td> Y </td>
115 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
116 * <tr><td> {@link #setPeriodMicroSecs} </td><td> Y </td>
117 * <td> Y </td><td> Y </td><td> Y </td><td> N </td></tr>
118 * <tr><td> {@link #start} </td><td> Y </td>
119 * <td> Y </td><td> Y </td><td> N </td><td> N </td></tr>
120 * <tr><td> {@link #stop} </td><td> Y </td>
121 * <td> Y </td><td> Y </td><td> N </td><td> N </td></tr>
122 * <tr><td colspan="6"> Definitions: <br />
123 * <ul>
124 * <li> <b>Hwi</b>: API is callable from a Hwi thread. </li>
125 * <li> <b>Swi</b>: API is callable from a Swi thread. </li>
126 * <li> <b>Task</b>: API is callable from a Task thread. </li>
127 * <li> <b>Main</b>: API is callable during any of these phases: </li>
128 * <ul>
129 * <li> In your module startup after this module is started
130 * (e.g. Timer_Module_startupDone() returns TRUE). </li>
131 * <li> During xdc.runtime.Startup.lastFxns. </li>
132 * <li> During main().</li>
133 * <li> During BIOS.startupFxns.</li>
134 * </ul>
135 * <li> <b>Startup</b>: API is callable during any of these phases:</li>
136 * <ul>
137 * <li> During xdc.runtime.Startup.firstFxns.</li>
138 * <li> In your module startup before this module is started
139 * (e.g. Timer_Module_startupDone() returns FALSE).</li>
140 * </ul>
141 * </ul>
142 * </td></tr>
143 *
144 * </table>
145 * @p
146 *
147 * @p(html)
148 * <h3> Timer Mapping Tables </h3>
149 * <p>
150 * The Timer module allows the user to use and configure the various timers
151 * that exist on a particular device. This is achieved by specifying a timer
152 * ID when calling {@link ti.sysbios.hal.Timer#Timer_create}.
153 * However, the timer ID
154 * specified may not always map to that timer; for example, specifying an ID
155 * value of 1 does not necessarily mean that this will map to "GPTimer1".
156 * These tables are provided to show which timers map to which timer IDs.
157 * </p>
158 * {@link ./doc-files/TimerTables.html Timer Mapping Tables}
159 * @p
160 */
161 @InstanceFinalize
162 @InstanceInitError
163 @ModuleStartup
164
165 module Timer inherits ti.sysbios.interfaces.ITimer
166 {
167 /*! override supportsDynamic - this Timer does support RunMode_DYNAMIC */
168 override metaonly config Bool supportsDynamic = true;
169
170 /*! Max value of Timer period for PeriodType_COUNTS*/
171 const UInt MAX_PERIOD = 0xffffffff;
172
173 /*! L4 interface Configuration Register (TIOCP_CFG). */
174 struct TiocpCfg {
175 Bits8 idlemode; /*! 0=force-idle;1=no-idle;2=Smart-idle;3=Smart-idle */
176 Bits8 emufree; /*! 0=counter frozen; 1=counter free-running */
177 Bits8 softreset; /*! 0=normal mode; 1=soft reset */
178 };
179
180 /*! Interrupt Enable Register (TIER). */
181 struct Tier {
182 Bits8 mat_it_ena; /*! Enable match interrupt */
183 Bits8 ovf_it_ena; /*! Enable overflow interrupt */
184 Bits8 tcar_it_ena; /*! Enable capture interrupt */
185 };
186
187 /*! WakepUp Enable Register (TWER). */
188 struct Twer {
189 Bits8 mat_wup_ena; /*! Enable match wake-up */
190 Bits8 ovf_wup_ena; /*! Enable overflow wake-up */
191 Bits8 tcar_wup_ena; /*! Enable capture wake-up */
192 };
193
194 /*! Control Register (TCLR). */
195 struct Tclr {
196 Bits32 ptv; /*! Trigger output mode */
197 Bits8 pre; /*! Prescalar enable */
198 Bits8 ce; /*! Compare enable */
199 Bits8 scpwm;/*! Pulse-width modulation */
200 Bits16 tcm; /*! Transition capture mode */
201 Bits16 trg; /*! Trigger output mode */
202 Bits8 pt; /*! Pulse or toggle select bit */
203 Bits8 captmode; /*! Capture mode select bit */
204 Bits8 gpocfg; /*! PWM output/event detection input pin */
205 };
206
207 /*! L4 Interface Synchronization Control Register (TSICR). */
208 struct Tsicr {
209 Bits8 sft; /*! Reset software functional registers */
210 Bits8 posted; /*! Posted mode selection */
211 };
212
213 /*! Timer Settings. */
214 metaonly struct TimerSetting {
215 Bool master; /*! specifies whether this is the master */
216 Ptr baseAddr; /*! specify the base address */
217 Int intNum; /*! specify which interrupt vector */
218 String name; /*! specify the timer name */
219 };
220
221 /*!
222 * ======== BasicView ========
223 * @_nodoc
224 */
225 metaonly struct BasicView {
226 Ptr halTimerHandle;
227 String label;
228 UInt id;
229 String name;
230 String startMode;
231 String runMode;
232 UInt period;
233 String periodType;
234 UInt intNum;
235 UInt eventId;
236 String tickFxn[];
237 UArg arg;
238 String extFreqLow;
239 String extFreqHigh;
240 String hwiHandle;
241 };
242
243
244 /*!
245 * ======== ModuleView ========
246 * @_nodoc
247 */
248 metaonly struct ModuleView {
249 String availMask;
250 String intFrequency;
251 }
252
253 /*!
254 * ======== rovViewInfo ========
255 * @_nodoc
256 */
257 @Facet
258 metaonly config ViewInfo.Instance rovViewInfo =
259 ViewInfo.create({
260 viewMap: [
261 [
262 'Basic',
263 {
264 type: ViewInfo.INSTANCE,
265 viewInitFxn: 'viewInitBasic',
266 structName: 'BasicView'
267 }
268 ],
269 [
270 'Module',
271 {
272 type: ViewInfo.MODULE,
273 viewInitFxn: 'viewInitModule',
274 structName: 'ModuleView'
275 }
276 ],
277 ]
278 });
279
280 /*!
281 * Assert raised when statically created timer is not available
282 */
283 config xdc.runtime.Assert.Id A_notAvailable = {
284 msg: "A_notAvailable: statically created timer not available"
285 };
286
287 /*!
288 * Error raised when timer id specified is not supported.
289 */
290 config Error.Id E_invalidTimer = {
291 msg: "E_invalidTimer: Invalid Timer Id %d"
292 };
293
294 /*!
295 * Error raised when timer requested is in use
296 */
297 config Error.Id E_notAvailable = {
298 msg: "E_notAvailable: Timer not available %d"
299 };
300
301 /*!
302 * Error raised when period requested is not supported
303 */
304 config Error.Id E_cannotSupport = {
305 msg: "E_cannotSupport: Timer cannot support requested period %d"
306 };
307
308 /*!
309 * Error raised when timer frequency does not match expected frequency
310 *
311 * BIOS does not configure the DMTimer clock source and expects this
312 * configuration to be performed via a GEL script or on the host OS. This
313 * error is raised if BIOS detects a mismatch between {@link #intFreq} and
314 * the actual operating frequency. The check is performed by comparing
315 * the timestamp operating frequency with the DMTimer frequency.
316 *
317 * To change the expected timer frequency to match the actual operating
318 * frequency, use the following example configuration:
319 * @p(code)
320 * var Timer = xdc.useModule('ti.sysbios.timers.dmtimer.Timer');
321 * Timer.intFreq.lo = 20000000; //For 20Mhz
322 * Timer.intFreq.hi = 0;
323 * @p
324 *
325 * This check can be skipped by setting {@link #checkFrequency} to FALSE.
326 */
327 config Error.Id E_freqMismatch = {
328 msg: "E_freqMismatch: Frequency mismatch: Expected %d Hz, actual: %d Hz. You need to modify Timer.intFreq.lo to match the actual frequency."
329 };
330
331 /*!
332 * ======== anyMask ========
333 * Available mask to be used when select = Timer_ANY.
334 *
335 * Default value is device specific.
336 */
337 config Bits32 anyMask;
338
339 /*!
340 * ======== checkFrequency ========
341 * Whether to check the timer operating frequency at startup
342 *
343 * When this flag is set to 'TRUE', the Timer module will verify that the
344 * operating frequency equals the frequency at which BIOS expects the
345 * timers to operate. This check is performed by checking the timer count
346 * rate against the {@link xdc.runtime.Timestamp} count rate.
347 */
348 config Bool checkFrequency = true;
349
350 /*!
351 * ======== timerSettings ========
352 * Global Control configuration for each physical timer.
353 */
354 metaonly config TimerSetting timerSettings[] = [];
355
356 /*!
357 * ======== intFreq ========
358 * Default internal timer input clock frequency.
359 */
360 metaonly config Types.FreqHz intFreq = {lo: 0, hi: 0};
361
362 /*!
363 * ======== stub ========
364 * @_nodoc
365 * Timer requires acknowledgement
366 *
367 * @param(arg) timer object passed in as argument.
368 */
369 @DirectCall
370 Void stub(UArg arg);
371
372 /*!
373 * ======== dynStub ========
374 * @_nodoc
375 * Acknowledges timer interrupt and sets next threshold for interrupt.
376 *
377 * @param(arg) timer object passed in as argument.
378 */
379 @DirectCall
380 Void dynStub(UArg arg);
381
382 /*!
383 * ======== setAvailMask ========
384 * @_nodoc
385 * Sets dmtimer anyMask.
386 *
387 * @param(arg) new anyMask is passed in as argument.
388 */
389 Void setAvailMask(UArg arg);
390
391 instance:
392
393 /*!
394 * ======== tiocpCfg ========
395 * Initial Timer TIOCP_CFG Register bit settings.
396 *
397 * For a detailed description of this timer register, please
398 * refer to your device's Technical Reference Manual.
399 */
400 config TiocpCfg tiocpCfg = {idlemode: 0, emufree: 0, softreset: 1};
401
402 /*!
403 * ======== tier ========
404 * Initial Timer IRQSTATUS_SET Register bit settings.
405 *
406 * For a detailed description of this timer register, please
407 * refer to your device's Technical Reference Manual.
408 */
409 config Tier tier = {mat_it_ena: 0, ovf_it_ena: 1, tcar_it_ena: 0};
410
411 /*!
412 * ======== twer ========
413 * Initial Timer IRQ Wakeup Enable Register bit settings.
414 *
415 * For a detailed description of this timer register, please
416 * refer to your device's Technical Reference Manual.
417 */
418 config Twer twer = {mat_wup_ena: 0, ovf_wup_ena: 0, tcar_wup_ena: 0};
419
420 /*!
421 * ======== tclr ========
422 * Initial Timer Control Register bit settings.
423 *
424 * For a detailed description of this timer register, please
425 * refer to your device's Technical Reference Manual.
426 */
427 config Tclr tclr = {ptv: 0, pre: 0, ce: 0, scpwm: 0, tcm: 0, trg: 0,
428 pt: 0, captmode: 0, gpocfg: 0};
429
430 /*!
431 * ======== tsicr ========
432 * Initial Timer Synchronous Interface Control Register bit settings.
433 *
434 * For a detailed description of this timer register, please
435 * refer to your device's Technical Reference Manual.
436 */
437 config Tsicr tsicr = {sft: 0, posted: 1};
438
439 /*!
440 * ======== tmar ========
441 * Initial Timer Match Register setting.
442 *
443 * For a detailed description of this timer register, please
444 * refer to your device's Technical Reference Manual.
445 */
446 config UInt32 tmar = 0;
447
448 /*!
449 * ======== intNum ========
450 * Hwi interrupt number to be used by Timer.
451 */
452 config Int intNum = -1;
453
454 /*!
455 * ======== eventId ========
456 * Hwi event Id to be used by Timer.
457 */
458 config Int eventId = -1;
459
460 /*! Hwi Params for Hwi Object. Default is null. */
461 config Hwi.Params *hwiParams = null;
462
463 /*!
464 * ======== reconfig ========
465 * Used to modify static timer instances at runtime.
466 *
467 * @param(timerParams) timer Params
468 * @param(tickFxn) functions that runs when timer expires
469 */
470 @DirectCall
471 Void reconfig(FuncPtr tickFxn, const Params *timerParams, Error.Block *eb);
472
473 /*!
474 * ======== getRollovers ========
475 * @_nodoc
476 * Returns the total number of timer rollovers since the timer was
477 * started. This API is used internally for implementing timestamping
478 * when the timer is shared with Clock, and running with RunMode_DYNAMIC.
479 * It has no other intended purpose.
480 *
481 * @b(returns) number of rollovers since timer was started
482 */
483 @DirectCall
484 UInt32 getRollovers();
485
486 /*!
487 * ======== enableTimestamping ========
488 * @_nodoc
489 * Enables the timer to be used for timestamping purposes. This API is
490 * used internally for enabling timestamping when the timer is shared with
491 * Clock, and running with RunMode_DYNAMIC. It has no other intended
492 * purpose.
493 *
494 */
495 @DirectCall
496 Void enableTimestamping();
497
498
499 internal:
500
501
502 /*! Device-specific Timer implementation. */
503 proxy TimerSupportProxy inherits ti.sysbios.interfaces.ITimerSupport;
504
505 /*!
506 * ======== startupNeeded ========
507 * This flag is use to prevent Timer_startup code (includes postInit(),
508 * deviceConfig(), initDevice() to be brought in un-necessarily.
509 */
510 config Bool startupNeeded = false;
511
512 /*! Information about timer */
513 struct TimerDevice {
514 UInt intNum;
515 UInt eventId;
516 Ptr baseAddr;
517 };
518
519 /*!
520 * ======== numTimerDevices ========
521 * The number of logical timers on a device.
522 */
523 config Int numTimerDevices;
524
525 /*!
526 * ======== spinLoop ========
527 * used by trigger function.
528 */
529 Void spinLoop(UInt count);
530
531 /*!
532 * ======== checkFreq ========
533 * Used to verify that the DMTimer is operating at the right frequency.
534 */
535 Void checkFreq(Timer.Object *obj);
536
537 /*! Instance state structure */
538 struct Instance_State {
539 Bool staticInst;
540 Int id;
541 UInt tiocpCfg;
542 UInt tmar;
543 UInt tier;
544 UInt twer;
545 UInt tclr;
546 UInt tsicr;
547 ITimer.RunMode runMode;
548 ITimer.StartMode startMode;
549 UInt period;
550 ITimer.PeriodType periodType;
551 UInt intNum;
552 UInt eventId;
553 UArg arg;
554 Hwi.FuncPtr tickFxn;
555 Types.FreqHz extFreq;
556 Hwi.Handle hwi;
557 UInt prevThreshold;
558 UInt rollovers;
559 560 561 562
563 Bool useDefaultEventId;
564 }
565
566 /*! Module state structure */
567 struct Module_State {
568 Bits32 availMask;
569 Types.FreqHz intFreq;
570 TimerDevice device[];
571 Handle handles[];
572 Bool firstInit;
573 }
574 }
575 576 577 578
579