Changeset 8028089 in rtems


Ignore:
Timestamp:
Sep 8, 2014, 1:18:07 PM (5 years ago)
Author:
Sebastian Huber <sebastian.huber@…>
Branches:
4.11, master
Children:
5674767
Parents:
80ad7090
git-author:
Sebastian Huber <sebastian.huber@…> (09/08/14 13:18:07)
git-committer:
Sebastian Huber <sebastian.huber@…> (09/10/14 05:12:55)
Message:

tests: Rework interrupt critical tests

This avoids test durations of more than one hour on fast targets, since
fast targets can count a lot during one clock tick period, so the minor
loop iteration count was quite high. Estimate now the test body
duration to iterate only through the interesting time window.

Add and use interrupt_critical_section_test().

Location:
testsuites
Files:
14 edited

Legend:

Unmodified
Added
Removed
  • testsuites/psxtests/psxintrcritical01/init.c

    r80ad7090 r8028089  
    2020/* forward declarations to avoid warnings */
    2121rtems_task Init(rtems_task_argument ignored);
    22 rtems_timer_service_routine test_release_from_isr(rtems_id timer, void *arg);
    2322
    2423#define TEST_NAME          "01"
    2524#define TEST_STRING        "POSIX Timer"
    2625
    27 rtems_id          Main_task;
    28 timer_t           Timer;
    29 struct itimerspec TimerParams;
     26static timer_t           Timer;
     27static struct itimerspec TimerParams;
    3028
    3129#define POSIX_TIMER_RELATIVE 0
    3230
    33 rtems_timer_service_routine test_release_from_isr(
     31static bool test_body( void *arg )
     32{
     33  int rv;
     34
     35  (void) arg;
     36
     37  rv = timer_settime(Timer, POSIX_TIMER_RELATIVE, &TimerParams, NULL);
     38  rtems_test_assert( rv == 0 );
     39
     40  return false;
     41}
     42
     43static rtems_timer_service_routine test_release_from_isr(
    3444  rtems_id  timer,
    3545  void     *arg
    3646)
    3747{
    38   (void) timer_settime(Timer, POSIX_TIMER_RELATIVE, &TimerParams, NULL);
     48  test_body( NULL );
    3949}
    4050
     
    4353)
    4454{
    45   int    sc;
    46   int    resets;
     55  int sc;
    4756
    4857  TEST_BEGIN();
     
    6069  }
    6170
    62   Main_task = rtems_task_self();
    63 
    6471  /* we don't care if it ever fires */
    6572  TimerParams.it_interval.tv_sec  = 10;
     
    6875  TimerParams.it_value.tv_nsec    = 0;
    6976
    70   interrupt_critical_section_test_support_initialize( test_release_from_isr );
    71 
    72   for (resets=0 ; resets<10 ;) {
    73     if ( interrupt_critical_section_test_support_delay() )
    74       resets++;
    75 
    76     sc = timer_settime(Timer, POSIX_TIMER_RELATIVE, &TimerParams, NULL);
    77     if ( sc == -1 ) {
    78       perror ("Error in timer setting\n");
    79       rtems_test_exit(0);
    80     }
    81 
    82   }
     77  interrupt_critical_section_test( test_body, NULL, test_release_from_isr );
    8378
    8479  TEST_END();
     
    9489#define CONFIGURE_MAXIMUM_TIMERS         1
    9590#define CONFIGURE_MAXIMUM_POSIX_TIMERS   1
     91#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    9692#define CONFIGURE_MICROSECONDS_PER_TICK  1000
    9793#define CONFIGURE_INITIAL_EXTENSIONS RTEMS_TEST_INITIAL_EXTENSION
  • testsuites/sptests/spintrcritical01/init.c

    r80ad7090 r8028089  
    5959const char rtems_test_name[] = "SPINTRCRITICAL " TEST_NAME;
    6060
    61 rtems_id Main_task;
    6261rtems_id Semaphore;
    63 volatile bool case_hit;
     62volatile bool case_hit = false;
    6463
    6564Thread_blocking_operation_States getState(void)
     
    9594
    9695
     96static bool test_body( void *arg )
     97{
     98  rtems_status_code status;
     99
     100  (void) arg;
     101
     102  status = rtems_semaphore_obtain(
     103    Semaphore,
     104    RTEMS_DEFAULT_OPTIONS,
     105    SEMAPHORE_OBTAIN_TIMEOUT
     106  );
     107  directive_failed( status, "rtems_semaphore_obtain" );
     108
     109  return case_hit;
     110}
    97111
    98112rtems_task Init(
     
    108122  status = rtems_semaphore_create(
    109123    rtems_build_name( 'S', 'M', '1', ' ' ),
    110     1,
     124    0,
    111125    SEMAPHORE_ATTRIBUTES,
    112126    RTEMS_NO_PRIORITY,
     
    115129  directive_failed( status, "rtems_semaphore_create of SM1" );
    116130
    117   Main_task = rtems_task_self();
    118 
    119   interrupt_critical_section_test_support_initialize( test_release_from_isr );
    120 
    121   case_hit = false;
    122 
    123   while (!case_hit) {
    124     interrupt_critical_section_test_support_delay();
    125 
    126     status = rtems_semaphore_obtain(
    127       Semaphore,
    128       RTEMS_DEFAULT_OPTIONS,
    129       SEMAPHORE_OBTAIN_TIMEOUT
    130     );
    131     directive_failed( status, "rtems_semaphore_obtain" );
    132   }
     131  interrupt_critical_section_test( test_body, NULL, test_release_from_isr );
    133132
    134133  if ( case_hit ) {
     
    149148#define CONFIGURE_MAXIMUM_TIMERS      1
    150149#define CONFIGURE_MAXIMUM_SEMAPHORES  1
     150#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    151151#define CONFIGURE_MICROSECONDS_PER_TICK  1000
    152152#if defined(PRIORITY_NO_TIMEOUT_REVERSE)
  • testsuites/sptests/spintrcritical06/init.c

    r80ad7090 r8028089  
    7272}
    7373
     74static bool test_body( void *arg )
     75{
     76  (void) arg;
     77
     78  rtems_semaphore_obtain(
     79    Semaphore,
     80    RTEMS_DEFAULT_OPTIONS,
     81    SEMAPHORE_OBTAIN_TIMEOUT
     82  );
     83
     84  return false;
     85}
     86
    7487rtems_task Init(
    7588  rtems_task_argument ignored
     
    7790{
    7891  rtems_status_code     status;
    79   int                   resets;
    8092
    8193  TEST_BEGIN();
     
    106118  directive_failed( status, "rtems_task_start" );
    107119
    108   interrupt_critical_section_test_support_initialize( test_release_from_isr );
    109 
    110   for (resets=0 ; resets< 2 ;) {
    111     if ( interrupt_critical_section_test_support_delay() )
    112       resets++;
    113 
    114     status = rtems_semaphore_obtain(
    115       Semaphore,
    116       RTEMS_DEFAULT_OPTIONS,
    117       SEMAPHORE_OBTAIN_TIMEOUT
    118     );
    119   }
     120  interrupt_critical_section_test( test_body, NULL, test_release_from_isr );
    120121
    121122  TEST_END();
     
    131132#define CONFIGURE_MAXIMUM_TIMERS      1
    132133#define CONFIGURE_MAXIMUM_SEMAPHORES  1
     134#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    133135#define CONFIGURE_INIT_TASK_PRIORITY  INIT_PRIORITY
    134136#define CONFIGURE_INIT_TASK_INITIAL_MODES RTEMS_PREEMPT
  • testsuites/sptests/spintrcritical08/init.c

    r80ad7090 r8028089  
    1414#include <tmacros.h>
    1515#include <intrcritical.h>
     16#include <rtems/score/watchdogimpl.h>
    1617#include <rtems/rtems/ratemonimpl.h>
    1718
     
    2021/* forward declarations to avoid warnings */
    2122rtems_task Init(rtems_task_argument argument);
    22 rtems_timer_service_routine test_release_from_isr(rtems_id  timer, void *arg);
    23 rtems_rate_monotonic_period_states getState(void);
    2423
    25 rtems_id Main_task;
    26 rtems_id Period;
    27 volatile bool case_hit;
     24static rtems_id Period;
    2825
    29 rtems_rate_monotonic_period_states getState(void)
     26static volatile bool case_hit = false;
     27
     28static rtems_rate_monotonic_period_states getState(void)
    3029{
    3130  Objects_Locations       location;
     
    4342}
    4443
    45 rtems_timer_service_routine test_release_from_isr(
     44static rtems_timer_service_routine test_release_from_isr(
    4645  rtems_id  timer,
    4746  void     *arg
    4847)
    4948{
    50   if ( getState() == RATE_MONOTONIC_EXPIRED_WHILE_BLOCKING )
    51     case_hit = true;
     49  Chain_Control *chain = &_Watchdog_Ticks_chain;
     50
     51  if ( !_Chain_Is_empty( chain ) ) {
     52    Watchdog_Control *watchdog = _Watchdog_First( chain );
     53
     54    if (
     55      watchdog->delta_interval == 0
     56        && watchdog->routine == _Rate_monotonic_Timeout
     57    ) {
     58      Watchdog_States state = _Watchdog_Remove( watchdog );
     59
     60      rtems_test_assert( state == WATCHDOG_ACTIVE );
     61      (*watchdog->routine)( watchdog->id, watchdog->user_data );
     62
     63      if ( getState() == RATE_MONOTONIC_EXPIRED_WHILE_BLOCKING ) {
     64        case_hit = true;
     65      }
     66    }
     67  }
     68}
     69
     70static bool test_body( void *arg )
     71{
     72  rtems_status_code sc;
     73
     74  (void) arg;
     75
     76  sc = rtems_rate_monotonic_cancel( Period );
     77  rtems_test_assert( sc == RTEMS_SUCCESSFUL );
     78
     79  sc = rtems_rate_monotonic_period( Period, 1 );
     80  rtems_test_assert( sc == RTEMS_SUCCESSFUL );
     81
     82  sc = rtems_rate_monotonic_period( Period, 1 );
     83  rtems_test_assert( sc == RTEMS_SUCCESSFUL || sc == RTEMS_TIMEOUT );
     84
     85  return case_hit;
    5286}
    5387
     
    5791{
    5892  rtems_status_code     sc;
    59   int                   resets;
    6093
    6194  TEST_BEGIN();
     
    70103  directive_failed( sc, "rtems_rate_monotonic_create" );
    71104
    72   Main_task = rtems_task_self();
    73 
    74   interrupt_critical_section_test_support_initialize( test_release_from_isr );
    75 
    76   case_hit = false;
    77 
    78   for (resets=0 ; case_hit == false && resets< 2 ;) {
    79     if ( interrupt_critical_section_test_support_delay() )
    80       resets++;
    81 
    82     sc = rtems_rate_monotonic_period( Period, 1 );
    83     if ( sc == RTEMS_TIMEOUT )
    84       continue;
    85     directive_failed( sc, "rtems_monotonic_period");
    86   }
     105  interrupt_critical_section_test( test_body, NULL, test_release_from_isr );
    87106
    88107  if ( case_hit ) {
     
    102121#define CONFIGURE_MAXIMUM_TIMERS      1
    103122#define CONFIGURE_MAXIMUM_PERIODS     1
     123#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    104124#define CONFIGURE_MICROSECONDS_PER_TICK  1000
    105125#define CONFIGURE_INITIAL_EXTENSIONS RTEMS_TEST_INITIAL_EXTENSION
  • testsuites/sptests/spintrcritical09/init.c

    r80ad7090 r8028089  
    2121
    2222static rtems_id Semaphore;
    23 static bool case_hit;
     23static bool case_hit = false;
    2424
    2525static Thread_blocking_operation_States getState(void)
     
    6565}
    6666
     67static bool test_body( void *arg )
     68{
     69  (void) arg;
     70
     71  rtems_semaphore_obtain( Semaphore, RTEMS_DEFAULT_OPTIONS, 1 );
     72
     73  return case_hit;
     74}
     75
    6776static rtems_task Init(
    6877  rtems_task_argument ignored
     
    7079{
    7180  rtems_status_code     sc;
    72   int                   resets;
    7381
    7482  TEST_BEGIN();
     
    8593  directive_failed( sc, "rtems_semaphore_create of SM1" );
    8694
    87   interrupt_critical_section_test_support_initialize( test_release_from_isr );
    88 
    89   case_hit = false;
    90 
    91   for (resets=0 ; resets< 2 ;) {
    92     if ( interrupt_critical_section_test_support_delay() )
    93       resets++;
    94 
    95     (void) rtems_semaphore_obtain( Semaphore, RTEMS_DEFAULT_OPTIONS, 1 );
    96   }
     95  interrupt_critical_section_test( test_body, NULL, test_release_from_isr );
    9796
    9897  if ( case_hit ) {
     
    113112#define CONFIGURE_MAXIMUM_TIMERS      1
    114113#define CONFIGURE_MAXIMUM_SEMAPHORES  1
     114#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    115115#define CONFIGURE_INITIAL_EXTENSIONS RTEMS_TEST_INITIAL_EXTENSION
    116116
  • testsuites/sptests/spintrcritical10/init.c

    r80ad7090 r8028089  
    8787}
    8888
     89static bool test_body_any_satisfy_before_timeout(void *arg)
     90{
     91  test_context *ctx = arg;
     92  rtems_status_code sc;
     93  rtems_event_set out;
     94
     95  out = DEADBEEF;
     96  sc = rtems_event_receive(EVENTS, RTEMS_EVENT_ANY | RTEMS_WAIT, 1, &out);
     97  rtems_test_assert(sc == RTEMS_SUCCESSFUL);
     98  rtems_test_assert(out == GREEN);
     99
     100  out = DEADBEEF;
     101  sc = rtems_event_receive(EVENTS, RTEMS_EVENT_ANY | RTEMS_NO_WAIT, 0, &out);
     102  rtems_test_assert(sc == RTEMS_SUCCESSFUL);
     103  rtems_test_assert(out == RED);
     104
     105  return ctx->hit;
     106}
     107
    89108static void test_any_satisfy_before_timeout(test_context *ctx)
    90109{
    91110  rtems_status_code sc;
    92   int resets = 0;
    93111
    94112  puts(
     
    99117  ctx->hit = false;
    100118
    101   interrupt_critical_section_test_support_initialize(NULL);
    102 
    103119  sc = rtems_timer_fire_after(ctx->timer, 1, any_satisfy_before_timeout, ctx);
    104120  rtems_test_assert(sc == RTEMS_SUCCESSFUL);
    105121
    106   while (!ctx->hit && resets < 2) {
    107     rtems_event_set out;
    108 
    109     if (interrupt_critical_section_test_support_delay())
    110       resets++;
    111 
    112     out = DEADBEEF;
    113     sc = rtems_event_receive(EVENTS, RTEMS_EVENT_ANY | RTEMS_WAIT, 1, &out);
    114     rtems_test_assert(sc == RTEMS_SUCCESSFUL);
    115     rtems_test_assert(out == GREEN);
    116 
    117     out = DEADBEEF;
    118     sc = rtems_event_receive(EVENTS, RTEMS_EVENT_ANY | RTEMS_NO_WAIT, 0, &out);
    119     rtems_test_assert(sc == RTEMS_SUCCESSFUL);
    120     rtems_test_assert(out == RED);
    121   }
     122  interrupt_critical_section_test(
     123    test_body_any_satisfy_before_timeout,
     124    ctx,
     125    NULL
     126  );
    122127
    123128  sc = rtems_timer_cancel(ctx->timer);
     
    179184}
    180185
     186static bool test_body_all_satisfy_before_timeout(void *arg)
     187{
     188  test_context *ctx = arg;
     189  rtems_status_code sc;
     190  rtems_event_set out;
     191
     192  out = DEADBEEF;
     193  sc = rtems_event_receive(EVENTS, RTEMS_EVENT_ALL | RTEMS_WAIT, 1, &out);
     194  rtems_test_assert(sc == RTEMS_SUCCESSFUL);
     195  rtems_test_assert(out == EVENTS);
     196
     197  return ctx->hit;
     198}
     199
    181200static void test_all_satisfy_before_timeout(test_context *ctx)
    182201{
    183202  rtems_status_code sc;
    184   int resets = 0;
    185203
    186204  puts(
     
    191209  ctx->hit = false;
    192210
    193   interrupt_critical_section_test_support_initialize(NULL);
    194 
    195211  sc = rtems_timer_fire_after(ctx->timer, 1, all_satisfy_before_timeout, ctx);
    196212  rtems_test_assert(sc == RTEMS_SUCCESSFUL);
    197213
    198   while (!ctx->hit && resets < 2) {
    199     rtems_event_set out;
    200 
    201     if (interrupt_critical_section_test_support_delay())
    202       resets++;
    203 
    204     out = DEADBEEF;
    205     sc = rtems_event_receive(EVENTS, RTEMS_EVENT_ALL | RTEMS_WAIT, 1, &out);
    206     rtems_test_assert(sc == RTEMS_SUCCESSFUL);
    207     rtems_test_assert(out == EVENTS);
    208   }
     214  interrupt_critical_section_test(
     215    test_body_all_satisfy_before_timeout,
     216    ctx,
     217    NULL
     218  );
    209219
    210220  sc = rtems_timer_cancel(ctx->timer);
     
    258268}
    259269
     270static bool test_body_timeout_before_all_satisfy(void *arg)
     271{
     272  test_context *ctx = arg;
     273  rtems_event_set out;
     274  rtems_status_code sc;
     275
     276  out = DEADBEEF;
     277  sc = rtems_event_receive(EVENTS, RTEMS_EVENT_ALL | RTEMS_WAIT, 1, &out);
     278  rtems_test_assert(sc == RTEMS_TIMEOUT);
     279  rtems_test_assert(out == DEADBEEF);
     280
     281  out = DEADBEEF;
     282  sc = rtems_event_receive(EVENTS, RTEMS_EVENT_ALL | RTEMS_NO_WAIT, 0, &out);
     283  rtems_test_assert(sc == RTEMS_SUCCESSFUL);
     284  rtems_test_assert(out == EVENTS);
     285
     286  return ctx->hit;
     287}
     288
    260289static void test_timeout_before_all_satisfy(test_context *ctx)
    261290{
    262291  rtems_status_code sc;
    263   int resets = 0;
    264292
    265293  puts(
     
    270298  ctx->hit = false;
    271299
    272   interrupt_critical_section_test_support_initialize(NULL);
    273 
    274300  sc = rtems_timer_fire_after(ctx->timer, 1, timeout_before_satisfied, ctx);
    275301  rtems_test_assert(sc == RTEMS_SUCCESSFUL);
    276302
    277   while (!ctx->hit && resets < 2) {
    278     rtems_event_set out;
    279 
    280     if (interrupt_critical_section_test_support_delay())
    281       resets++;
    282 
    283     out = DEADBEEF;
    284     sc = rtems_event_receive(EVENTS, RTEMS_EVENT_ALL | RTEMS_WAIT, 1, &out);
    285     rtems_test_assert(sc == RTEMS_TIMEOUT);
    286     rtems_test_assert(out == DEADBEEF);
    287 
    288     out = DEADBEEF;
    289     sc = rtems_event_receive(EVENTS, RTEMS_EVENT_ALL | RTEMS_NO_WAIT, 0, &out);
    290     rtems_test_assert(sc == RTEMS_SUCCESSFUL);
    291     rtems_test_assert(out == EVENTS);
    292   }
     303  interrupt_critical_section_test(
     304    test_body_timeout_before_all_satisfy,
     305    ctx,
     306    NULL
     307  );
    293308
    294309  sc = rtems_timer_cancel(ctx->timer);
     
    327342#define CONFIGURE_MAXIMUM_TASKS       1
    328343#define CONFIGURE_MAXIMUM_TIMERS      1
     344#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    329345#define CONFIGURE_INITIAL_EXTENSIONS RTEMS_TEST_INITIAL_EXTENSION
    330346
  • testsuites/sptests/spintrcritical11/init.c

    r80ad7090 r8028089  
    4848}
    4949
     50static bool test_body( void *arg )
     51{
     52  rtems_event_set out;
     53
     54  (void) arg;
     55
     56  rtems_event_receive( EVENTS_TO_RECEIVE, RTEMS_EVENT_ANY, 1, &out );
     57
     58  return false;
     59}
     60
    5061rtems_task Init(
    5162  rtems_task_argument ignored
    5263)
    5364{
    54   rtems_event_set       out;
    55   int                   resets;
    56 
    5765  TEST_BEGIN();
    5866
     
    6371  Main_task = rtems_task_self();
    6472
    65   interrupt_critical_section_test_support_initialize( test_release_from_isr );
    66 
    67   for (resets=0 ; resets< 2 ;) {
    68     if ( interrupt_critical_section_test_support_delay() )
    69       resets++;
    70 
    71     (void) rtems_event_receive( EVENTS_TO_RECEIVE, RTEMS_EVENT_ANY, 1, &out );
    72   }
     73  interrupt_critical_section_test( test_body, NULL, test_release_from_isr );
    7374
    7475  TEST_END();
     
    8485#define CONFIGURE_MAXIMUM_TIMERS      1
    8586#define CONFIGURE_MAXIMUM_SEMAPHORES  1
     87#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    8688#define CONFIGURE_INITIAL_EXTENSIONS RTEMS_TEST_INITIAL_EXTENSION
    8789
  • testsuites/sptests/spintrcritical13/init.c

    r80ad7090 r8028089  
    3636rtems_timer_service_routine TimerMethod(rtems_id  timer, void *arg);
    3737
    38 rtems_id Main_task;
    3938rtems_id Timer;
    4039
     
    5453}
    5554
     55static bool test_body( void *arg )
     56{
     57  rtems_status_code sc;
     58
     59  (void) arg;
     60
     61  sc = TEST_DIRECTIVE( Timer, 10, TimerMethod, NULL );
     62  rtems_test_assert( sc == RTEMS_SUCCESSFUL );
     63
     64  return false;
     65}
     66
    5667rtems_task Init(
    5768  rtems_task_argument ignored
     
    5970{
    6071  rtems_status_code     sc;
    61   int                   resets;
    6272
    6373  TEST_BEGIN();
     
    8292  directive_failed( sc, "rtems_timer_create" );
    8393
    84   Main_task = rtems_task_self();
    85 
    86   interrupt_critical_section_test_support_initialize( test_release_from_isr );
    87 
    88   for (resets=0 ; resets<10 ;) {
    89     if ( interrupt_critical_section_test_support_delay() )
    90       resets++;
    91 
    92     sc = TEST_DIRECTIVE( Timer, 10, TimerMethod, NULL );
    93     directive_failed( sc, "rtems_timer_fire_after");
    94   }
     94  interrupt_critical_section_test( test_body, NULL, test_release_from_isr );
    9595
    9696  TEST_END();
     
    109109#endif
    110110#define CONFIGURE_MAXIMUM_TIMERS      2
     111#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    111112#define CONFIGURE_MICROSECONDS_PER_TICK  1000
    112113#define CONFIGURE_INITIAL_EXTENSIONS RTEMS_TEST_INITIAL_EXTENSION
  • testsuites/sptests/spintrcritical15/init.c

    r80ad7090 r8028089  
    2424#define BLOCKER_PRIORITY   1
    2525
    26 rtems_id Main_task;
    2726rtems_id Secondary_task_id;
    2827rtems_id Semaphore;
     
    4039}
    4140
     41static bool test_body( void *arg )
     42{
     43  rtems_status_code sc;
     44
     45  (void) arg;
     46
     47  sc = rtems_task_restart( Secondary_task_id, 1 );
     48  rtems_test_assert( sc == RTEMS_SUCCESSFUL );
     49
     50  sc = rtems_semaphore_obtain( Semaphore, RTEMS_DEFAULT_OPTIONS, 1 );
     51  rtems_test_assert( sc == RTEMS_TIMEOUT );
     52
     53  return false;
     54}
     55
    4256rtems_task Init(
    4357  rtems_task_argument ignored
     
    4559{
    4660  rtems_status_code     sc;
    47   int                   resets;
    4861
    4962  TEST_BEGIN();
     
    7891  directive_failed( sc, "rtems_task_start" );
    7992
    80   Main_task = rtems_task_self();
    81 
    82   interrupt_critical_section_test_support_initialize( NULL );
    83 
    84   for (resets=0 ; resets<10 ;) {
    85     if ( interrupt_critical_section_test_support_delay() )
    86       resets++;
    87 
    88     sc = rtems_task_restart( Secondary_task_id, 1 );
    89     directive_failed( sc, "rtems_task_restart" );
    90 
    91     sc = rtems_semaphore_obtain( Semaphore, RTEMS_DEFAULT_OPTIONS, 1 );
    92     fatal_directive_status( sc, RTEMS_TIMEOUT, "rtems_semaphore_obtain" );
    93   }
     93  interrupt_critical_section_test( test_body, NULL, NULL );
    9494
    9595  TEST_END();
     
    104104#define CONFIGURE_MAXIMUM_TASKS          2
    105105#define CONFIGURE_MAXIMUM_SEMAPHORES     1
     106#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    106107#define CONFIGURE_MICROSECONDS_PER_TICK  1000
    107108#define CONFIGURE_INIT_TASK_PRIORITY  INIT_PRIORITY
  • testsuites/sptests/spintrcritical16/init.c

    r80ad7090 r8028089  
    2525
    2626Thread_Control *Main_TCB;
    27 rtems_id        Main_task;
    2827rtems_id        Semaphore;
    29 volatile bool   case_hit;
     28volatile bool   case_hit = false;
    3029
    3130Thread_blocking_operation_States getState(void)
     
    6059}
    6160
     61static bool test_body( void *arg )
     62{
     63  rtems_status_code sc;
     64
     65  (void) arg;
     66
     67  sc = rtems_semaphore_obtain( Semaphore, RTEMS_DEFAULT_OPTIONS, 2 );
     68  rtems_test_assert( sc == RTEMS_SUCCESSFUL || sc == RTEMS_TIMEOUT );
     69
     70  return case_hit;
     71}
     72
    6273rtems_task Init(
    6374  rtems_task_argument ignored
     
    6576{
    6677  rtems_status_code     sc;
    67   int                   resets;
    6878
    6979  TEST_BEGIN();
     
    8393  directive_failed( sc, "rtems_semaphore_create of SM1" );
    8494
    85   Main_task = rtems_task_self();
    8695  Main_TCB  = _Thread_Get_executing();
    8796
    88   interrupt_critical_section_test_support_initialize( test_release_from_isr );
    89 
    90   case_hit = false;
    91 
    92   for (resets=0 ; !case_hit && resets<10 ;) {
    93     if ( interrupt_critical_section_test_support_delay() )
    94       resets++;
    95 
    96     sc = rtems_semaphore_obtain( Semaphore, RTEMS_DEFAULT_OPTIONS, 2 );
    97     if ( sc == RTEMS_SUCCESSFUL )
    98       break;
    99     fatal_directive_status( sc, RTEMS_TIMEOUT, "rtems_semaphore_obtain" );
    100   }
     97  interrupt_critical_section_test( test_body, NULL, test_release_from_isr );
    10198
    10299  if ( case_hit ) {
     
    118115#define CONFIGURE_MAXIMUM_TIMERS         1
    119116#define CONFIGURE_MAXIMUM_SEMAPHORES     1
     117#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    120118#define CONFIGURE_MICROSECONDS_PER_TICK  1000
    121119#define CONFIGURE_INITIAL_EXTENSIONS RTEMS_TEST_INITIAL_EXTENSION
  • testsuites/sptests/spintrcritical18/init.c

    r80ad7090 r8028089  
    9696}
    9797
     98static bool test_body( void *arg )
     99{
     100  test_context *ctx = arg;
     101
     102  wake_up( ctx->middle_priority_task );
     103
     104  return false;
     105}
     106
    98107static void Init( rtems_task_argument ignored )
    99108{
    100109  test_context *ctx = &global_ctx;
    101110  rtems_status_code sc;
    102   int resets = 0;
    103111
    104112  TEST_BEGIN();
     
    138146  ASSERT_SC(sc);
    139147
    140   interrupt_critical_section_test_support_initialize(
    141     active_high_priority_task
    142   );
    143 
    144   while ( resets < 3 ) {
    145     if ( interrupt_critical_section_test_support_delay() ) {
    146       ++resets;
    147     }
    148 
    149     wake_up( ctx->middle_priority_task );
    150   }
     148  interrupt_critical_section_test( test_body, ctx, active_high_priority_task );
    151149
    152150  TEST_END();
     
    162160#define CONFIGURE_MAXIMUM_TASKS 3
    163161#define CONFIGURE_MAXIMUM_TIMERS 1
     162#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    164163
    165164#define CONFIGURE_INIT_TASK_PRIORITY PRIORITY_LOW
  • testsuites/sptests/spintrcritical20/init.c

    r80ad7090 r8028089  
    6464}
    6565
     66static bool test_body(void *arg)
     67{
     68  test_context *ctx = arg;
     69  int busy;
     70
     71  _Thread_Disable_dispatch();
     72
     73  rtems_test_assert(
     74    ctx->semaphore_task_tcb->Wait.return_code
     75      == CORE_SEMAPHORE_STATUS_SUCCESSFUL
     76  );
     77
     78  /*
     79   * Spend some time to make it more likely that we hit the test condition
     80   * below.
     81   */
     82  for (busy = 0; busy < 1000; ++busy) {
     83    __asm__ volatile ("");
     84  }
     85
     86  if (ctx->semaphore_task_tcb->Wait.queue == NULL) {
     87    ctx->thread_queue_was_null = true;
     88  }
     89
     90  _Thread_queue_Process_timeout(ctx->semaphore_task_tcb);
     91
     92  switch (ctx->semaphore_task_tcb->Wait.return_code) {
     93    case CORE_SEMAPHORE_STATUS_SUCCESSFUL:
     94      ctx->status_was_successful = true;
     95      break;
     96    case CORE_SEMAPHORE_TIMEOUT:
     97      ctx->status_was_timeout = true;
     98      break;
     99    default:
     100      rtems_test_assert(0);
     101      break;
     102  }
     103
     104  _Thread_Enable_dispatch();
     105
     106  return false;
     107}
     108
    66109static void Init(rtems_task_argument ignored)
    67110{
    68111  test_context *ctx = &ctx_instance;
    69   int resets = 0;
    70112  rtems_status_code sc;
    71113
     
    100142  rtems_test_assert(sc == RTEMS_SUCCESSFUL);
    101143
    102   interrupt_critical_section_test_support_initialize(
    103     release_semaphore
    104   );
    105 
    106   while (resets < 3) {
    107     if (interrupt_critical_section_test_support_delay()) {
    108       ++resets;
    109     }
    110 
    111     _Thread_Disable_dispatch();
    112 
    113     rtems_test_assert(
    114       ctx->semaphore_task_tcb->Wait.return_code
    115         == CORE_SEMAPHORE_STATUS_SUCCESSFUL
    116     );
    117 
    118     if (ctx->semaphore_task_tcb->Wait.queue == NULL) {
    119       ctx->thread_queue_was_null = true;
    120     }
    121 
    122     _Thread_queue_Process_timeout(ctx->semaphore_task_tcb);
    123 
    124     switch (ctx->semaphore_task_tcb->Wait.return_code) {
    125       case CORE_SEMAPHORE_STATUS_SUCCESSFUL:
    126         ctx->status_was_successful = true;
    127         break;
    128       case CORE_SEMAPHORE_TIMEOUT:
    129         ctx->status_was_timeout = true;
    130         break;
    131       default:
    132         rtems_test_assert(0);
    133         break;
    134     }
    135 
    136     _Thread_Enable_dispatch();
    137   }
     144  interrupt_critical_section_test(test_body, ctx, release_semaphore);
    138145
    139146  rtems_test_assert(ctx->thread_queue_was_null);
     
    154161#define CONFIGURE_MAXIMUM_TASKS 2
    155162#define CONFIGURE_MAXIMUM_TIMERS 1
     163#define CONFIGURE_MAXIMUM_USER_EXTENSIONS 1
    156164
    157165#define CONFIGURE_INIT_TASK_PRIORITY PRIORITY_MASTER
  • testsuites/sptests/spintrcritical_support/intrcritical.c

    r80ad7090 r8028089  
    1515#include <intrcritical.h>
    1616
    17 static uint32_t Maximum;
    18 static uint32_t Maximum_current;
    19 static rtems_id Timer;
    20 static rtems_timer_service_routine (*TSR)( rtems_id, void * );
    21 
    22 static uint32_t interrupt_critical_remaining_units_of_tick( void )
    23 {
    24   uint32_t       units = 0;
     17#define INTERRUPT_CRITICAL_NAME rtems_build_name( 'I', 'C', 'R', 'I' )
     18
     19typedef struct {
     20  rtems_interval minimum;
     21  rtems_interval maximum;
     22  rtems_interval maximum_current;
     23  rtems_timer_service_routine_entry tsr;
     24  rtems_id timer;
     25  uint64_t t0;
     26  uint64_t t1;
     27} interrupt_critical_control;
     28
     29static interrupt_critical_control interrupt_critical;
     30
     31static rtems_interval estimate_busy_loop_maximum( void )
     32{
     33  rtems_interval units = 0;
    2534  rtems_interval initial = rtems_clock_get_ticks_since_boot();
    2635
     
    3241}
    3342
     43static rtems_interval wait_for_tick_change( void )
     44{
     45  rtems_interval initial = rtems_clock_get_ticks_since_boot();
     46  rtems_interval now;
     47
     48  do {
     49    now = rtems_clock_get_ticks_since_boot();
     50  } while ( now == initial );
     51
     52  return now;
     53}
     54
     55/*
     56 * It is important that we use actually use the same busy() function at the
     57 * various places, since otherwise the obtained maximum value might be wrong.
     58 * So the compiler must not inline this function.
     59 */
     60static __attribute__( ( noinline ) ) void busy( rtems_interval max )
     61{
     62  rtems_interval i;
     63
     64  for ( i = 0; i < max; ++i ) {
     65    __asm__ volatile ("");
     66  }
     67}
     68
    3469static bool interrupt_critical_busy_wait( void )
    3570{
    36   uint32_t max = Maximum_current;
    37   uint32_t unit = 0;
    38   rtems_interval initial = rtems_clock_get_ticks_since_boot();
    39 
    40   while ( unit < max && initial == rtems_clock_get_ticks_since_boot() ) {
    41     ++unit;
    42   }
    43 
    44   if ( max > 0 ) {
    45     Maximum_current = max - 1;
    46 
    47     return false;
     71  rtems_interval max = interrupt_critical.maximum_current;
     72  bool reset = max <= interrupt_critical.minimum;
     73
     74  if ( reset ) {
     75    interrupt_critical.maximum_current = interrupt_critical.maximum;
    4876  } else {
    49     Maximum_current = Maximum;
    50 
    51     return true;
    52   }
     77    interrupt_critical.maximum_current = max - 1;
     78  }
     79
     80  busy( max );
     81
     82  return reset;
    5383}
    5484
    5585void interrupt_critical_section_test_support_initialize(
    56   rtems_timer_service_routine (*tsr)( rtems_id, void * )
     86  rtems_timer_service_routine_entry tsr
    5787)
    5888{
    59   Timer = 0;
    60   TSR   = tsr;
    61   if ( tsr ) {
    62     rtems_status_code rc;
    63 
    64     puts( "Support - rtems_timer_create - creating timer 1" );
    65     rc = rtems_timer_create( rtems_build_name( 'T', 'M', '1', ' ' ), &Timer );
    66     directive_failed( rc, "rtems_timer_create" );
    67   }
    68 
    69   /* Wait for tick change */
    70   interrupt_critical_remaining_units_of_tick();
    71 
    72   /* Get units for a hole tick */
    73   Maximum = interrupt_critical_remaining_units_of_tick();
    74   Maximum_current = Maximum;
    75 
    76   #if 0
    77     printf( "%d 0x%08x units\n", Maximum, Maximum );
    78   #endif
     89  rtems_interval last;
     90  rtems_interval now;
     91  rtems_interval a;
     92  rtems_interval b;
     93  rtems_interval m;
     94
     95  interrupt_critical.tsr = tsr;
     96
     97  if ( tsr != NULL && interrupt_critical.timer == 0 ) {
     98    rtems_status_code sc = rtems_timer_create(
     99      INTERRUPT_CRITICAL_NAME,
     100      &interrupt_critical.timer
     101    );
     102    rtems_test_assert( sc == RTEMS_SUCCESSFUL );
     103  }
     104
     105  /* Choose a lower bound */
     106  a = 1;
     107
     108  /* Estimate an upper bound */
     109
     110  wait_for_tick_change();
     111  b = 2 * estimate_busy_loop_maximum();
     112
     113  while ( true ) {
     114    last = wait_for_tick_change();
     115    busy( b );
     116    now = rtems_clock_get_ticks_since_boot();
     117
     118    if ( now != last ) {
     119      break;
     120    }
     121
     122    b *= 2;
     123    last = now;
     124  }
     125
     126  /* Find a good value */
     127  do {
     128    m = ( a + b ) / 2;
     129
     130    last = wait_for_tick_change();
     131    busy( m );
     132    now = rtems_clock_get_ticks_since_boot();
     133
     134    if ( now != last ) {
     135      b = m;
     136    } else {
     137      a = m;
     138    }
     139  } while ( b - a > 1 );
     140
     141  interrupt_critical.minimum = 0;
     142  interrupt_critical.maximum = m;
     143  interrupt_critical.maximum_current = m;
     144}
     145
     146static void timer_fire_after(void)
     147{
     148  if ( interrupt_critical.tsr != NULL ) {
     149    rtems_status_code sc = rtems_timer_fire_after(
     150      interrupt_critical.timer,
     151      1,
     152      interrupt_critical.tsr,
     153      NULL
     154    );
     155    rtems_test_assert( sc == RTEMS_SUCCESSFUL );
     156  }
    79157}
    80158
    81159bool interrupt_critical_section_test_support_delay(void)
    82160{
    83   if (TSR) {
    84     rtems_status_code rc;
    85 
    86     rc = rtems_timer_fire_after( Timer, 1, TSR, NULL );
    87     directive_failed( rc, "timer_fire_after failed" );
    88   }
     161  timer_fire_after();
    89162
    90163  return interrupt_critical_busy_wait();
    91164}
     165
     166static bool is_idle( const Thread_Control *thread )
     167{
     168  return thread->Start.entry_point
     169    == (Thread_Entry) rtems_configuration_get_idle_task();
     170}
     171
     172static void thread_switch( Thread_Control *executing, Thread_Control *heir )
     173{
     174  (void) executing;
     175  (void) heir;
     176
     177  if ( interrupt_critical.t1 == 0 && is_idle( heir ) ) {
     178    interrupt_critical.t1 = rtems_clock_get_uptime_nanoseconds();
     179  }
     180}
     181
     182static const rtems_extensions_table extensions = {
     183  .thread_switch = thread_switch
     184};
     185
     186bool interrupt_critical_section_test(
     187  bool                              ( *test_body )( void * ),
     188  void                                *test_body_arg,
     189  rtems_timer_service_routine_entry    tsr
     190)
     191{
     192  bool done;
     193  rtems_status_code sc;
     194  rtems_id id;
     195  uint64_t delta;
     196  rtems_interval busy_delta;
     197  int retries = 3;
     198
     199  interrupt_critical_section_test_support_initialize( tsr );
     200
     201  sc = rtems_extension_create(
     202    INTERRUPT_CRITICAL_NAME,
     203    &extensions,
     204    &id
     205  );
     206  rtems_test_assert( sc == RTEMS_SUCCESSFUL );
     207
     208  wait_for_tick_change();
     209  timer_fire_after();
     210
     211  /* Get estimate for test body duration */
     212  interrupt_critical.t0 = rtems_clock_get_uptime_nanoseconds();
     213  done = ( *test_body )( test_body_arg );
     214  if ( interrupt_critical.t1 == 0 ) {
     215    interrupt_critical.t1 = rtems_clock_get_uptime_nanoseconds();
     216  }
     217
     218  /* Update minimum */
     219
     220  delta = interrupt_critical.t1 - interrupt_critical.t0;
     221  busy_delta = (rtems_interval)
     222    ( ( interrupt_critical.maximum * ( 2 * delta ) )
     223      / rtems_configuration_get_nanoseconds_per_tick() );
     224
     225  if ( busy_delta < interrupt_critical.maximum ) {
     226    interrupt_critical.minimum = interrupt_critical.maximum - busy_delta;
     227  }
     228
     229  sc = rtems_extension_delete( id );
     230  rtems_test_assert( sc == RTEMS_SUCCESSFUL );
     231
     232  while ( !done && retries >= 0 ) {
     233    wait_for_tick_change();
     234
     235    if ( interrupt_critical_section_test_support_delay() ) {
     236      --retries;
     237    }
     238
     239    done = ( *test_body )( test_body_arg );
     240  }
     241
     242  return done;
     243}
  • testsuites/sptests/spintrcritical_support/intrcritical.h

    r80ad7090 r8028089  
    1717 */
    1818void interrupt_critical_section_test_support_initialize(
    19   rtems_timer_service_routine (*tsr)( rtems_id, void * )
     19  rtems_timer_service_routine_entry tsr
    2020);
    2121
     
    3030bool interrupt_critical_section_test_support_delay(void);
    3131
     32/**
     33 * @brief Interrupt critical section test.
     34 *
     35 * This function first estimates the test body duration and then repeatedly
     36 * calls the test body with varying times to the next clock tick interrupt.
     37 *
     38 * @param[in] test_body The test body function.  In case the test body returns
     39 * true, then the test iteration stops.
     40 * @param[in] test_body_arg The argument for the test body function.
     41 * @param[in] tsr An optional timer service routine.
     42 *
     43 * @return The test body return status.
     44 */
     45bool interrupt_critical_section_test(
     46  bool                              ( *test_body )( void * ),
     47  void                                *test_body_arg,
     48  rtems_timer_service_routine_entry    tsr
     49);
     50
    3251#endif
    3352
Note: See TracChangeset for help on using the changeset viewer.