|
168
|
1 /* this is a very simple program meant to demonstrate |
|
|
2 a basic use of time, alarms and alarm-handling functions |
|
|
3 in eCos */ |
|
|
4 |
|
|
5 #include <cyg/kernel/kapi.h> |
|
|
6 |
|
|
7 #include <stdio.h> |
|
|
8 |
|
|
9 #define NTHREADS 1 |
|
|
10 #define STACKSIZE 4096 |
|
|
11 |
|
|
12 static cyg_handle_t thread[NTHREADS]; |
|
|
13 |
|
|
14 static cyg_thread thread_obj[NTHREADS]; |
|
|
15 static char stack[NTHREADS][STACKSIZE]; |
|
|
16 |
|
|
17 static void alarm_prog( cyg_addrword_t data ); |
|
|
18 |
|
|
19 /* we install our own startup routine which sets up |
|
|
20 threads and starts the scheduler */ |
|
|
21 void cyg_user_start(void) |
|
|
22 { |
|
|
23 cyg_thread_create(4, alarm_prog, (cyg_addrword_t) 0, |
|
|
24 "alarm_thread", (void *) stack[0], |
|
|
25 STACKSIZE, &thread[0], &thread_obj[0]); |
|
|
26 cyg_thread_resume(thread[0]); |
|
|
27 } |
|
|
28 |
|
|
29 /* we need to declare the alarm handling function (which is |
|
|
30 defined below), so that we can pass it to |
|
|
31 cyg_alarm_initialize() */ |
|
|
32 cyg_alarm_t test_alarm_func; |
|
|
33 |
|
|
34 /* alarm_prog() is a thread which sets up an alarm which is then |
|
|
35 handled by test_alarm_func() */ |
|
|
36 static void alarm_prog(cyg_addrword_t data) |
|
|
37 { |
|
|
38 cyg_handle_t test_counterH, system_clockH, test_alarmH; |
|
|
39 cyg_tick_count_t ticks; |
|
|
40 cyg_alarm test_alarm; |
|
|
41 unsigned how_many_alarms = 0, prev_alarms = 0, tmp_how_many; |
|
|
42 |
|
|
43 system_clockH = cyg_real_time_clock(); |
|
|
44 cyg_clock_to_counter(system_clockH, &test_counterH); |
|
|
45 cyg_alarm_create(test_counterH, test_alarm_func, |
|
|
46 (cyg_addrword_t) &how_many_alarms, |
|
|
47 &test_alarmH, &test_alarm); |
|
|
48 cyg_alarm_initialize(test_alarmH, cyg_current_time()+200, 200); |
|
|
49 |
|
|
50 /* get in a loop in which we read the current time and |
|
|
51 print it out, just to have something scrolling by */ |
|
|
52 for (;;) { |
|
|
53 ticks = cyg_current_time(); |
|
|
54 printf("Time is %llu\n", ticks); |
|
|
55 /* note that we must lock access to how_many_alarms, since the |
|
|
56 alarm handler might change it. this involves using the |
|
|
57 annoying temporary variable tmp_how_many so that I can keep the |
|
|
58 critical region short */ |
|
|
59 cyg_scheduler_lock(); |
|
|
60 tmp_how_many = how_many_alarms; |
|
|
61 cyg_scheduler_unlock(); |
|
|
62 if (prev_alarms != tmp_how_many) { |
|
|
63 printf(" ---> alarm calls so far: %u\n", tmp_how_many); |
|
|
64 prev_alarms = tmp_how_many; |
|
|
65 } |
|
|
66 cyg_thread_delay(30); |
|
|
67 } |
|
|
68 } |
|
|
69 |
|
|
70 /* test_alarm_func() is invoked as an alarm handler, so |
|
|
71 it should be quick and simple. in this case it increments |
|
|
72 the data that is passed to it. */ |
|
|
73 void test_alarm_func(cyg_handle_t alarmH, cyg_addrword_t data) |
|
|
74 { |
|
|
75 ++*((unsigned *) data); |
|
|
76 } |