timer_tc.c 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747
  1. /*
  2. * Copyright (c) 2006-2019, RT-Thread Development Team
  3. *
  4. * SPDX-License-Identifier: Apache-2.0
  5. *
  6. * Change Logs:
  7. * Date Author Notes
  8. * 2021-08-12 luckyzjq the first version
  9. */
  10. #include <rtthread.h>
  11. #include <stdlib.h>
  12. #include "utest.h"
  13. #undef uassert_true
  14. #define uassert_true(value) \
  15. do \
  16. { \
  17. if (!(value)) \
  18. { \
  19. __utest_assert(value, "(" #value ") is false"); \
  20. } \
  21. } while (0)
  22. /* notify user that the test is not corrupted */
  23. #define PRINT_PROGRESS(id) LOG_I("Testing on %d", id)
  24. static rt_uint8_t timer_flag_oneshot[] = {
  25. RT_TIMER_FLAG_ONE_SHOT,
  26. RT_TIMER_FLAG_ONE_SHOT | RT_TIMER_FLAG_HARD_TIMER,
  27. RT_TIMER_FLAG_ONE_SHOT | RT_TIMER_FLAG_SOFT_TIMER,
  28. };
  29. static rt_uint8_t timer_flag_periodic[] = {
  30. RT_TIMER_FLAG_PERIODIC,
  31. RT_TIMER_FLAG_PERIODIC | RT_TIMER_FLAG_HARD_TIMER,
  32. RT_TIMER_FLAG_PERIODIC | RT_TIMER_FLAG_SOFT_TIMER,
  33. };
  34. typedef struct test_timer_struct
  35. {
  36. struct rt_timer static_timer; /* static timer handler */
  37. rt_timer_t dynamic_timer; /* dynamic timer pointer */
  38. rt_tick_t expect_tick; /* expect tick */
  39. rt_ubase_t callbacks; /* timer callback times */
  40. rt_bool_t is_static; /* static or dynamic timer */
  41. } timer_struct;
  42. static timer_struct timer;
  43. static void timer_oneshot(void *param)
  44. {
  45. timer_struct *timer_call;
  46. timer_call = (timer_struct *)param;
  47. timer_call->callbacks++;
  48. uassert_true(rt_tick_get() == timer_call->expect_tick);
  49. }
  50. static void timer_periodic(void *param)
  51. {
  52. rt_err_t result;
  53. timer_struct *timer_call;
  54. timer_call = (timer_struct *)param;
  55. timer_call->callbacks++;
  56. uassert_true(rt_tick_get() == timer_call->expect_tick);
  57. if (timer_call->is_static)
  58. {
  59. timer_call->expect_tick = rt_tick_get() + timer_call->static_timer.init_tick;
  60. }
  61. else
  62. {
  63. timer_call->expect_tick = rt_tick_get() + timer_call->dynamic_timer->init_tick;
  64. }
  65. if (timer_call->callbacks == 5)
  66. {
  67. /* periodic timer can stop */
  68. if (timer_call->is_static)
  69. {
  70. result = rt_timer_stop(&timer_call->static_timer);
  71. }
  72. else
  73. {
  74. result = rt_timer_stop(timer_call->dynamic_timer);
  75. }
  76. uassert_true(result == RT_EOK);
  77. }
  78. }
  79. static void test_static_timer(void)
  80. {
  81. rt_err_t result;
  82. timer.callbacks = 0;
  83. timer.is_static = RT_TRUE;
  84. /* one shot timer test */
  85. for (int time_out = 1; time_out < 10; time_out++)
  86. {
  87. for (int i = 0; i < sizeof(timer_flag_oneshot); i++)
  88. {
  89. rt_timer_init(&timer.static_timer,
  90. "static_timer",
  91. timer_oneshot,
  92. &timer,
  93. time_out,
  94. timer_flag_oneshot[i]);
  95. /* calc expect tick */
  96. timer.expect_tick = rt_tick_get() + time_out;
  97. /* start timer */
  98. result = rt_timer_start(&timer.static_timer);
  99. uassert_true(result == RT_EOK);
  100. /* wait for timerout */
  101. rt_thread_delay(3 * time_out + 1);
  102. uassert_true(timer.callbacks == 1);
  103. /* detach timer */
  104. result = rt_timer_detach(&timer.static_timer);
  105. uassert_true(result == RT_EOK);
  106. timer.callbacks = 0;
  107. }
  108. }
  109. /* periodic timer test */
  110. for (int time_out = 1; time_out < 10; time_out++)
  111. {
  112. for (int i = 0; i < sizeof(timer_flag_periodic); i++)
  113. {
  114. rt_timer_init(&timer.static_timer,
  115. "static_timer",
  116. timer_periodic,
  117. &timer,
  118. time_out,
  119. timer_flag_periodic[i]);
  120. /* calc expect tick */
  121. timer.expect_tick = rt_tick_get() + time_out;
  122. /* start timer */
  123. result = rt_timer_start(&timer.static_timer);
  124. uassert_true(result == RT_EOK);
  125. /* wait for timerout */
  126. rt_thread_delay(5 * time_out + 1);
  127. uassert_true(timer.callbacks >= 5);
  128. /* detach timer */
  129. result = rt_timer_detach(&timer.static_timer);
  130. uassert_true(result == RT_EOK);
  131. timer.callbacks = 0;
  132. }
  133. }
  134. }
  135. static void test_static_timer_start_twice(void)
  136. {
  137. rt_err_t result;
  138. timer.callbacks = 0;
  139. timer.is_static = RT_TRUE;
  140. /* timer start twice test */
  141. for (int time_out = 2; time_out < 10; time_out++)
  142. {
  143. for (int i = 0; i < sizeof(timer_flag_oneshot); i++)
  144. {
  145. rt_timer_init(&timer.static_timer,
  146. "static_timer",
  147. timer_oneshot,
  148. &timer,
  149. time_out,
  150. timer_flag_oneshot[i]);
  151. /* calc expect tick */
  152. timer.expect_tick = rt_tick_get() + time_out;
  153. /* start timer */
  154. result = rt_timer_start(&timer.static_timer);
  155. uassert_true(result == RT_EOK);
  156. rt_thread_delay(1);
  157. /* calc expect tick */
  158. timer.expect_tick = rt_tick_get() + time_out;
  159. /* start timer */
  160. result = rt_timer_start(&timer.static_timer);
  161. uassert_true(result == RT_EOK);
  162. /* wait for timerout */
  163. rt_thread_delay(3 * time_out + 1);
  164. uassert_true(timer.callbacks == 1);
  165. /* detach timer */
  166. result = rt_timer_detach(&timer.static_timer);
  167. uassert_true(result == RT_EOK);
  168. timer.callbacks = 0;
  169. }
  170. }
  171. }
  172. static void timer_control(void *param)
  173. {
  174. rt_err_t result;
  175. timer_struct *timer_call;
  176. timer_call = (timer_struct *)param;
  177. timer_call->callbacks++;
  178. uassert_true(rt_tick_get() == timer_call->expect_tick);
  179. /* periodic timer can stop */
  180. if (timer_call->is_static)
  181. {
  182. result = rt_timer_stop(&timer_call->static_timer);
  183. }
  184. else
  185. {
  186. result = rt_timer_stop(timer_call->dynamic_timer);
  187. }
  188. uassert_true(result == RT_EOK);
  189. }
  190. static void test_static_timer_control(void)
  191. {
  192. rt_err_t result;
  193. int set_data;
  194. int get_data;
  195. timer.callbacks = 0;
  196. timer.is_static = RT_TRUE;
  197. rt_timer_init(&timer.static_timer,
  198. "static_timer",
  199. timer_control,
  200. &timer,
  201. 5,
  202. RT_TIMER_FLAG_PERIODIC);
  203. /* test set data */
  204. set_data = 10;
  205. result = rt_timer_control(&timer.static_timer, RT_TIMER_CTRL_SET_TIME, &set_data);
  206. uassert_true(result == RT_EOK);
  207. /* test get data */
  208. result = rt_timer_control(&timer.static_timer, RT_TIMER_CTRL_GET_TIME, &get_data);
  209. uassert_true(result == RT_EOK);
  210. uassert_true(set_data == get_data);
  211. /* calc expect tick */
  212. timer.expect_tick = rt_tick_get() + set_data;
  213. /* start timer */
  214. result = rt_timer_start(&timer.static_timer);
  215. uassert_true(result == RT_EOK);
  216. rt_thread_delay(3 * set_data + 1);
  217. /* detach timer */
  218. result = rt_timer_detach(&timer.static_timer);
  219. uassert_true(result == RT_EOK);
  220. uassert_true(timer.callbacks == 1);
  221. }
  222. static void timer_start_in_callback(void *param)
  223. {
  224. rt_err_t result;
  225. timer_struct *timer_call;
  226. timer_call = (timer_struct *)param;
  227. timer_call->callbacks++;
  228. uassert_true(rt_tick_get() == timer_call->expect_tick);
  229. if (timer_call->is_static)
  230. {
  231. timer_call->expect_tick = rt_tick_get() + timer_call->static_timer.init_tick;
  232. result = rt_timer_start(&timer_call->static_timer);
  233. }
  234. else
  235. {
  236. timer_call->expect_tick = rt_tick_get() + timer_call->dynamic_timer->init_tick;
  237. result = rt_timer_start(timer_call->dynamic_timer);
  238. }
  239. uassert_true(result == RT_EOK);
  240. }
  241. static void timer_start_stop_in_callback(void *param)
  242. {
  243. rt_err_t result;
  244. timer_struct *timer_call;
  245. timer_call = (timer_struct *)param;
  246. timer_call->callbacks++;
  247. uassert_true(rt_tick_get() == timer_call->expect_tick);
  248. if (timer_call->is_static)
  249. {
  250. result = rt_timer_start(&timer_call->static_timer);
  251. }
  252. else
  253. {
  254. result = rt_timer_start(timer_call->dynamic_timer);
  255. }
  256. uassert_true(result == RT_EOK);
  257. if (timer_call->is_static)
  258. {
  259. result = rt_timer_stop(&timer_call->static_timer);
  260. }
  261. else
  262. {
  263. result = rt_timer_stop(timer_call->dynamic_timer);
  264. }
  265. uassert_true(result == RT_EOK);
  266. }
  267. static void test_static_timer_op_in_callback(void)
  268. {
  269. rt_err_t result;
  270. timer.callbacks = 0;
  271. timer.is_static = RT_TRUE;
  272. /* start in callback test */
  273. for (int time_out = 1; time_out < 10; time_out++)
  274. {
  275. for (int i = 0; i < sizeof(timer_flag_oneshot); i++)
  276. {
  277. rt_timer_init(&timer.static_timer,
  278. "static_timer",
  279. timer_start_in_callback,
  280. &timer,
  281. time_out,
  282. timer_flag_oneshot[i]);
  283. /* calc expect tick */
  284. timer.expect_tick = rt_tick_get() + time_out;
  285. /* start timer */
  286. result = rt_timer_start(&timer.static_timer);
  287. uassert_true(result == RT_EOK);
  288. /* wait for timerout */
  289. rt_thread_delay(5 * time_out + 1);
  290. uassert_true(timer.callbacks >= 5);
  291. /* detach timer */
  292. result = rt_timer_detach(&timer.static_timer);
  293. uassert_true(result == RT_EOK);
  294. timer.callbacks = 0;
  295. }
  296. }
  297. /* start & stop in callback test */
  298. for (int time_out = 1; time_out < 10; time_out++)
  299. {
  300. for (int i = 0; i < sizeof(timer_flag_periodic); i++)
  301. {
  302. rt_timer_init(&timer.static_timer,
  303. "static_timer",
  304. timer_start_stop_in_callback,
  305. &timer,
  306. time_out,
  307. timer_flag_periodic[i]);
  308. /* calc expect tick */
  309. timer.expect_tick = rt_tick_get() + time_out;
  310. /* start timer */
  311. result = rt_timer_start(&timer.static_timer);
  312. uassert_true(result == RT_EOK);
  313. /* wait for timerout */
  314. rt_thread_delay(3 * time_out + 1);
  315. uassert_true(timer.callbacks == 1);
  316. /* detach timer */
  317. result = rt_timer_detach(&timer.static_timer);
  318. uassert_true(result == RT_EOK);
  319. timer.callbacks = 0;
  320. }
  321. }
  322. }
  323. #ifdef RT_USING_HEAP
  324. static void test_dynamic_timer(void)
  325. {
  326. rt_err_t result;
  327. timer.callbacks = 0;
  328. timer.is_static = RT_FALSE;
  329. /* one shot timer test */
  330. for (int time_out = 1; time_out < 10; time_out++)
  331. {
  332. for (int i = 0; i < sizeof(timer_flag_oneshot); i++)
  333. {
  334. timer.dynamic_timer = rt_timer_create("dynamic_timer",
  335. timer_oneshot,
  336. &timer,
  337. time_out,
  338. timer_flag_oneshot[i]);
  339. /* calc expect tick */
  340. timer.expect_tick = rt_tick_get() + time_out;
  341. /* start timer */
  342. result = rt_timer_start(timer.dynamic_timer);
  343. uassert_true(result == RT_EOK);
  344. /* wait for timerout */
  345. rt_thread_delay(3 * time_out + 1);
  346. uassert_true(timer.callbacks == 1);
  347. /* detach timer */
  348. result = rt_timer_delete(timer.dynamic_timer);
  349. uassert_true(result == RT_EOK);
  350. timer.callbacks = 0;
  351. }
  352. }
  353. /* periodic timer test */
  354. for (int time_out = 1; time_out < 10; time_out++)
  355. {
  356. for (int i = 0; i < sizeof(timer_flag_periodic); i++)
  357. {
  358. timer.dynamic_timer = rt_timer_create("dynamic_timer",
  359. timer_periodic,
  360. &timer,
  361. time_out,
  362. timer_flag_periodic[i]);
  363. /* calc expect tick */
  364. timer.expect_tick = rt_tick_get() + time_out;
  365. /* start timer */
  366. result = rt_timer_start(timer.dynamic_timer);
  367. uassert_true(result == RT_EOK);
  368. /* wait for timerout */
  369. rt_thread_delay(5 * time_out + 1);
  370. uassert_true(timer.callbacks >= 5);
  371. /* detach timer */
  372. result = rt_timer_delete(timer.dynamic_timer);
  373. uassert_true(result == RT_EOK);
  374. timer.callbacks = 0;
  375. }
  376. }
  377. }
  378. static void test_dynamic_timer_control(void)
  379. {
  380. rt_err_t result;
  381. int set_data;
  382. int get_data;
  383. timer.callbacks = 0;
  384. timer.is_static = RT_FALSE;
  385. timer.dynamic_timer = rt_timer_create("dynamic_timer",
  386. timer_control,
  387. &timer,
  388. 5,
  389. RT_TIMER_FLAG_PERIODIC);
  390. /* test set data */
  391. set_data = 10;
  392. result = rt_timer_control(timer.dynamic_timer, RT_TIMER_CTRL_SET_TIME, &set_data);
  393. uassert_true(result == RT_EOK);
  394. /* test get data */
  395. result = rt_timer_control(timer.dynamic_timer, RT_TIMER_CTRL_GET_TIME, &get_data);
  396. uassert_true(result == RT_EOK);
  397. uassert_true(set_data == get_data);
  398. /* calc expect tick */
  399. timer.expect_tick = rt_tick_get() + set_data;
  400. /* start timer */
  401. result = rt_timer_start(timer.dynamic_timer);
  402. uassert_true(result == RT_EOK);
  403. rt_thread_delay(3 * set_data + 1);
  404. /* detach timer */
  405. result = rt_timer_delete(timer.dynamic_timer);
  406. uassert_true(result == RT_EOK);
  407. uassert_true(timer.callbacks == 1);
  408. }
  409. static void test_dynamic_timer_start_twice(void)
  410. {
  411. rt_err_t result;
  412. timer.callbacks = 0;
  413. timer.is_static = RT_FALSE;
  414. /* timer start twice test */
  415. for (int time_out = 2; time_out < 10; time_out++)
  416. {
  417. for (int i = 0; i < sizeof(timer_flag_oneshot); i++)
  418. {
  419. timer.dynamic_timer = rt_timer_create("dynamic_timer",
  420. timer_oneshot,
  421. &timer,
  422. time_out,
  423. timer_flag_oneshot[i]);
  424. /* calc expect tick */
  425. timer.expect_tick = rt_tick_get() + time_out;
  426. /* start timer */
  427. result = rt_timer_start(timer.dynamic_timer);
  428. uassert_true(result == RT_EOK);
  429. rt_thread_delay(1);
  430. /* calc expect tick */
  431. timer.expect_tick = rt_tick_get() + time_out;
  432. /* start timer */
  433. result = rt_timer_start(timer.dynamic_timer);
  434. uassert_true(result == RT_EOK);
  435. /* wait for timerout */
  436. rt_thread_delay(3 * time_out + 1);
  437. uassert_true(timer.callbacks == 1);
  438. /* detach timer */
  439. result = rt_timer_delete(timer.dynamic_timer);
  440. uassert_true(result == RT_EOK);
  441. timer.callbacks = 0;
  442. }
  443. }
  444. }
  445. static void test_dynamic_timer_op_in_callback(void)
  446. {
  447. rt_err_t result;
  448. timer.callbacks = 0;
  449. timer.is_static = RT_FALSE;
  450. /* start in callback test */
  451. for (int time_out = 1; time_out < 10; time_out++)
  452. {
  453. for (int i = 0; i < sizeof(timer_flag_oneshot); i++)
  454. {
  455. timer.dynamic_timer = rt_timer_create("dynamic_timer",
  456. timer_start_in_callback,
  457. &timer,
  458. time_out,
  459. timer_flag_oneshot[i]);
  460. /* calc expect tick */
  461. timer.expect_tick = rt_tick_get() + time_out;
  462. /* start timer */
  463. result = rt_timer_start(timer.dynamic_timer);
  464. uassert_true(result == RT_EOK);
  465. /* wait for timerout */
  466. rt_thread_delay(5 * time_out + 1);
  467. uassert_true(timer.callbacks >= 5);
  468. /* detach timer */
  469. result = rt_timer_delete(timer.dynamic_timer);
  470. uassert_true(result == RT_EOK);
  471. timer.callbacks = 0;
  472. }
  473. }
  474. /* start & stop in callback test */
  475. for (int time_out = 1; time_out < 10; time_out++)
  476. {
  477. for (int i = 0; i < sizeof(timer_flag_periodic); i++)
  478. {
  479. timer.dynamic_timer = rt_timer_create("dynamic_timer",
  480. timer_start_stop_in_callback,
  481. &timer,
  482. time_out,
  483. timer_flag_periodic[i]);
  484. /* calc expect tick */
  485. timer.expect_tick = rt_tick_get() + time_out;
  486. /* start timer */
  487. result = rt_timer_start(timer.dynamic_timer);
  488. uassert_true(result == RT_EOK);
  489. /* wait for timerout */
  490. rt_thread_delay(3 * time_out + 1);
  491. uassert_true(timer.callbacks == 1);
  492. /* detach timer */
  493. result = rt_timer_delete(timer.dynamic_timer);
  494. uassert_true(result == RT_EOK);
  495. timer.callbacks = 0;
  496. }
  497. }
  498. }
  499. #endif /* RT_USING_HEAP */
  500. #define TEST_TIME_S 60 // test 60 seconds
  501. #define STRESS_TIMERS 100
  502. static struct rt_timer stress_timer[STRESS_TIMERS];
  503. static void timer_stress(void *param)
  504. {
  505. rt_timer_t stress_timer = (rt_timer_t)param;
  506. if (rand() % 2 == 0)
  507. {
  508. rt_timer_start(stress_timer);
  509. }
  510. else
  511. {
  512. rt_timer_stop(stress_timer);
  513. }
  514. }
  515. static void test_timer_stress(void)
  516. {
  517. rt_tick_t start;
  518. rt_ubase_t iters = 0;
  519. rt_ubase_t cur_tick;
  520. rt_ubase_t next_print_time;
  521. LOG_I("timer stress test begin, it will take %d seconds", 3*TEST_TIME_S);
  522. for (int i = 0; i < sizeof(timer_flag_periodic); i++)
  523. {
  524. for (int j = 0; j < STRESS_TIMERS; j++)
  525. {
  526. rt_timer_init(&stress_timer[j],
  527. "stress_timer",
  528. timer_stress,
  529. &stress_timer[j],
  530. j + 1,
  531. timer_flag_periodic[i]);
  532. }
  533. start = rt_tick_get();
  534. cur_tick = rt_tick_get();
  535. next_print_time = cur_tick + RT_TICK_PER_SECOND;
  536. while (cur_tick - start <= TEST_TIME_S * RT_TICK_PER_SECOND)
  537. {
  538. for (int j = 0; j < STRESS_TIMERS; j++)
  539. {
  540. if (rand() % 2 == 0)
  541. {
  542. rt_timer_start(&stress_timer[j]);
  543. }
  544. else
  545. {
  546. rt_timer_stop(&stress_timer[j]);
  547. }
  548. }
  549. iters ++;
  550. cur_tick = rt_tick_get();
  551. if (cur_tick > next_print_time)
  552. {
  553. PRINT_PROGRESS(next_print_time);
  554. next_print_time = cur_tick + RT_TICK_PER_SECOND;
  555. }
  556. }
  557. for (int j = 0; j < STRESS_TIMERS; j++)
  558. {
  559. rt_timer_detach(&stress_timer[j]);
  560. }
  561. }
  562. LOG_I("success after %lu iterations", iters);
  563. }
  564. static rt_err_t utest_tc_init(void)
  565. {
  566. timer.dynamic_timer = RT_NULL;
  567. timer.callbacks = 0;
  568. return RT_EOK;
  569. }
  570. static rt_err_t utest_tc_cleanup(void)
  571. {
  572. timer.dynamic_timer = RT_NULL;
  573. timer.callbacks = 0;
  574. return RT_EOK;
  575. }
  576. static void testcase(void)
  577. {
  578. UTEST_UNIT_RUN(test_static_timer);
  579. PRINT_PROGRESS(__LINE__);
  580. UTEST_UNIT_RUN(test_static_timer_control);
  581. PRINT_PROGRESS(__LINE__);
  582. UTEST_UNIT_RUN(test_static_timer_start_twice);
  583. PRINT_PROGRESS(__LINE__);
  584. UTEST_UNIT_RUN(test_static_timer_op_in_callback);
  585. PRINT_PROGRESS(__LINE__);
  586. #ifdef RT_USING_HEAP
  587. UTEST_UNIT_RUN(test_dynamic_timer);
  588. PRINT_PROGRESS(__LINE__);
  589. UTEST_UNIT_RUN(test_dynamic_timer_control);
  590. PRINT_PROGRESS(__LINE__);
  591. UTEST_UNIT_RUN(test_dynamic_timer_start_twice);
  592. PRINT_PROGRESS(__LINE__);
  593. UTEST_UNIT_RUN(test_dynamic_timer_op_in_callback);
  594. PRINT_PROGRESS(__LINE__);
  595. #endif /* RT_USING_HEAP */
  596. UTEST_UNIT_RUN(test_timer_stress);
  597. PRINT_PROGRESS(__LINE__);
  598. }
  599. UTEST_TC_EXPORT(testcase, "testcases.kernel.timer_tc", utest_tc_init, utest_tc_cleanup, 1000);
  600. /*********************** end of file ****************************/