source: rtems/testsuites/libtests/block05/init.c @ 64734fc

4.104.115
Last change on this file since 64734fc was 64734fc, checked in by Thomas Doerfler <Thomas.Doerfler@…>, on 01/19/10 at 08:55:18

updates and new test cases

  • Property mode set to 100644
File size: 10.3 KB
Line 
1/**
2 * @file
3 *
4 * @ingroup test_bdbuf
5 *
6 * @brief Bdbuf test.
7 */
8
9/*
10 * Copyright (c) 2009
11 * embedded brains GmbH
12 * Obere Lagerstr. 30
13 * D-82178 Puchheim
14 * Germany
15 * <rtems@embedded-brains.de>
16 *
17 * The license and distribution terms for this file may be
18 * found in the file LICENSE in this distribution or at
19 * http://www.rtems.com/license/LICENSE.
20 */
21
22#include "tmacros.h"
23#include <stdarg.h>
24#include <errno.h>
25
26#include <rtems.h>
27#include <rtems/bdbuf.h>
28#include <rtems/diskdevs.h>
29
30#define ASSERT_SC(sc) rtems_test_assert((sc) == RTEMS_SUCCESSFUL)
31
32#define PRIORITY_INIT 1
33
34#define PRIORITY_HIGH 2
35
36#define PRIORITY_LOW_ALT 3
37
38#define PRIORITY_SWAPOUT 4
39
40#define PRIORITY_LOW 5
41
42#define PRIORITY_RESUME 6
43
44#define BLOCK_SIZE_A 1
45
46#define BLOCK_COUNT_A 2
47
48#define BLOCK_SIZE_B 2
49
50#define BLOCK_COUNT_B 1
51
52/* In case of trouble change this to 1 or 2 for more output */
53static unsigned output_level = 0;
54
55static dev_t dev_a;
56
57static dev_t dev_b;
58
59static rtems_id task_id_init;
60
61static rtems_id task_id_low;
62
63static rtems_id task_id_high;
64
65static rtems_id task_id_resume;
66
67static volatile bool finish_low;
68
69static volatile bool finish_high;
70
71static volatile enum resume_style {
72  RESUME_IMMEDIATE,
73  RESUME_FINISH
74} resume;
75
76static volatile enum trig_style {
77  SUSP = 0,
78  CONT
79} trig;
80
81static volatile enum get_type {
82  GET = 0,
83  READ
84} trig_get, low_get, high_get;
85
86static volatile enum blk_kind {
87  BLK_A0 = 0,
88  BLK_A1,
89  BLK_B0
90} trig_blk, low_blk, high_blk;
91
92static volatile enum rel_type {
93  REL = 0,
94  REL_MOD,
95  SYNC
96} trig_rel, low_rel, high_rel;
97
98static const char trig_style_desc [] = {
99  'S',
100  'C'
101};
102
103static const char get_type_desc [] = {
104  'G',
105  'R'
106};
107
108static const char *blk_kind_desc [] = {
109  "A0",
110  "A1",
111  "B0"
112};
113
114static const char rel_type_desc [] = {
115  'R',
116  'M',
117  'S'
118};
119
120static void print(unsigned level, const char *fmt, ...)
121{
122  if (level <= output_level) {
123    va_list ap;
124
125    va_start(ap, fmt);
126    vprintk(fmt, ap);
127    va_end(ap);
128  }
129}
130
131static void set_task_prio(rtems_id task, rtems_task_priority prio)
132{
133  rtems_status_code sc = RTEMS_SUCCESSFUL;
134  rtems_task_priority cur = 0;
135
136  sc = rtems_task_set_priority(task, prio, &cur);
137  ASSERT_SC(sc);
138}
139
140static rtems_bdbuf_buffer *get(enum get_type type, enum blk_kind kind)
141{
142  rtems_status_code sc = RTEMS_SUCCESSFUL;
143  rtems_bdbuf_buffer *bd = NULL;
144  rtems_blkdev_bnum blk_index = 0;
145  rtems_status_code (*get_bd)(dev_t, rtems_blkdev_bnum, rtems_bdbuf_buffer **)
146    = NULL;
147  dev_t dev = 0;
148  size_t bds_per_group = 0;
149
150  switch (kind) {
151    case BLK_A0:
152      dev = dev_a;
153      blk_index = 0;
154      bds_per_group = 2;
155      break;
156    case BLK_A1:
157      dev = dev_a;
158      blk_index = 1;
159      bds_per_group = 2;
160      break;
161    case BLK_B0:
162      dev = dev_b;
163      blk_index = 0;
164      bds_per_group = 1;
165      break;
166    default:
167      rtems_test_assert(false);
168      break;
169  }
170
171  switch (type) {
172    case GET:
173      get_bd = rtems_bdbuf_get;
174      break;
175    case READ:
176      get_bd = rtems_bdbuf_read;
177      break;
178    default:
179      rtems_test_assert(false);
180      break;
181  }
182
183  sc = (*get_bd)(dev, blk_index, &bd);
184  rtems_test_assert(
185    sc == RTEMS_SUCCESSFUL
186      && bd->dev == dev
187      && bd->block == blk_index
188      && bd->group->bds_per_group == bds_per_group
189   );
190
191  return bd;
192}
193
194static void rel(rtems_bdbuf_buffer *bd, enum rel_type type)
195{
196  rtems_status_code sc = RTEMS_SUCCESSFUL;
197  rtems_status_code (*rel_bd)(rtems_bdbuf_buffer *) = NULL;
198
199  switch (type) {
200    case REL:
201      rel_bd = rtems_bdbuf_release;
202      break;
203    case REL_MOD:
204      rel_bd = rtems_bdbuf_release_modified;
205      break;
206    case SYNC:
207      rel_bd = rtems_bdbuf_sync;
208      break;
209    default:
210      rtems_test_assert(false);
211      break;
212  }
213
214  sc = (*rel_bd)(bd);
215  ASSERT_SC(sc);
216}
217
218static void task_low(rtems_task_argument arg)
219{
220  rtems_status_code sc = RTEMS_SUCCESSFUL;
221
222  while (true) {
223    print(2, "LG\n");
224    rtems_bdbuf_buffer *bd = get(low_get, low_blk);
225
226    print(2, "LR\n");
227    rel(bd, low_rel);
228
229    finish_low = true;
230
231    sc = rtems_task_suspend(RTEMS_SELF);
232    ASSERT_SC(sc);
233  }
234}
235
236static void task_high(rtems_task_argument arg)
237{
238  rtems_status_code sc = RTEMS_SUCCESSFUL;
239
240  while (true) {
241    print(2, "HG\n");
242    rtems_bdbuf_buffer *bd = get(high_get, high_blk);
243
244    print(2, "HR\n");
245    rel(bd, high_rel);
246
247    finish_high = true;
248
249    sc = rtems_task_suspend(RTEMS_SELF);
250    ASSERT_SC(sc);
251  }
252}
253
254static void task_resume(rtems_task_argument arg)
255{
256  while (true) {
257    bool do_resume = false;
258
259    switch (resume) {
260      case RESUME_IMMEDIATE:
261        print(2, "RI\n");
262        do_resume = true;
263        break;
264      case RESUME_FINISH:
265        print(2, "RF\n");
266        do_resume = finish_low && finish_high;
267        break;
268      default:
269        rtems_test_assert(false);
270        break;
271    }
272
273    if (do_resume) {
274      rtems_task_resume(task_id_init);
275    }
276  }
277}
278
279static void execute_test(unsigned i)
280{
281  rtems_status_code sc = RTEMS_SUCCESSFUL;
282  rtems_bdbuf_buffer *bd = NULL;
283  bool suspend = false;
284
285  print(
286    1,
287    "[%05u]T(%c,%c,%s,%c)L(%c,%s,%c)H(%c,%s,%c)\n",
288    i,
289    trig_style_desc [trig],
290    get_type_desc [trig_get],
291    blk_kind_desc [trig_blk],
292    rel_type_desc [trig_rel],
293    get_type_desc [low_get],
294    blk_kind_desc [low_blk],
295    rel_type_desc [low_rel],
296    get_type_desc [high_get],
297    blk_kind_desc [high_blk],
298    rel_type_desc [high_rel]
299  );
300
301  set_task_prio(task_id_low, PRIORITY_LOW);
302
303  finish_low = false;
304  finish_high = false;
305
306  sc = rtems_task_resume(task_id_low);
307  ASSERT_SC(sc);
308
309  sc = rtems_task_resume(task_id_high);
310  ASSERT_SC(sc);
311
312  sc = rtems_bdbuf_get(dev_b, 0, &bd);
313  rtems_test_assert(sc == RTEMS_SUCCESSFUL && bd->dev == dev_b && bd->block == 0);
314
315  sc = rtems_bdbuf_release(bd);
316  ASSERT_SC(sc);
317
318  switch (trig) {
319    case SUSP:
320      suspend = true;
321      break;
322    case CONT:
323      suspend = false;
324      break;
325    default:
326      rtems_test_assert(false);
327      break;
328  }
329
330  print(2, "TG\n");
331  bd = get(trig_get, trig_blk);
332
333  if (suspend) {
334    print(2, "S\n");
335    resume = RESUME_IMMEDIATE;
336    sc = rtems_task_suspend(RTEMS_SELF);
337    ASSERT_SC(sc);
338  }
339  resume = RESUME_FINISH;
340
341  print(2, "TR\n");
342  rel(bd, trig_rel);
343
344  sc = rtems_task_suspend(RTEMS_SELF);
345  ASSERT_SC(sc);
346
347  print(2, "F\n");
348
349  sc = rtems_bdbuf_syncdev(dev_a);
350  ASSERT_SC(sc);
351
352  sc = rtems_bdbuf_syncdev(dev_b);
353  ASSERT_SC(sc);
354}
355
356static const rtems_driver_address_table disk_ops = {
357  .initialization_entry = NULL,
358  RTEMS_GENERIC_BLOCK_DEVICE_DRIVER_ENTRIES
359};
360
361static int disk_ioctl(rtems_disk_device *dd, uint32_t req, void *argp)
362{
363  if (req == RTEMS_BLKIO_REQUEST) {
364    rtems_blkdev_request *r = argp;
365
366    set_task_prio(task_id_low, PRIORITY_LOW_ALT);
367
368    switch (r->req) {
369      case RTEMS_BLKDEV_REQ_READ:
370      case RTEMS_BLKDEV_REQ_WRITE:
371        r->req_done(r->done_arg, RTEMS_SUCCESSFUL);
372        return 0;
373      default:
374        errno = EINVAL;
375        return -1;
376    }
377  } else {
378    return rtems_blkdev_ioctl(dd, req, argp);
379  }
380}
381
382rtems_status_code disk_register(
383  uint32_t block_size,
384  rtems_blkdev_bnum block_count,
385  dev_t *dev_ptr
386)
387{
388  rtems_status_code sc = RTEMS_SUCCESSFUL;
389  rtems_device_major_number major = 0;
390  dev_t dev = 0;
391
392  sc = rtems_io_register_driver(0, &disk_ops, &major);
393  ASSERT_SC(sc);
394
395  dev = rtems_filesystem_make_dev_t(major, 0);
396
397  sc = rtems_disk_create_phys(
398    dev,
399    block_size,
400    block_count,
401    disk_ioctl,
402    NULL,
403    NULL
404  );
405  ASSERT_SC(sc);
406
407  *dev_ptr = dev;
408
409  return RTEMS_SUCCESSFUL;
410}
411
412static rtems_task Init(rtems_task_argument argument)
413{
414  rtems_status_code sc = RTEMS_SUCCESSFUL;
415  unsigned i = 0;
416
417  printk("\n\n*** TEST BLOCK 5 ***\n");
418
419  task_id_init = rtems_task_self();
420
421  sc = rtems_disk_io_initialize();
422  ASSERT_SC(sc);
423
424  sc = disk_register(BLOCK_SIZE_A, BLOCK_COUNT_A, &dev_a);
425  ASSERT_SC(sc);
426
427  sc = disk_register(BLOCK_SIZE_B, BLOCK_COUNT_B, &dev_b);
428  ASSERT_SC(sc);
429
430  sc = rtems_task_create(
431    rtems_build_name(' ', 'L', 'O', 'W'),
432    PRIORITY_LOW,
433    0,
434    RTEMS_DEFAULT_MODES,
435    RTEMS_DEFAULT_ATTRIBUTES,
436    &task_id_low
437  );
438  ASSERT_SC(sc);
439
440  sc = rtems_task_start(task_id_low, task_low, 0);
441  ASSERT_SC(sc);
442
443  sc = rtems_task_create(
444    rtems_build_name('H', 'I', 'G', 'H'),
445    PRIORITY_HIGH,
446    0,
447    RTEMS_DEFAULT_MODES,
448    RTEMS_DEFAULT_ATTRIBUTES,
449    &task_id_high
450  );
451  ASSERT_SC(sc);
452
453  sc = rtems_task_start(task_id_high, task_high, 0);
454  ASSERT_SC(sc);
455
456  sc = rtems_task_create(
457    rtems_build_name('R', 'E', 'S', 'U'),
458    PRIORITY_RESUME,
459    0,
460    RTEMS_DEFAULT_MODES,
461    RTEMS_DEFAULT_ATTRIBUTES,
462    &task_id_resume
463  );
464  ASSERT_SC(sc);
465
466  sc = rtems_task_start(task_id_resume, task_resume, 0);
467  ASSERT_SC(sc);
468
469  sc = rtems_task_suspend(task_id_low);
470  ASSERT_SC(sc);
471
472  sc = rtems_task_suspend(task_id_high);
473  ASSERT_SC(sc);
474
475  for (trig = SUSP; trig <= CONT; ++trig) {
476    for (trig_get = GET; trig_get <= READ; ++trig_get) {
477      for (low_get = GET; low_get <= READ; ++low_get) {
478        for (high_get = GET; high_get <= READ; ++high_get) {
479          for (trig_blk = BLK_A0; trig_blk <= BLK_B0; ++trig_blk) {
480            for (low_blk = BLK_A0; low_blk <= BLK_B0; ++low_blk) {
481              for (high_blk = BLK_A0; high_blk <= BLK_B0; ++high_blk) {
482                for (trig_rel = REL; trig_rel <= SYNC; ++trig_rel) {
483                  for (low_rel = REL; low_rel <= SYNC; ++low_rel) {
484                    for (high_rel = REL; high_rel <= SYNC; ++high_rel) {
485                      execute_test(i);
486                      ++i;
487                    }
488                  }
489                }
490              }
491            }
492          }
493        }
494      }
495    }
496  }
497
498  printk("*** END OF TEST BLOCK 5 ***\n");
499
500  exit(0);
501}
502
503#define CONFIGURE_INIT
504
505#define CONFIGURE_APPLICATION_NEEDS_CLOCK_DRIVER
506#define CONFIGURE_APPLICATION_NEEDS_CONSOLE_DRIVER
507#define CONFIGURE_APPLICATION_NEEDS_LIBBLOCK
508
509#define CONFIGURE_USE_IMFS_AS_BASE_FILESYSTEM
510
511#define CONFIGURE_MAXIMUM_TASKS 6
512#define CONFIGURE_MAXIMUM_DRIVERS 4
513#define CONFIGURE_MAXIMUM_SEMAPHORES 5
514
515#define CONFIGURE_RTEMS_INIT_TASKS_TABLE
516
517#define CONFIGURE_INIT_TASK_PRIORITY PRIORITY_INIT
518#define CONFIGURE_INIT_TASK_ATTRIBUTES RTEMS_DEFAULT_ATTRIBUTES
519#define CONFIGURE_INIT_TASK_INITIAL_MODES RTEMS_DEFAULT_MODES
520
521#define CONFIGURE_SWAPOUT_TASK_PRIORITY PRIORITY_SWAPOUT
522
523#define CONFIGURE_BDBUF_BUFFER_MIN_SIZE BLOCK_SIZE_A
524#define CONFIGURE_BDBUF_BUFFER_MAX_SIZE BLOCK_SIZE_B
525#define CONFIGURE_BDBUF_CACHE_MEMORY_SIZE BLOCK_SIZE_B
526
527#include <rtems/confdefs.h>
Note: See TracBrowser for help on using the repository browser.