Ticket #1212: test.c

File test.c, 3.5 KB (added by Xudong Guan, on 01/12/07 at 09:56:35)

This source file will reproduce the time slicing problem.

Line 
1/*
2 * This example shows a possible blocking of timeslicing if task mode is
3 * changed to timeslicing in the middle of its executing.
4 *
5 * The expected output is:
6 *
7 *   Task #0's turn. Now setting turn to 1
8 *   Task #1's turn. Now setting turn to 0
9 *   Task #0's turn. Now setting turn to 1
10 *   Task #1's turn. Now setting turn to 0
11 *   Task #0's turn. Now setting turn to 1
12 *   Task #1's turn. Now setting turn to 0
13 *   Task #0's turn. Now setting turn to 1
14 *   ...
15 *
16 * The actural output is:
17 *
18 *   Task #0's turn. Now setting turn to 1
19 *
20 * Task #1 can not be dispatched also both tasks have timeslice enabled.
21 *
22 * Setting TASK_A/B_INITMODE to RTEMS_DEFAULT_MODES | RTEMS_TIMESLICE
23 * will produce the expected output.
24 */
25
26#include <rtems.h>
27#include <stdio.h>
28
29/*** Task priorities ***/
30#define TASK_A_PRIORITY         10
31#define TASK_B_PRIORITY         10
32
33/*** Task names ***/
34#define TASK_A_NAME             1
35#define TASK_B_NAME             2
36
37/*** Task atributes ***/
38#define TASK_A_INITMODE         RTEMS_DEFAULT_MODES
39#define TASK_B_INITMODE         RTEMS_DEFAULT_MODES
40
41/*** Task generic parameters ***/
42#define TASK_A_STACKSIZE        RTEMS_MINIMUM_STACK_SIZE
43#define TASK_A_MODEATTR         RTEMS_DEFAULT_ATTRIBUTES
44#define TASK_B_STACKSIZE        RTEMS_MINIMUM_STACK_SIZE
45#define TASK_B_MODEATTR         RTEMS_DEFAULT_ATTRIBUTES
46
47static rtems_unsigned32 turn;
48static rtems_id TaskA_id, TaskB_id;
49
50#define TEST_FAILED(status, msg) do {                                     \
51        printf("Test failed, status code: %d, msg: %s\n", status, msg);   \
52        exit(1);                                                          \
53} while(0)
54
55/* TASK A/B */
56rtems_task TaskAB_entry(rtems_task_argument me)
57{
58        static rtems_mode previous_mode_set;
59        rtems_status_code status;
60
61        status = rtems_task_mode(RTEMS_PREEMPT | RTEMS_TIMESLICE,
62                        RTEMS_PREEMPT_MASK | RTEMS_TIMESLICE_MASK,
63                        &previous_mode_set);
64        if (status != RTEMS_SUCCESSFUL)
65                TEST_FAILED(status, "Unable to change task mode.");
66
67        while(1) {
68                if (turn == me) {
69                        printf("Task #%d's turn. Now setting turn to %d\n", me, 1 - me);
70                        turn = 1 - me;
71                }
72        }
73}
74
75rtems_task Init(rtems_task_argument ignored)
76{
77        static rtems_status_code status;
78
79        /* Create Task A */
80        status=rtems_task_create(TASK_A_NAME,
81                                 TASK_A_PRIORITY,
82                                 TASK_A_STACKSIZE,
83                                 TASK_A_INITMODE,
84                                 TASK_A_MODEATTR,
85                                 &TaskA_id);
86
87        if (status != RTEMS_SUCCESSFUL){
88                TEST_FAILED(status,"rtems_task_create failed.\n");
89        }
90
91        /* Start Task A */
92        status=rtems_task_start(TaskA_id, TaskAB_entry, 0);
93        if (status != RTEMS_SUCCESSFUL){
94                TEST_FAILED(status,"rtems_task_start failed.\n");
95        }
96
97        /* Create Task B */
98        status=rtems_task_create(TASK_B_NAME,
99                                 TASK_B_PRIORITY,
100                                 TASK_B_STACKSIZE,
101                                 TASK_B_INITMODE,
102                                 TASK_B_MODEATTR,
103                                 &TaskB_id);
104
105        if (status != RTEMS_SUCCESSFUL){
106                TEST_FAILED(status,"rtems_task_create failed.\n");
107        }
108
109        /* Start Task B */
110        status=rtems_task_start(TaskB_id, TaskAB_entry, 1);
111        if (status != RTEMS_SUCCESSFUL){
112                TEST_FAILED(status,"rtems_task_start failed.\n");
113        }
114
115        /* Suspend itself */
116        status=rtems_task_suspend(RTEMS_SELF);
117        if (status != RTEMS_SUCCESSFUL){
118                TEST_FAILED(status,"rtems_task_suspend failed.\n");
119        }
120
121        /* This task is not suposed to be executed anymore */
122        printf("\nNOT SUPOSED TO RETURN HERE...\n");
123        exit(1);
124}
125
126/* configuration information */
127
128#define CONFIGURE_APPLICATION_NEEDS_CLOCK_DRIVER
129#define CONFIGURE_TEST_NEEDS_CONSOLE_DRIVER
130
131#define CONFIGURE_MICROSECONDS_PER_TICK         10
132#define CONFIGURE_TICKS_PER_TIMESLICE           10
133#define CONFIGURE_MAXIMUM_TASKS                 10
134
135#define CONFIGURE_RTEMS_INIT_TASKS_TABLE
136
137#define CONFIGURE_INIT
138
139#include <confdefs.h>