/* * The wrapper for the function we want to trace. Records * input arguments and the result to the capture trace. */ static uint32_t add_number_wrapper(uint32_t a, uint32_t b) { enter_add_number_record_t enter_rec; exit_add_number_record_t exit_rec; uint32_t res; void* rec; enter_rec.id = enter_add_number; enter_rec.a = a; enter_rec.b = b; rtems_capture_begin_add_record(_Thread_Get_executing(), RTEMS_CAPTURE_TIMESTAMP, sizeof(rtems_capture_record_t)+ sizeof(enter_add_number_record_t), &rec); rec = rtems_capture_append_to_record(rec, &enter_rec, sizeof(enter_rec)); rtems_capture_end_add_record(rec); res = add_number(a, b); exit_rec.id = exit_add_number; exit_rec.res = res; rtems_capture_begin_add_record(_Thread_Get_executing(), RTEMS_CAPTURE_TIMESTAMP, sizeof(rtems_capture_record_t)+ sizeof(exit_add_number_record_t), &rec); rec = rtems_capture_append_to_record(rec, &exit_rec, sizeof(exit_rec)); rtems_capture_end_add_record(rec); return res; }
rtems_task Middle_task( rtems_task_argument argument ) { Scheduler_priority_Context *scheduler_context = _Scheduler_priority_Get_context( _Scheduler_Get( _Thread_Get_executing() ) ); thread_dispatch_no_fp_time = benchmark_timer_read(); _Thread_Set_state( _Thread_Get_executing(), STATES_SUSPENDED ); Middle_tcb = _Thread_Get_executing(); set_thread_executing( (Thread_Control *) _Chain_First(&scheduler_context->Ready[LOW_PRIORITY]) ); /* do not force context switch */ set_thread_dispatch_necessary( false ); _Thread_Dispatch_disable(); benchmark_timer_initialize(); _Context_Switch( &Middle_tcb->Registers, &_Thread_Get_executing()->Registers ); benchmark_timer_initialize(); _Context_Switch(&Middle_tcb->Registers, &Low_tcb->Registers); }
rtems_task Floating_point_task_2( rtems_task_argument argument ) { Scheduler_priority_Context *scheduler_context = _Scheduler_priority_Get_context( _Scheduler_Get( _Thread_Get_executing() ) ); Thread_Control *executing; FP_DECLARE; context_switch_save_restore_idle_time = benchmark_timer_read(); executing = _Thread_Get_executing(); set_thread_executing( (Thread_Control *) _Chain_First(&scheduler_context->Ready[FP1_PRIORITY]) ); FP_LOAD( 1.0 ); benchmark_timer_initialize(); #if (CPU_HARDWARE_FP == 1) || (CPU_SOFTWARE_FP == 1) _Context_Save_fp( &executing->fp_context ); _Context_Restore_fp( &_Thread_Get_executing()->fp_context ); #endif _Context_Switch( &executing->Registers, &_Thread_Get_executing()->Registers ); /* switch to Floating_point_task_1 */ context_switch_save_restore_initted_time = benchmark_timer_read(); complete_test(); }
rtems_task Init( rtems_task_argument ignored ) { Objects_Name_or_id_lookup_errors namerc; Objects_Information TestClass; Objects_Id id; char name[64]; bool bc; puts( "\n\n*** POSIX OBJECT TEST 1 ***" ); /* very fake object class to test with */ _Objects_Initialize_information( &TestClass, 1, /* the_api */ 4, /* the_class */ 0, /* maximum */ 4, /* size */ true, /* is_string */ 10 /* maximum_name_length */ #if defined(RTEMS_MULTIPROCESSING) , false, /* supports_global */ NULL /* Objects_Thread_queue_Extract_callout extract */ #endif ); puts( "INIT - _Objects_Name_to_id_string - NULL name" ); namerc = _Objects_Name_to_id_string( &TestClass, NULL, &id ); if ( namerc != OBJECTS_INVALID_NAME ) { printf( "ERROR - Status = %d\n", namerc ); rtems_test_exit(0); } puts( "INIT - _Objects_Name_to_id_string - NULL ID" ); namerc = _Objects_Name_to_id_string( &TestClass, name, NULL ); if ( namerc != OBJECTS_INVALID_ADDRESS ) { printf( "ERROR - Status = %d\n", namerc ); rtems_test_exit(0); } puts( "INIT - _Objects_Name_to_id_string - name of non-existent object" ); strcpy( name, "NOT FOUND" ); namerc = _Objects_Name_to_id_string( &TestClass, name, &id ); if ( namerc != OBJECTS_INVALID_NAME ) { printf( "ERROR - Status = %d\n", namerc ); rtems_test_exit(0); } /* out of memory error ONLY when POSIX is enabled */ puts( "INIT - _Objects_Set_name fails - out of memory" ); rtems_workspace_greedy_allocate( NULL, 0 ); bc = _Objects_Set_name( &TestClass, &_Thread_Get_executing()->Object, name ); rtems_test_assert( bc == false ); puts( "*** END OF POSIX OBJECT TEST 1 ***" ); rtems_test_exit(0); }
rtems_status_code rtems_task_set_note( rtems_id id, uint32_t notepad, uint32_t note ) { Thread_Control *the_thread; Objects_Locations location; RTEMS_API_Control *api; Thread_Control *executing; if ( !rtems_configuration_get_notepads_enabled() ) return RTEMS_NOT_CONFIGURED; /* * NOTE: There is no check for < RTEMS_NOTEPAD_FIRST because that would * be checking an unsigned number for being negative. */ if ( notepad > RTEMS_NOTEPAD_LAST ) return RTEMS_INVALID_NUMBER; /* * Optimize the most likely case to avoid the Thread_Dispatch. */ executing = _Thread_Get_executing(); if ( _Objects_Are_ids_equal( id, OBJECTS_ID_OF_SELF ) || _Objects_Are_ids_equal( id, executing->Object.id ) ) { api = executing->API_Extensions[ THREAD_API_RTEMS ]; api->Notepads[ notepad ] = note; return RTEMS_SUCCESSFUL; } the_thread = _Thread_Get( id, &location ); switch ( location ) { case OBJECTS_LOCAL: api = the_thread->API_Extensions[ THREAD_API_RTEMS ]; api->Notepads[ notepad ] = note; _Objects_Put( &the_thread->Object ); return RTEMS_SUCCESSFUL; #if defined(RTEMS_MULTIPROCESSING) case OBJECTS_REMOTE: return _RTEMS_tasks_MP_Send_request_packet( RTEMS_TASKS_MP_SET_NOTE_REQUEST, id, 0, /* Not used */ notepad, note ); #endif case OBJECTS_ERROR: break; } return RTEMS_INVALID_ID; }
/** * POSIX 1003.1b 4.5.2 - Get Process Times */ clock_t _times( struct tms *ptms ) { uint32_t tick_interval; sbintime_t uptime; sbintime_t cpu_time_used; if ( !ptms ) rtems_set_errno_and_return_minus_one( EFAULT ); tick_interval = (uint32_t) (SBT_1US * rtems_configuration_get_microseconds_per_tick()); ptms = memset( ptms, 0, sizeof( *ptms ) ); _TOD_Get_zero_based_uptime( &uptime ); ptms->tms_stime = ((clock_t) uptime) / tick_interval; /* * RTEMS technically has no notion of system versus user time * since there is no separation of OS from application tasks. * But we can at least make a distinction between the number * of ticks since boot and the number of ticks executed by this * this thread. */ _Thread_Get_CPU_time_used( _Thread_Get_executing(), &cpu_time_used ); ptms->tms_utime = ((clock_t) cpu_time_used) / tick_interval; return ptms->tms_stime; }
void blow_stack(void) { volatile uint32_t *low, *high; unsigned char *area; Thread_Control *executing; b(); /* * Destroy the first and last 16 bytes of our stack... Hope it * does not cause problems :) */ executing = _Thread_Get_executing(); area = (unsigned char *)executing->Start.Initial_stack.area; /* Look in the stack checker implementation for this magic offset */ low = (volatile uint32_t *) \ (area + sizeof(Heap_Block) - HEAP_BLOCK_HEADER_SIZE); high = (volatile uint32_t *) (area + executing->Start.Initial_stack.size - 16); low[0] = 0x11111111; low[1] = 0x22222222; low[2] = 0x33333333; low[3] = 0x44444444; high[0] = 0x55555555; high[1] = 0x66666666; high[2] = 0x77777777; high[3] = 0x88888888; rtems_stack_checker_report_usage(); }
static void Init(rtems_task_argument ignored) { test_context *ctx = &ctx_instance; rtems_status_code sc; TEST_BEGIN(); ctx->main_task_control = _Thread_Get_executing(); sc = rtems_semaphore_create( rtems_build_name('S', 'E', 'M', 'A'), 1, RTEMS_SIMPLE_BINARY_SEMAPHORE, 0, &ctx->semaphore_id ); rtems_test_assert(sc == RTEMS_SUCCESSFUL); ctx->semaphore_control = get_semaphore_control(ctx->semaphore_id); interrupt_critical_section_test(test_body, ctx, release_semaphore); rtems_test_assert(ctx->done); TEST_END(); rtems_test_exit(0); }
/* * CallerName -- print the calling tasks name or id as configured */ const char *CallerName(void) { static char buffer[32]; Thread_Control *executing = _Thread_Get_executing(); #if defined(TEST_PRINT_TASK_ID) sprintf( buffer, "0x%08x -- %d", rtems_task_self(), _Thread_Get_priority( executing ) ); #else volatile union { uint32_t u; unsigned char c[4]; } TempName; #if defined(TEST_ON_RTEMS_45) TempName.u = *(uint32_t *)executing->Object.name; #else TempName.u = executing->Object.name.name_u32; #endif sprintf( buffer, "%c%c%c%c -- %" PRIdPriority_Control, TempName.c[0], TempName.c[1], TempName.c[2], TempName.c[3], _Thread_Get_priority( executing ) ); #endif return buffer; }
static rtems_task Init( rtems_task_argument ignored ) { rtems_status_code sc; TEST_BEGIN(); thread = _Thread_Get_executing(); puts( "Init - Test may not be able to detect case is hit reliably" ); puts( "Init - Trying to generate timeout from ISR while blocking" ); sc = rtems_semaphore_create( rtems_build_name( 'S', 'M', '1', ' ' ), 0, RTEMS_DEFAULT_ATTRIBUTES, RTEMS_NO_PRIORITY, &Semaphore ); directive_failed( sc, "rtems_semaphore_create of SM1" ); interrupt_critical_section_test( test_body, NULL, test_release_from_isr ); if ( case_hit ) { puts( "Init - It appears the case has been hit" ); TEST_END(); } else puts( "Init - Case not hit - ran too long" ); rtems_test_exit(0); }
bool _API_Mutex_Is_owner( const API_Mutex_Control *the_mutex ) { return _CORE_mutex_Is_owner( &the_mutex->Mutex.Mutex, _Thread_Get_executing() ); }
rtems_status_code rtems_task_ident( rtems_name name, uint32_t node, rtems_id *id ) { Objects_Name_or_id_lookup_errors status; if ( !id ) return RTEMS_INVALID_ADDRESS; if ( name == OBJECTS_ID_OF_SELF ) { *id = _Thread_Get_executing()->Object.id; return RTEMS_SUCCESSFUL; } status = _Objects_Name_to_id_u32( &_RTEMS_tasks_Information.Objects, name, node, id ); return _Status_Object_name_errors_to_status[ status ]; }
static void _Heap_Protection_delay_block_free( Heap_Control *heap, Heap_Block *block ) { uintptr_t *const pattern_begin = (uintptr_t *) _Heap_Alloc_area_of_block( block ); uintptr_t *const pattern_end = (uintptr_t *) ((uintptr_t) block + _Heap_Block_size( block ) + HEAP_ALLOC_BONUS); uintptr_t const delayed_free_block_count = heap->Protection.delayed_free_block_count; uintptr_t *current = NULL; block->Protection_begin.next_delayed_free_block = block; block->Protection_begin.task = _Thread_Get_executing(); if ( delayed_free_block_count > 0 ) { Heap_Block *const last = heap->Protection.last_delayed_free_block; last->Protection_begin.next_delayed_free_block = block; } else { heap->Protection.first_delayed_free_block = block; } heap->Protection.last_delayed_free_block = block; heap->Protection.delayed_free_block_count = delayed_free_block_count + 1; for ( current = pattern_begin; current != pattern_end; ++current ) { *current = HEAP_FREE_PATTERN; } }
static rtems_task Init( rtems_task_argument ignored ) { rtems_status_code status; TEST_BEGIN(); thread = _Thread_Get_executing(); puts( "Init - Trying to generate semaphore release from ISR while blocking" ); puts( "Init - Variation is: " TEST_STRING ); status = rtems_semaphore_create( rtems_build_name( 'S', 'M', '1', ' ' ), 0, SEMAPHORE_ATTRIBUTES, RTEMS_NO_PRIORITY, &Semaphore ); directive_failed( status, "rtems_semaphore_create of SM1" ); interrupt_critical_section_test( test_body, NULL, test_release_from_isr ); if ( case_hit ) { puts( "Init - Case hit" ); TEST_END(); } else puts( "Init - Case not hit - ran too long" ); rtems_test_exit(0); }
static bool life_protected(void) { Thread_Control *executing; executing = _Thread_Get_executing(); return executing == NULL || (executing->Life.state & THREAD_LIFE_PROTECTED) != 0; }
static void _POSIX_signals_Post_switch_hook( Thread_Control *the_thread ) { POSIX_API_Control *api; int signo; ISR_Level level; int hold_errno; Thread_Control *executing; executing = _Thread_Get_executing(); api = the_thread->API_Extensions[ THREAD_API_POSIX ]; /* * We need to ensure that if the signal handler executes a call * which overwrites the unblocking status, we restore it. */ hold_errno = executing->Wait.return_code; /* * api may be NULL in case of a thread close in progress */ if ( !api ) return; /* * If we invoke any user code, there is the possibility that * a new signal has been posted that we should process so we * restart the loop if a signal handler was invoked. * * The first thing done is to check there are any signals to be * processed at all. No point in doing this loop otherwise. */ while (1) { _ISR_Disable( level ); if ( !(~api->signals_blocked & (api->signals_pending | _POSIX_signals_Pending)) ) { _ISR_Enable( level ); break; } _ISR_Enable( level ); for ( signo = SIGRTMIN ; signo <= SIGRTMAX ; signo++ ) { _POSIX_signals_Check_signal( api, signo, false ); _POSIX_signals_Check_signal( api, signo, true ); } /* Unfortunately - nothing like __SIGFIRSTNOTRT in newlib signal .h */ for ( signo = SIGHUP ; signo <= __SIGLASTNOTRT ; signo++ ) { _POSIX_signals_Check_signal( api, signo, false ); _POSIX_signals_Check_signal( api, signo, true ); } } executing->Wait.return_code = hold_errno; }
void *__tls_get_addr(const TLS_Index *ti) { const Thread_Control *executing = _Thread_Get_executing(); void *tls_block = (char *) executing->Start.tls_area + _TLS_Get_thread_control_block_area_size( (uintptr_t) _TLS_Alignment ); assert(ti->module == 1); return (char *) tls_block + ti->offset; }
rtems_task Low_task( rtems_task_argument argument ) { Scheduler_priority_Context *scheduler_context = _Scheduler_priority_Get_context( _Scheduler_Get( _Thread_Get_executing() ) ); Thread_Control *executing; context_switch_no_fp_time = benchmark_timer_read(); executing = _Thread_Get_executing(); Low_tcb = executing; benchmark_timer_initialize(); _Context_Switch( &executing->Registers, &executing->Registers ); context_switch_self_time = benchmark_timer_read(); _Context_Switch(&executing->Registers, &Middle_tcb->Registers); context_switch_another_task_time = benchmark_timer_read(); set_thread_executing( (Thread_Control *) _Chain_First(&scheduler_context->Ready[FP1_PRIORITY]) ); /* do not force context switch */ set_thread_dispatch_necessary( false ); thread_disable_dispatch(); benchmark_timer_initialize(); #if (CPU_HARDWARE_FP == 1) || (CPU_SOFTWARE_FP == 1) _Context_Restore_fp( &_Thread_Get_executing()->fp_context ); #endif _Context_Switch( &executing->Registers, &_Thread_Get_executing()->Registers ); }
static void _RTEMS_Global_construction( rtems_task_argument arg ) { Thread_Control *executing = _Thread_Get_executing(); Thread_Entry_information entry = executing->Start.Entry; entry.Kinds.Numeric.entry = Configuration_RTEMS_API.User_initialization_tasks_table[ 0 ].entry_point; (void) arg; _Thread_Global_construction( executing, &entry ); }
rtems_status_code _Partition_MP_Get_buffer( rtems_id id, void **buffer ) { _Thread_Get_executing()->Wait.return_argument = buffer; return _Partition_MP_Send_request_packet( id, buffer, PARTITION_MP_GET_BUFFER_REQUEST ); }
Thread _MPCI_Receive_server( uint32_t ignored ) { MP_packet_Prefix *the_packet; MPCI_Packet_processor the_function; Thread_Control *executing; executing = _Thread_Get_executing(); for ( ; ; ) { executing->receive_packet = NULL; _Thread_Disable_dispatch(); _CORE_semaphore_Seize( &_MPCI_Semaphore, executing, 0, true, WATCHDOG_NO_TIMEOUT ); _Thread_Enable_dispatch(); for ( ; ; ) { the_packet = _MPCI_Receive_packet(); if ( !the_packet ) break; executing->receive_packet = the_packet; if ( !_Mp_packet_Is_valid_packet_class ( the_packet->the_class ) ) break; the_function = _MPCI_Packet_processors[ the_packet->the_class ]; if ( !the_function ) _Terminate( INTERNAL_ERROR_CORE, true, INTERNAL_ERROR_BAD_PACKET ); (*the_function)( the_packet ); } } return 0; /* unreached - only to remove warnings */ }
/* Writes an entry in the capture trace for every clock tick */ static void clock_tick_wrapper(void *arg) { void* rec; clock_tick_record_t clock_tick_record = {.id = clock_tick}; Thread_Control* tcb = _Thread_Get_executing(); rtems_capture_begin_add_record(tcb, RTEMS_CAPTURE_TIMESTAMP, sizeof(rtems_capture_record_t) + sizeof(clock_tick_record_t), &rec); rec = rtems_capture_append_to_record(rec, &clock_tick_record, sizeof(clock_tick_record)); rtems_capture_end_add_record(rec); org_clock_handler(arg); }
Objects_Name_or_id_lookup_errors _Objects_Id_to_name ( Objects_Id id, Objects_Name *name ) { uint32_t the_api; uint32_t the_class; Objects_Id tmpId; Objects_Information *information; Objects_Control *the_object = (Objects_Control *) 0; Objects_Locations ignored_location; ISR_lock_Context lock_context; /* * Caller is trusted for name != NULL. */ tmpId = (id == OBJECTS_ID_OF_SELF) ? _Thread_Get_executing()->Object.id : id; the_api = _Objects_Get_API( tmpId ); if ( !_Objects_Is_api_valid( the_api ) ) return OBJECTS_INVALID_ID; if ( !_Objects_Information_table[ the_api ] ) return OBJECTS_INVALID_ID; the_class = _Objects_Get_class( tmpId ); information = _Objects_Information_table[ the_api ][ the_class ]; if ( !information ) return OBJECTS_INVALID_ID; #if defined(RTEMS_SCORE_OBJECT_ENABLE_STRING_NAMES) if ( information->is_string ) return OBJECTS_INVALID_ID; #endif the_object = _Objects_Get_isr_disable( information, tmpId, &ignored_location, &lock_context ); if ( !the_object ) return OBJECTS_INVALID_ID; *name = the_object->name; _ISR_lock_ISR_enable( &lock_context ); return OBJECTS_NAME_OR_ID_LOOKUP_SUCCESSFUL; }
rtems_task Init( rtems_task_argument ignored ) { rtems_status_code sc; int resets; puts( "\n\n*** TEST INTERRUPT CRITICAL SECTION " TEST_NAME " ***\n" "Init - Trying to generate timeout of a thread that had its blocking\n" "Init - request satisfied while blocking but before time timeout" ); puts( "Init - rtems_semaphore_create - OK" ); sc = rtems_semaphore_create( rtems_build_name( 'S', 'M', '1', ' ' ), 0, RTEMS_DEFAULT_ATTRIBUTES, RTEMS_NO_PRIORITY, &Semaphore ); directive_failed( sc, "rtems_semaphore_create of SM1" ); Main_task = rtems_task_self(); Main_TCB = _Thread_Get_executing(); interrupt_critical_section_test_support_initialize( test_release_from_isr ); case_hit = false; for (resets=0 ; !case_hit && resets<10 ;) { if ( interrupt_critical_section_test_support_delay() ) resets++; sc = rtems_semaphore_obtain( Semaphore, RTEMS_DEFAULT_OPTIONS, 2 ); if ( sc == RTEMS_SUCCESSFUL ) break; fatal_directive_status( sc, RTEMS_TIMEOUT, "rtems_semaphore_obtain" ); } if ( case_hit ) { puts( "Init - Case hit" ); puts( "*** END OF TEST INTERRUPT CRITICAL SECTION " TEST_NAME " ***" ); } else puts( "Init - Case not hit - ran too long" ); rtems_test_exit(0); }
int sigpending( sigset_t *set ) { POSIX_API_Control *api; if ( !set ) rtems_set_errno_and_return_minus_one( EINVAL ); api = _Thread_Get_executing()->API_Extensions[ THREAD_API_POSIX ]; *set = api->signals_pending | _POSIX_signals_Pending; return 0; }
static void semaphore_task(rtems_task_argument arg) { test_context *ctx = (test_context *) arg; ctx->semaphore_task_tcb = _Thread_Get_executing(); while (true) { rtems_status_code sc = rtems_semaphore_obtain( ctx->semaphore_id, RTEMS_WAIT, RTEMS_NO_TIMEOUT ); rtems_test_assert(sc == RTEMS_SUCCESSFUL || sc == RTEMS_TIMEOUT); } }
rtems_task Task_2( rtems_task_argument argument ) { Thread_Control *executing = _Thread_Get_executing(); Scheduler_priority_Context *scheduler_context = _Scheduler_priority_Get_context( _Scheduler_Get( executing ) ); ISR_lock_Context lock_context; #if (MUST_WAIT_FOR_INTERRUPT == 1) while ( Interrupt_occurred == 0 ); #endif end_time = benchmark_timer_read(); put_time( "rtems interrupt: entry overhead returns to preempting task", Interrupt_enter_time, 1, 0, timer_overhead ); put_time( "rtems interrupt: exit overhead returns to preempting task", end_time, 1, 0, 0 ); fflush( stdout ); /* * Switch back to the other task to exit the test. */ _Scheduler_Acquire( executing, &lock_context ); _Thread_Executing = (Thread_Control *) _Chain_First(&scheduler_context->Ready[LOW_PRIORITY]); _Thread_Dispatch_necessary = 1; _Scheduler_Release( executing, &lock_context ); _Thread_Dispatch(); }
rtems_task High_task( rtems_task_argument argument ) { rtems_interrupt_level level; _Thread_Dispatch_disable(); benchmark_timer_initialize(); rtems_interrupt_local_disable( level ); isr_disable_time = benchmark_timer_read(); benchmark_timer_initialize(); #if defined(RTEMS_SMP) rtems_interrupt_local_enable( level ); rtems_interrupt_local_disable( level ); #else rtems_interrupt_flash( level ); #endif isr_flash_time = benchmark_timer_read(); benchmark_timer_initialize(); rtems_interrupt_local_enable( level ); isr_enable_time = benchmark_timer_read(); _Thread_Dispatch_enable( _Per_CPU_Get() ); benchmark_timer_initialize(); _Thread_Dispatch_disable(); thread_disable_dispatch_time = benchmark_timer_read(); benchmark_timer_initialize(); _Thread_Dispatch_enable( _Per_CPU_Get() ); thread_enable_dispatch_time = benchmark_timer_read(); benchmark_timer_initialize(); _Thread_Set_state( _Thread_Get_executing(), STATES_SUSPENDED ); thread_set_state_time = benchmark_timer_read(); set_thread_dispatch_necessary( true ); benchmark_timer_initialize(); _Thread_Dispatch(); /* dispatches Middle_task */ }
int pthread_sigmask( int how, const sigset_t *set, sigset_t *oset ) { POSIX_API_Control *api; if ( !set && !oset ) rtems_set_errno_and_return_minus_one( EINVAL ); api = _Thread_Get_executing()->API_Extensions[ THREAD_API_POSIX ]; if ( oset ) *oset = api->signals_blocked; if ( !set ) return 0; switch ( how ) { case SIG_BLOCK: api->signals_blocked |= *set; break; case SIG_UNBLOCK: api->signals_blocked &= ~*set; break; case SIG_SETMASK: api->signals_blocked = *set; break; default: rtems_set_errno_and_return_minus_one( EINVAL ); } /* XXX are there critical section problems here? */ /* XXX evaluate the new set */ if ( ~api->signals_blocked & (api->signals_pending | _POSIX_signals_Pending) ) { _Thread_Dispatch(); } return 0; }
rtems_status_code rtems_rate_monotonic_create( rtems_name name, rtems_id *id ) { Rate_monotonic_Control *the_period; if ( !rtems_is_name_valid( name ) ) return RTEMS_INVALID_NAME; if ( !id ) return RTEMS_INVALID_ADDRESS; the_period = _Rate_monotonic_Allocate(); if ( !the_period ) { _Objects_Allocator_unlock(); return RTEMS_TOO_MANY; } _ISR_lock_Initialize( &the_period->Lock, "Rate Monotonic Period" ); _Priority_Node_initialize( &the_period->Priority, 0 ); _Priority_Node_set_inactive( &the_period->Priority ); the_period->owner = _Thread_Get_executing(); the_period->state = RATE_MONOTONIC_INACTIVE; _Watchdog_Preinitialize( &the_period->Timer, _Per_CPU_Get_by_index( 0 ) ); _Watchdog_Initialize( &the_period->Timer, _Rate_monotonic_Timeout ); _Rate_monotonic_Reset_statistics( the_period ); _Objects_Open( &_Rate_monotonic_Information, &the_period->Object, (Objects_Name) name ); *id = the_period->Object.id; _Objects_Allocator_unlock(); return RTEMS_SUCCESSFUL; }