1 <!-- Copyright (C) 2003 Red Hat, Inc. -->
2 <!-- This material may be distributed only subject to the terms -->
3 <!-- and conditions set forth in the Open Publication License, v1.0 -->
4 <!-- or later (the latest version is presently available at -->
5 <!-- http://www.opencontent.org/openpub/). -->
6 <!-- Distribution of the work or derivative of the work in any -->
7 <!-- standard (paper) book form is prohibited unless prior -->
8 <!-- permission is obtained from the copyright holder. -->
12 >µITRON Configuration FAQ</TITLE
13 ><meta name="MSSmartTagsPreventParsing" content="TRUE">
16 CONTENT="Modular DocBook HTML Stylesheet Version 1.76b+
19 TITLE="eCos Reference Manual"
20 HREF="ecos-ref.html"><LINK
23 HREF="compat-uitron-microitron-api.html"><LINK
25 TITLE=" Network Support Functions"
26 HREF="compat-uitron-network-support-functions.html"><LINK
28 TITLE="TCP/IP Stack Support for eCos"
29 HREF="net-common-tcpip.html"></HEAD
40 SUMMARY="Header navigation table"
49 >eCos Reference Manual</TH
57 HREF="compat-uitron-network-support-functions.html"
65 >Chapter 32. µITRON API</TD
71 HREF="net-common-tcpip.html"
85 NAME="COMPAT-UITRON-CONFIGURATION-FAQ">µITRON Configuration FAQ</H1
91 >Q: How are µITRON objects created?</I
95 >For each type of uITRON object (tasks, semaphores, flags, mboxes, mpf, mpl)
96 these two quantities are controlled by configuration:</P
108 > number of this type of object.</P
112 >The number of these objects which exist <SPAN
122 >This is assuming that for the relevant object type,
136 operations are enabled; enabled is the default. For example, the option
139 >CYGPKG_UITRON_MBOXES_CREATE_DELETE</TT
141 controls whether the functions
151 exist in the API. If not, then the maximum number of
152 mboxes is the same as the initial number of mboxes, and so on for all
153 µITRON object types.</P
155 >Mboxes have no initialization, so there are only a few, simple
156 configuration options:</P
164 >CYGNUM_UITRON_MBOXES</TT
166 is the total number of mboxes that you can have in the
167 system. By default this is 4, so you can use mboxes 1,2,3 and 4. You
168 cannot create mboxes outside this range; trying to
173 will return an error.</P
179 >CYGNUM_UITRON_MBOXES_INITIALLY</TT
181 is the number of mboxes created
182 automatically for you, during startup. By default this is 4, so all 4
183 mboxes exist already, and an attempt to create one of these
188 will return an error because the mbox in quesion already
189 exists. You can delete a pre-existing mbox, and then re-create it.</P
196 >CYGNUM_UITRON_MBOXES_INITIALLY</TT
198 for example to 0, no mboxes
199 are created automatically for you during startup. Any attempt to use an
200 mbox without creating it will return E_NOEXS because the mbox does not
201 exist. You can create an mbox, say <TT
208 >snd_msg(3,&foo)</TT
209 >, and all will be well.</P
215 >Q: How are µITRON objects initialized?</I
219 >Some object types have optional initialization. Semaphores are an
220 example. You could have
223 >CYGNUM_UITRON_SEMAS</TT
227 >CYGNUM_UITRON_SEMAS_INITIALLY</TT
229 which means you can use semaphores 1-5
230 straight off, but you must create semaphores 6-10 before you can use them.
231 If you decide not to initialize semaphores, semaphores 1-5 will have an
232 initial count of zero. If you decide to initialize them, you must supply
233 a dummy initializer for semaphores 6-10 also. For example,
234 in terms of the configuration output in
237 >pkgconf/uitron.h</TT
246 CLASS="PROGRAMLISTING"
247 > #define CYGDAT_UITRON_SEMA_INITIALIZERS \
251 CYG_UIT_SEMA( 99 ), \
253 CYG_UIT_SEMA_NOEXS, \
254 CYG_UIT_SEMA_NOEXS, \
255 CYG_UIT_SEMA_NOEXS, \
256 CYG_UIT_SEMA_NOEXS, \
257 CYG_UIT_SEMA_NOEXS</PRE
262 >Semaphore 1 will have initial count 1, semaphores 2 and 3 will be zero,
263 number 4 will be 99 initially, 5 will be one and numbers 6 though 10 do not
266 >Aside: this is how the definition of the symbol would appear in the
267 configuration header file <TT
269 >pkgconf/uitron.h</TT
271 unfortunately editing such a long, multi-line definition is somewhat
272 cumbersome in the GUI config tool in current releases. The macros
277 — to create a semaphore initializer — and
280 >CYG_UIT_SEMA_NOEXS</TT
282 — to invoke a dummy initializer —
283 are provided in in the environment to help with this. Similar macros are
284 provided for other object types. The resulting #define symbol is used in
285 the context of a C++ array initializer, such as:
293 CLASS="PROGRAMLISTING"
294 >Cyg_Counting_Semaphore2 cyg_uitron_SEMAS[ CYGNUM_UITRON_SEMAS ] = {
295 CYGDAT_UITRON_SEMA_INITIALIZERS
301 which is eventually macro-processed to give
309 CLASS="PROGRAMLISTING"
310 >Cyg_Counting_Semaphore2 cyg_uitron_SEMAS[ 10 ] = {
311 Cyg_Counting_Semaphore2( ( 1 ) ),
312 Cyg_Counting_Semaphore2( ( 0 ) ),
313 Cyg_Counting_Semaphore2( ( 0 ) ),
314 Cyg_Counting_Semaphore2( ( 99 ) ),
315 Cyg_Counting_Semaphore2( ( 1 ) ),
316 Cyg_Counting_Semaphore2(0),
317 Cyg_Counting_Semaphore2(0),
318 Cyg_Counting_Semaphore2(0),
319 Cyg_Counting_Semaphore2(0),
320 Cyg_Counting_Semaphore2(0),
326 so you can see how it is necessary to include the dummy entries in that
327 definition, otherwise the resulting code will not compile correctly.</P
332 >CYGNUM_UITRON_SEMAS_INITIALLY</TT
334 it is meaningless to initialize them, for they must be created and so
335 initialized then, before use.</P
341 >Q: What about µITRON tasks?</I
345 >Some object types require initialization. Tasks are an example of this.
346 You must provide a task with a priority, a function to enter when the task
347 starts, a name (for debugging purposes), and some memory to use for the stack.
348 For example (again in terms of the resulting
351 >pkgconf/uitron.h</TT
360 CLASS="PROGRAMLISTING"
361 >#define CYGNUM_UITRON_TASKS 4 // valid task ids are 1,2,3,4
362 #define CYGNUM_UITRON_TASKS_INITIALLY 4 // they all exist at start
364 #define CYGDAT_UITRON_TASK_EXTERNS \
365 extern "C" void startup( unsigned int ); \
366 extern "C" void worktask( unsigned int ); \
367 extern "C" void lowtask( unsigned int ); \
368 static char stack1[ CYGNUM_UITRON_STACK_SIZE ], \
369 stack2[ CYGNUM_UITRON_STACK_SIZE ], \
370 stack3[ CYGNUM_UITRON_STACK_SIZE ], \
371 stack4[ CYGNUM_UITRON_STACK_SIZE ];
373 #define CYGDAT_UITRON_TASK_INITIALIZERS \
374 CYG_UIT_TASK("main task", 8, startup, &stack1, sizeof( stack1 )), \
375 CYG_UIT_TASK("worker 2" , 9, worktask, &stack2, sizeof( stack2 )), \
376 CYG_UIT_TASK("worker 3" , 9, worktask, &stack3, sizeof( stack3 )), \
377 CYG_UIT_TASK("low task" ,20, lowtask, &stack4, sizeof( stack4 )), \ </PRE
382 >So this example has all four tasks statically configured to exist, ready to
383 run, from the start of time. The “main task” runs a routine
388 “worker” tasks run both a priority 9, and a “low
389 priority” task runs at priority 20 to do useful non-urgent background
399 >Task ID | Exists at | Function | Priority | Stack | Stack
400 number | startup | entry | | address | size
401 --------+-----------+----------+----------+---------+----------
402 1 | Yes | startup | 8 | &stack1 | CYGNUM...
403 2 | Yes | worktask | 9 | &stack2 | CYGNUM...
404 3 | Yes | worktask | 9 | &stack3 | CYGNUM...
405 4 | Yes | lowtask | 20 | &stack4 | CYGNUM...
406 --------+-----------+----------+----------+---------+----------</PRE
415 >Q: How can I create µITRON tasks in the program?</I
419 >You must provide free slots in the task table in which to create new tasks,
420 by configuring the number of tasks existing initially to be smaller than
422 For a task ID which does not initially exist, it will be told what routine
423 to call, and what priority it is, when the task is created. But you must
424 still set aside memory for the task to use for its stack, and give it a
425 name during initialization. For example:</P
433 CLASS="PROGRAMLISTING"
434 >#define CYGNUM_UITRON_TASKS 4 // valid task ids are 1-4
435 #define CYGNUM_UITRON_TASKS_INITIALLY 1 // only task #1 exists
437 #define CYGDAT_UITRON_TASK_EXTERNS \
438 extern "C" void startup( unsigned int ); \
439 static char stack1[ CYGNUM_UITRON_STACK_SIZE ], \
440 stack2[ CYGNUM_UITRON_STACK_SIZE ], \
441 stack3[ CYGNUM_UITRON_STACK_SIZE ], \
442 stack4[ CYGNUM_UITRON_STACK_SIZE ];
444 #define CYGDAT_UITRON_TASK_INITIALIZERS \
445 CYG_UIT_TASK( "main", 8, startup, &stack1, sizeof( stack1 ) ), \
446 CYG_UIT_TASK_NOEXS( "slave", &stack2, sizeof( stack2 ) ), \
447 CYG_UIT_TASK_NOEXS( "slave2", &stack3, sizeof( stack3 ) ), \
448 CYG_UIT_TASK_NOEXS( "slave3", &stack4, sizeof( stack4 ) ), \ </PRE
453 >So tasks numbered 2,3 and 4 have been given their stacks during startup,
454 though they do not yet exist in terms of <TT
461 > so you can create tasks 2–4 at
471 >Task ID | Exists at | Function | Priority | Stack | Stack
472 number | startup | entry | | address | size
473 --------+-----------+----------+----------+---------+----------
474 1 | Yes | startup | 8 | &stack1 | CYGNUM...
475 2 | No | N/A | N/A | &stack2 | CYGNUM...
476 3 | No | N/A | N/A | &stack3 | CYGNUM...
477 4 | No | N/A | N/A | &stack4 | CYGNUM...
478 --------+-----------+----------+----------+---------+----------</PRE
483 >(you must have at least one task at startup in order that the system can
484 actually run; this is not so for other uITRON object types)</P
490 >Q: Can I have different stack sizes for µITRON tasks?</I
494 >Simply set aside different amounts of memory for each task to use for its
495 stack. Going back to a typical default setting for the µITRON tasks,
496 the definitions in <TT
498 >pkgconf/uitron.h</TT
499 > might look like this:</P
507 CLASS="PROGRAMLISTING"
508 >#define CYGDAT_UITRON_TASK_EXTERNS \
509 extern "C" void task1( unsigned int ); \
510 extern "C" void task2( unsigned int ); \
511 extern "C" void task3( unsigned int ); \
512 extern "C" void task4( unsigned int ); \
513 static char stack1[ CYGNUM_UITRON_STACK_SIZE ], \
514 stack2[ CYGNUM_UITRON_STACK_SIZE ], \
515 stack3[ CYGNUM_UITRON_STACK_SIZE ], \
516 stack4[ CYGNUM_UITRON_STACK_SIZE ];
518 #define CYGDAT_UITRON_TASK_INITIALIZERS \
519 CYG_UIT_TASK( "t1", 1, task1, &stack1, CYGNUM_UITRON_STACK_SIZE ), \
520 CYG_UIT_TASK( "t2", 2, task2, &stack2, CYGNUM_UITRON_STACK_SIZE ), \
521 CYG_UIT_TASK( "t3", 3, task3, &stack3, CYGNUM_UITRON_STACK_SIZE ), \
522 CYG_UIT_TASK( "t4", 4, task4, &stack4, CYGNUM_UITRON_STACK_SIZE ) </PRE
530 >CYGNUM_UITRON_STACK_SIZE</TT
532 is used to control the size of the stack
533 objects themselves, and to tell the system what size stack is being provided.</P
535 >Suppose instead stack sizes of 2000, 1000, 800 and 800 were required:
536 this could be achieved by using the GUI config tool to edit these
537 options, or editting the <TT
543 >pkgconf/uitron.h</TT
552 CLASS="PROGRAMLISTING"
553 >#define CYGDAT_UITRON_TASK_EXTERNS \
554 extern "C" void task1( unsigned int ); \
555 extern "C" void task2( unsigned int ); \
556 extern "C" void task3( unsigned int ); \
557 extern "C" void task4( unsigned int ); \
558 static char stack1[ 2000 ], \
563 #define CYGDAT_UITRON_TASK_INITIALIZERS \
564 CYG_UIT_TASK( "t1", 1, task1, &stack1, sizeof( stack1 ) ), \
565 CYG_UIT_TASK( "t2", 2, task2, &stack2, sizeof( stack2 ) ), \
566 CYG_UIT_TASK( "t3", 3, task3, &stack3, sizeof( stack3 ) ), \
567 CYG_UIT_TASK( "t4", 4, task4, &stack4, sizeof( stack4 ) )</PRE
572 >Note that the sizeof() operator has been used to tell the system what size
573 stacks are provided, rather than quoting a number (which is difficult for
574 maintenance) or the symbol
577 >CYGNUM_UITRON_STACK_SIZE</TT
581 >We recommend using (if available in your release) the stacksize symbols
582 provided in the architectural HAL for your target, called
585 >CYGNUM_HAL_STACK_SIZE_TYPICAL</TT
590 >CYGNUM_HAL_STACK_SIZE_MINIMUM</TT
592 So a better (more portable) version of the above might be:</P
600 CLASS="PROGRAMLISTING"
601 >#define CYGDAT_UITRON_TASK_EXTERNS \
602 extern "C" void task1( unsigned int ); \
603 extern "C" void task2( unsigned int ); \
604 extern "C" void task3( unsigned int ); \
605 extern "C" void task4( unsigned int ); \
606 static char stack1[ CYGNUM_HAL_STACK_SIZE_TYPICAL + 1200 ], \
607 stack2[ CYGNUM_HAL_STACK_SIZE_TYPICAL + 200 ], \
608 stack3[ CYGNUM_HAL_STACK_SIZE_TYPICAL ], \
609 stack4[ CYGNUM_HAL_STACK_SIZE_TYPICAL ];
611 #define CYGDAT_UITRON_TASK_INITIALIZERS \
612 CYG_UIT_TASK( "t1", 1, task1, &stack1, sizeof( stack1 ) ), \
613 CYG_UIT_TASK( "t2", 2, task2, &stack2, sizeof( stack2 ) ), \
614 CYG_UIT_TASK( "t3", 3, task3, &stack3, sizeof( stack3 ) ), \
615 CYG_UIT_TASK( "t4", 4, task4, &stack4, sizeof( stack4 ) )</PRE
625 SUMMARY="Footer navigation table"
636 HREF="compat-uitron-network-support-functions.html"
654 HREF="net-common-tcpip.html"
664 >Network Support Functions</TD
670 HREF="compat-uitron-microitron-api.html"
678 >TCP/IP Stack Support for eCos</TD