/*--------------------------------------------------------------------------------------- Name: OS_initfs Purpose: Inititalizes a file system on the target Returns: OS_FS_ERR_INVALID_POINTER if devname is NULL OS_FS_DRIVE_NOT_CREATED if the OS calls to create the the drive failed OS_FS_SUCCESS on creating the disk OS_FS_ERR_PATH_TOO_LONG if the name is too long OS_FS_ERR_DEVICE_NOT_FREE if the volume table is full ---------------------------------------------------------------------------------------*/ int32 OS_initfs (char *address,char *devname, char *volname, uint32 blocksize, uint32 numblocks) { int i; int32 ReturnCode; rtems_status_code rtems_sc; if ( devname == NULL || volname == NULL ) { return OS_FS_ERR_INVALID_POINTER; } if(strlen(devname) > 32 || strlen(volname) > 32) { return OS_FS_ERR_PATH_TOO_LONG; } /* ** Lock */ rtems_sc = rtems_semaphore_obtain (OS_VolumeTableSem, RTEMS_WAIT, RTEMS_NO_TIMEOUT); /* find an open entry in the Volume Table */ for (i = 0; i < NUM_TABLE_ENTRIES; i++) { if (OS_VolumeTable[i].FreeFlag == TRUE && OS_VolumeTable[i].IsMounted == FALSE && strcmp(OS_VolumeTable[i].DeviceName, devname) == 0) break; } if (i >= NUM_TABLE_ENTRIES) { rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return OS_FS_ERR_DEVICE_NOT_FREE; } /* ** Initialize the RAM disk. */ if (OS_VolumeTable[i].VolumeType == RAM_DISK) { printf("OSAL: Re-Initializing a RAM disk at: 0x%08X\n",(unsigned int)address ); /* ** Create the RAM disk device. Do not erase the disk! */ ReturnCode = rtems_setup_ramdisk (OS_VolumeTable[i].PhysDevName, (uint32 *) address, blocksize, numblocks); if ( ReturnCode != OS_FS_SUCCESS ) { ReturnCode = OS_FS_ERR_DRIVE_NOT_CREATED; } else { /* ** Success */ OS_VolumeTable[i].FreeFlag = FALSE; strcpy(OS_VolumeTable[i].VolumeName, volname); OS_VolumeTable[i].BlockSize = blocksize; ReturnCode = OS_FS_SUCCESS; } } else if (OS_VolumeTable[i].VolumeType == FS_BASED) { /* now enter the info in the table */ OS_VolumeTable[i].FreeFlag = FALSE; strcpy(OS_VolumeTable[i].VolumeName, volname); OS_VolumeTable[i].BlockSize = blocksize; /* note we don't know the mount point yet */ ReturnCode = OS_FS_SUCCESS; } else { /* ** VolumeType is something else that is not supported right now */ ReturnCode = OS_FS_ERROR; } /* ** Unlock */ rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return(ReturnCode); }/* end OS_initfs */
rtems_task Test_task2( rtems_task_argument argument ) { rtems_status_code status; puts( "Getting SMID of semaphore" ); do { status = rtems_semaphore_ident( Semaphore_name[ 1 ], RTEMS_SEARCH_ALL_NODES, &Semaphore_id[ 1 ] ); } while ( !rtems_is_status_successful( status ) ); directive_failed( status, "rtems_semaphore_ident" ); if ( Multiprocessing_configuration.node == 1 ) { status = rtems_task_wake_after( TICKS_PER_SECOND ); directive_failed( status, "rtems_task_wake_after" ); puts( "Releasing semaphore ..." ); status = rtems_semaphore_release( Semaphore_id[ 1 ] ); directive_failed( status, "rtems_semaphore_release" ); status = rtems_task_wake_after( TICKS_PER_SECOND / 2 ); directive_failed( status, "rtems_task_wake_after" ); puts( "Getting semaphore ..." ); status = rtems_semaphore_obtain( Semaphore_id[ 1 ], RTEMS_DEFAULT_OPTIONS, RTEMS_NO_TIMEOUT ); directive_failed( status, "rtems_semaphore_obtain" ); puts( "Getting semaphore ..." ); status = rtems_semaphore_obtain( Semaphore_id[ 1 ], RTEMS_DEFAULT_OPTIONS, RTEMS_NO_TIMEOUT ); puts( "How did I get back from here????" ); directive_failed( status, "rtems_semaphore_obtain" ); } /* status = rtems_task_wake_after( TICKS_PER_SECOND / 2 ); directive_failed( status, "rtems_task_wake_after" ); */ puts( "Getting semaphore ..." ); status = rtems_semaphore_obtain( Semaphore_id[ 1 ], RTEMS_DEFAULT_OPTIONS, RTEMS_NO_TIMEOUT ); directive_failed( status, "rtems_semaphore_obtain" ); puts( "Releasing semaphore ..." ); status = rtems_semaphore_release( Semaphore_id[ 1 ] ); directive_failed( status, "rtems_semaphore_release" ); status = rtems_task_wake_after( TICKS_PER_SECOND ); directive_failed( status, "rtems_task_wake_after" ); puts( "Getting semaphore ..." ); status = rtems_semaphore_obtain( Semaphore_id[ 1 ], RTEMS_DEFAULT_OPTIONS, 2 * TICKS_PER_SECOND ); fatal_directive_status( status, RTEMS_TIMEOUT, "rtems_semaphore_obtain" ); puts( "rtems_semaphore_obtain correctly returned RTEMS_TIMEOUT" ); puts( "*** END OF TEST 13 ***" ); rtems_test_exit( 0 ); }
/****************************************************************************** ** Function: OS_TimerCreate ** ** Purpose: Create a new OSAL Timer ** ** Arguments: ** ** Return: */ int32 OS_TimerCreate(uint32 *timer_id, const char *timer_name, uint32 *clock_accuracy, OS_TimerCallback_t callback_ptr) { rtems_status_code status; rtems_name RtemsTimerName; uint32 possible_tid; int32 i; if ( timer_id == NULL || timer_name == NULL) { return OS_INVALID_POINTER; } /* ** we don't want to allow names too long ** if truncated, two names might be the same */ if (strlen(timer_name) > OS_MAX_API_NAME) { return OS_ERR_NAME_TOO_LONG; } /* ** Check Parameters */ status = rtems_semaphore_obtain (OS_timer_table_sem, RTEMS_WAIT, RTEMS_NO_TIMEOUT); for(possible_tid = 0; possible_tid < OS_MAX_TIMERS; possible_tid++) { if (OS_timer_table[possible_tid].free == TRUE) break; } if( possible_tid >= OS_MAX_TIMERS || OS_timer_table[possible_tid].free != TRUE) { status = rtems_semaphore_release (OS_timer_table_sem); return OS_ERR_NO_FREE_IDS; } /* ** Check to see if the name is already taken */ for (i = 0; i < OS_MAX_TIMERS; i++) { if ((OS_timer_table[i].free == FALSE) && strcmp ((char*) timer_name, OS_timer_table[i].name) == 0) { status = rtems_semaphore_release (OS_timer_table_sem); return OS_ERR_NAME_TAKEN; } } /* ** Verify callback parameter */ if (callback_ptr == NULL ) { status = rtems_semaphore_release (OS_timer_table_sem); return OS_TIMER_ERR_INVALID_ARGS; } /* ** Set the possible timer Id to not free so that ** no other task can try to use it */ OS_timer_table[possible_tid].free = FALSE; status = rtems_semaphore_release (OS_timer_table_sem); OS_timer_table[possible_tid].creator = OS_FindCreator(); OS_timer_table[possible_tid].start_time = 0; OS_timer_table[possible_tid].interval_time = 0; OS_timer_table[possible_tid].callback_ptr = callback_ptr; /* ** Create an interval timer */ RtemsTimerName = rtems_build_name('T','M','E','R'); status = rtems_timer_create(RtemsTimerName, &(OS_timer_table[possible_tid].host_timerid)); if ( status != RTEMS_SUCCESSFUL ) { OS_timer_table[possible_tid].free = TRUE; return(OS_TIMER_ERR_UNAVAILABLE); } /* ** Return the clock accuracy to the user */ *clock_accuracy = os_clock_accuracy; /* ** Return timer ID */ *timer_id = possible_tid; return OS_SUCCESS; }
rtems_task Task_1( rtems_task_argument argument ) { rtems_id smid; rtems_status_code status; status = rtems_semaphore_ident( Semaphore_name[ 1 ], RTEMS_SEARCH_ALL_NODES, &smid ); printf( "TA1 - rtems_semaphore_ident - smid => %08" PRIxrtems_id "\n", smid ); directive_failed( status, "rtems_semaphore_ident of SM1" ); puts( "TA1 - rtems_semaphore_obtain - wait forever on SM2" ); status = rtems_semaphore_obtain( Semaphore_id[ 2 ], RTEMS_DEFAULT_OPTIONS, RTEMS_NO_TIMEOUT ); directive_failed( status, "rtems_semaphore_obtain of SM2" ); puts( "TA1 - got SM2" ); puts( "TA1 - rtems_semaphore_obtain - wait forever on SM3" ); status = rtems_semaphore_obtain( Semaphore_id[ 3 ], RTEMS_DEFAULT_OPTIONS, RTEMS_NO_TIMEOUT ); directive_failed( status, "rtems_semaphore_obtain of SM3" ); puts( "TA1 - got SM3" ); puts( "TA1 - rtems_semaphore_obtain - get SM1 - RTEMS_NO_WAIT" ); status = rtems_semaphore_obtain( Semaphore_id[ 1 ], RTEMS_NO_WAIT, RTEMS_NO_TIMEOUT ); directive_failed( status, "rtems_semaphore_obtain of SM1" ); puts( "TA1 - got SM1" ); puts( "TA1 - rtems_task_wake_after - sleep 5 seconds" ); status = rtems_task_wake_after( 5 * rtems_clock_get_ticks_per_second() ); directive_failed( status, "rtems_task_wake_after" ); rtems_test_pause(); puts( "TA1 - rtems_semaphore_release - release SM1" ); status = rtems_semaphore_release( Semaphore_id[ 1 ] ); directive_failed( status, "rtems_semaphore_release of SM1" ); puts( "TA1 - rtems_semaphore_obtain - waiting for SM1 with 10 second timeout" ); status = rtems_semaphore_obtain( Semaphore_id[ 1 ], RTEMS_DEFAULT_OPTIONS, 10 * rtems_clock_get_ticks_per_second() ); directive_failed( status, "rtems_semaphore_obtain of SM1" ); puts( "TA1 - got SM1" ); puts( "TA1 - rtems_semaphore_release - release SM2" ); status = rtems_semaphore_release( Semaphore_id[ 2 ] ); directive_failed( status, "rtems_semaphore_release of SM2" ); puts( "TA1 - rtems_task_wake_after - sleep 5 seconds" ); status = rtems_task_wake_after( 5 * rtems_clock_get_ticks_per_second() ); directive_failed( status, "rtems_task_wake_after" ); rtems_test_pause(); puts( "TA1 - rtems_task_delete - delete TA3" ); status = rtems_task_delete( Task_id[ 3 ] ); directive_failed( status, "rtems_task_delete of TA3" ); status = rtems_task_create( Task_name[ 4 ], 4, RTEMS_MINIMUM_STACK_SIZE, RTEMS_DEFAULT_MODES, RTEMS_DEFAULT_ATTRIBUTES, &Task_id[ 4 ] ); directive_failed( status, "rtems_task_create of TA4" ); status = rtems_task_create( Task_name[ 5 ], 4, RTEMS_MINIMUM_STACK_SIZE, RTEMS_DEFAULT_MODES, RTEMS_DEFAULT_ATTRIBUTES, &Task_id[ 5 ] ); directive_failed( status, "rtems_task_create of TA5" ); status = rtems_task_start( Task_id[ 4 ], Task_4, 0 ); directive_failed( status, "rtems_task_start of TA4" ); status = rtems_task_start( Task_id[ 5 ], Task5, 0 ); directive_failed( status, "rtems_task_start of TA5" ); puts( "TA1 - rtems_task_wake_after - sleep 5 seconds" ); status = rtems_task_wake_after( 5 * rtems_clock_get_ticks_per_second() ); directive_failed( status, "rtems_task_wake_after" ); puts( "TA1 - rtems_task_delete - delete TA4" ); status = rtems_task_delete( Task_id[ 4 ] ); directive_failed( status, "rtems_task_delete of TA4" ); puts( "TA1 - rtems_semaphore_release - release SM1" ); status = rtems_semaphore_release( Semaphore_id[ 1 ] ); directive_failed( status, "rtems_semaphore_release on SM1" ); puts( "TA1 - rtems_task_wake_after - sleep 5 seconds" ); status = rtems_task_wake_after( 5 * rtems_clock_get_ticks_per_second() ); directive_failed( status, "rtems_task_wake_after" ); puts( "TA1 - rtems_semaphore_delete - delete SM1" ); status = rtems_semaphore_delete( Semaphore_id[ 1 ] ); directive_failed( status, "rtems_semaphore_delete of SM1" ); puts( "TA1 - rtems_semaphore_delete - delete SM3" ); status = rtems_semaphore_delete( Semaphore_id[ 3 ] ); directive_failed( status, "rtems_semaphore_delete of SM3" ); puts( "TA1 - rtems_task_delete - delete self" ); status = rtems_task_delete( RTEMS_SELF ); directive_failed( status, "rtems_task_delete of TA1" ); }
static void test(void) { rtems_status_code sc; rtems_task_argument i; size_t size; uint32_t cpu_count; rtems_task_priority priority; /* Get the number of processors that we are using. */ cpu_count = rtems_get_processor_count(); if (cpu_count != 4) { printf("Test requires a minimum of 4 cores\n"); return; } size = sizeof(cpu_set_t); task_data[0].id = rtems_task_self(); printf("Create Semaphore\n"); sc = rtems_semaphore_create( rtems_build_name('S', 'E', 'M', '0'), 1, /* initial count = 1 */ RTEMS_LOCAL | RTEMS_SIMPLE_BINARY_SEMAPHORE | RTEMS_NO_INHERIT_PRIORITY | RTEMS_NO_PRIORITY_CEILING | RTEMS_FIFO, 0, &task_sem ); rtems_test_assert(sc == RTEMS_SUCCESSFUL); /* Create and start tasks on each cpu with the appropriate affinity. */ for (i = 1; i < TASK_COUNT; i++) { sc = rtems_task_create( rtems_build_name('T', 'A', '0', '0'+i), task_data[ i ].priority, RTEMS_MINIMUM_STACK_SIZE, RTEMS_DEFAULT_MODES, RTEMS_DEFAULT_ATTRIBUTES, &task_data[ i ].id ); rtems_test_assert(sc == RTEMS_SUCCESSFUL); sc = rtems_task_set_affinity( task_data[ i ].id, size, &task_data[i].cpuset ); rtems_test_assert(sc == RTEMS_SUCCESSFUL); printf( "Start TA%d at priority %d on cpu %d\n", i, task_data[i].priority, task_data[i].expected_cpu ); sc = rtems_task_start( task_data[ i ].id, task, i ); rtems_test_assert(sc == RTEMS_SUCCESSFUL); } /* spin for 100 ticks */ test_delay(100); verify_tasks(); i = TASK_COUNT - 1; task_data[ i ].priority = 4; printf("Set TA%d priority %d\n", i,task_data[i].priority ); sc = rtems_task_set_priority( task_data[ i ].id, task_data[ i ].priority, &priority ); test_delay(25); while( rtems_semaphore_obtain (task_sem, RTEMS_NO_WAIT, 0) != RTEMS_SUCCESSFUL ); for (i = 0; i < TASK_COUNT; i++) { task_data[ i ].expected_cpu = task_data[ i ].migrate_cpu; task_data[ i ].actual_cpu = -1; task_data[ i ].ran = false; } rtems_semaphore_release(task_sem); test_delay(25); verify_tasks(); }
void __po_hi_gqueue_wait_for_incoming_event (__po_hi_task_id id, __po_hi_local_port_t* port) { #ifdef RTEMS_PURE rtems_status_code ret; #endif #ifdef _WIN32 DWORD ret; #endif #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) int error = pthread_mutex_lock (&__po_hi_gqueues_mutexes[id]); __DEBUGMSG("*** Locking (%d) %d\n", id, error); #elif defined (XENO_NATIVE) rt_mutex_acquire (&__po_hi_gqueues_mutexes[id], TM_INFINITE); #elif defined (RTEMS_PURE) ret = rtems_semaphore_obtain (__po_hi_gqueues_semaphores[id], RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (ret != RTEMS_SUCCESSFUL) { __DEBUGMSG ("[GQUEUE] Cannot obtain semaphore in __po_hi_gqueue_store_in()\n"); } #elif defined (_WIN32) EnterCriticalSection(&__po_hi_gqueues_cs[id]); #endif while(__po_hi_gqueues_queue_is_empty[id] == 1) { __PO_HI_INSTRUMENTATION_VCD_WRITE("0t%d\n", id); #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) __DEBUGMSG("*** Waiting (%d)\n", id); int error = pthread_cond_wait (&__po_hi_gqueues_conds[id], &__po_hi_gqueues_mutexes[id]); __DEBUGMSG("*** Done Waiting (%d) %d\n", id, error); #elif defined (XENO_NATIVE) rt_cond_wait (&__po_hi_gqueues_conds[id], &__po_hi_gqueues_mutexes[id], TM_INFINITE); #elif defined (RTEMS_PURE) ret = rtems_semaphore_release (__po_hi_gqueues_semaphores[id]); if (ret != RTEMS_SUCCESSFUL) { __DEBUGMSG ("[GQUEUE] Cannot obtain semaphore in __po_hi_gqueue_store_in()\n"); } rtems_task_wake_after (1); ret = rtems_semaphore_obtain (__po_hi_gqueues_semaphores[id], RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (ret != RTEMS_SUCCESSFUL) { __DEBUGMSG ("[GQUEUE] Cannot obtain semaphore in __po_hi_gqueue_store_in()\n"); } else { __PO_HI_DEBUG_CRITICAL ("[GQUEUE] semaphore %d obtained\n", id); } #elif defined (_WIN32) LeaveCriticalSection(&__po_hi_gqueues_cs[id]); ret = WaitForSingleObject (__po_hi_gqueues_events[id], INFINITE); if (ret == WAIT_FAILED) { __PO_HI_DEBUG_CRITICAL ("[GQUEUE] Wait failed\n"); } EnterCriticalSection(&__po_hi_gqueues_cs[id]); #endif __PO_HI_INSTRUMENTATION_VCD_WRITE("1t%d\n", id); } __DEBUGMSG ("[GQUEUE] Gogo kiki\n"); *port = __po_hi_gqueues_global_history[id][__po_hi_gqueues_global_history_offset[id]]; #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) pthread_mutex_unlock (&__po_hi_gqueues_mutexes[id]); #elif defined (XENO_NATIVE) rt_mutex_release (&__po_hi_gqueues_mutexes[id]); #elif defined (_WIN32) LeaveCriticalSection(&__po_hi_gqueues_cs[id]); #elif defined (RTEMS_PURE) ret = rtems_semaphore_release (__po_hi_gqueues_semaphores[id]); if (ret != RTEMS_SUCCESSFUL) { __DEBUGMSG ("[GQUEUE] Cannot release semaphore in __po_hi_gqueue_store_in()\n"); } __PO_HI_DEBUG_CRITICAL ("[GQUEUE] semaphore %d released\n", id); #endif }
int __po_hi_gqueue_next_value (__po_hi_task_id id, __po_hi_local_port_t port) { #ifdef RTEMS_PURE rtems_status_code ret; #endif /* incomplete semantics, should discriminate and report whether there is a next value or not */ /* XXX change and use assert ? */ if (__po_hi_gqueues_sizes[id][port] == __PO_HI_GQUEUE_FIFO_INDATA) { return 1; } #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) pthread_mutex_lock (&__po_hi_gqueues_mutexes[id]); #elif defined (XENO_NATIVE) rt_mutex_acquire (&__po_hi_gqueues_mutexes[id], TM_INFINITE); #elif defined (_WIN32) EnterCriticalSection(&__po_hi_gqueues_cs[id]); #elif defined (RTEMS_PURE) ret = rtems_semaphore_obtain (__po_hi_gqueues_semaphores[id], RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (ret != RTEMS_SUCCESSFUL) { __DEBUGMSG ("[GQUEUE] Cannot obtain semaphore in __po_hi_gqueue_store_in()\n"); } #endif __po_hi_gqueues_offsets[id][port] = (__po_hi_gqueues_offsets[id][port] + 1) % __po_hi_gqueues_sizes[id][port]; __po_hi_gqueues_used_size[id][port]--; __PO_HI_INSTRUMENTATION_VCD_WRITE("r%d p%d.%d\n", __po_hi_gqueues_used_size[id][port], id, port); if (__po_hi_gqueues_used_size[id][port] == 0) { __po_hi_gqueues_n_empty[id]++; __po_hi_gqueues_port_is_empty[id][port] = 1; } if (__po_hi_gqueues_n_empty[id] == __po_hi_gqueues_nb_ports[id]) { __po_hi_gqueues_queue_is_empty[id] = 1; } __po_hi_gqueues_global_history_offset[id] = (__po_hi_gqueues_global_history_offset[id] + 1) % __po_hi_gqueues_total_fifo_size[id]; #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) pthread_mutex_unlock (&__po_hi_gqueues_mutexes[id]); #elif defined (XENO_NATIVE) rt_mutex_release (&__po_hi_gqueues_mutexes[id]); #elif defined (RTEMS_PURE) ret = rtems_semaphore_release (__po_hi_gqueues_semaphores[id]); if (ret != RTEMS_SUCCESSFUL) { __DEBUGMSG ("[GQUEUE] Cannot release semaphore in __po_hi_gqueue_store_in()\n"); } #elif defined (_WIN32) LeaveCriticalSection(&__po_hi_gqueues_cs[id]); #endif return __PO_HI_SUCCESS; }
rtems_status_code rtems_termios_close (void *arg) { rtems_libio_open_close_args_t *args = arg; struct rtems_termios_tty *tty = args->iop->data1; rtems_status_code sc; sc = rtems_semaphore_obtain( rtems_termios_ttyMutex, RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); if (--tty->refcount == 0) { if (rtems_termios_linesw[tty->t_line].l_close != NULL) { /* * call discipline-specific close */ sc = rtems_termios_linesw[tty->t_line].l_close(tty); } else { /* * default: just flush output buffer */ sc = rtems_semaphore_obtain(tty->osem, RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (sc != RTEMS_SUCCESSFUL) { rtems_fatal_error_occurred (sc); } drainOutput (tty); rtems_semaphore_release (tty->osem); } if (tty->device.outputUsesInterrupts == TERMIOS_TASK_DRIVEN) { /* * send "terminate" to I/O tasks */ sc = rtems_event_send( tty->rxTaskId, TERMIOS_RX_TERMINATE_EVENT ); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); sc = rtems_event_send( tty->txTaskId, TERMIOS_TX_TERMINATE_EVENT ); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); } if (tty->device.lastClose) (*tty->device.lastClose)(tty->major, tty->minor, arg); if (tty->forw == NULL) { rtems_termios_ttyTail = tty->back; if ( rtems_termios_ttyTail != NULL ) { rtems_termios_ttyTail->forw = NULL; } } else { tty->forw->back = tty->back; } if (tty->back == NULL) { rtems_termios_ttyHead = tty->forw; if ( rtems_termios_ttyHead != NULL ) { rtems_termios_ttyHead->back = NULL; } } else { tty->back->forw = tty->forw; } rtems_semaphore_delete (tty->isem); rtems_semaphore_delete (tty->osem); rtems_semaphore_delete (tty->rawOutBuf.Semaphore); if ((tty->device.pollRead == NULL) || (tty->device.outputUsesInterrupts == TERMIOS_TASK_DRIVEN)) rtems_semaphore_delete (tty->rawInBuf.Semaphore); rtems_interrupt_lock_destroy (&tty->interrupt_lock); free (tty->rawInBuf.theBuf); free (tty->rawOutBuf.theBuf); free (tty->cbuf); free (tty); } rtems_semaphore_release (rtems_termios_ttyMutex); return RTEMS_SUCCESSFUL; }
rtems_status_code rtems_termios_ioctl (void *arg) { rtems_libio_ioctl_args_t *args = arg; struct rtems_termios_tty *tty = args->iop->data1; struct ttywakeup *wakeup = (struct ttywakeup *)args->buffer; rtems_status_code sc; args->ioctl_return = 0; sc = rtems_semaphore_obtain (tty->osem, RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (sc != RTEMS_SUCCESSFUL) { return sc; } switch (args->command) { default: if (rtems_termios_linesw[tty->t_line].l_ioctl != NULL) { sc = rtems_termios_linesw[tty->t_line].l_ioctl(tty,args); } else { sc = RTEMS_INVALID_NUMBER; } break; case RTEMS_IO_GET_ATTRIBUTES: *(struct termios *)args->buffer = tty->termios; break; case RTEMS_IO_SET_ATTRIBUTES: tty->termios = *(struct termios *)args->buffer; /* check for and process change in flow control options */ termios_set_flowctrl(tty); if (tty->termios.c_lflag & ICANON) { tty->rawInBufSemaphoreOptions = RTEMS_WAIT; tty->rawInBufSemaphoreTimeout = RTEMS_NO_TIMEOUT; tty->rawInBufSemaphoreFirstTimeout = RTEMS_NO_TIMEOUT; } else { tty->vtimeTicks = tty->termios.c_cc[VTIME] * rtems_clock_get_ticks_per_second() / 10; if (tty->termios.c_cc[VTIME]) { tty->rawInBufSemaphoreOptions = RTEMS_WAIT; tty->rawInBufSemaphoreTimeout = tty->vtimeTicks; if (tty->termios.c_cc[VMIN]) tty->rawInBufSemaphoreFirstTimeout = RTEMS_NO_TIMEOUT; else tty->rawInBufSemaphoreFirstTimeout = tty->vtimeTicks; } else { if (tty->termios.c_cc[VMIN]) { tty->rawInBufSemaphoreOptions = RTEMS_WAIT; tty->rawInBufSemaphoreTimeout = RTEMS_NO_TIMEOUT; tty->rawInBufSemaphoreFirstTimeout = RTEMS_NO_TIMEOUT; } else { tty->rawInBufSemaphoreOptions = RTEMS_NO_WAIT; } } } if (tty->device.setAttributes) (*tty->device.setAttributes)(tty->minor, &tty->termios); break; case RTEMS_IO_TCDRAIN: drainOutput (tty); break; case RTEMS_IO_TCFLUSH: switch ((intptr_t) args->buffer) { case TCIFLUSH: flushInput (tty); break; case TCOFLUSH: flushOutput (tty); break; case TCIOFLUSH: flushOutput (tty); flushInput (tty); break; default: sc = RTEMS_INVALID_NAME; break; } break; case RTEMS_IO_SNDWAKEUP: tty->tty_snd = *wakeup; break; case RTEMS_IO_RCVWAKEUP: tty->tty_rcv = *wakeup; break; /* * FIXME: add various ioctl code handlers */ #if 1 /* FIXME */ case TIOCSETD: /* * close old line discipline */ if (rtems_termios_linesw[tty->t_line].l_close != NULL) { sc = rtems_termios_linesw[tty->t_line].l_close(tty); } tty->t_line=*(int*)(args->buffer); tty->t_sc = NULL; /* ensure that no more valid data */ /* * open new line discipline */ if (rtems_termios_linesw[tty->t_line].l_open != NULL) { sc = rtems_termios_linesw[tty->t_line].l_open(tty); } break; case TIOCGETD: *(int*)(args->buffer)=tty->t_line; break; #endif case FIONREAD: { int rawnc = tty->rawInBuf.Tail - tty->rawInBuf.Head; if ( rawnc < 0 ) rawnc += tty->rawInBuf.Size; /* Half guess that this is the right operation */ *(int *)args->buffer = tty->ccount - tty->cindex + rawnc; } break; } rtems_semaphore_release (tty->osem); return sc; }
/* * Fill the input buffer from the raw input queue */ static rtems_status_code fillBufferQueue (struct rtems_termios_tty *tty) { rtems_interval timeout = tty->rawInBufSemaphoreFirstTimeout; rtems_status_code sc; int wait = 1; while ( wait ) { /* * Process characters read from raw queue */ while ((tty->rawInBuf.Head != tty->rawInBuf.Tail) && (tty->ccount < (CBUFSIZE-1))) { unsigned char c; unsigned int newHead; newHead = (tty->rawInBuf.Head + 1) % tty->rawInBuf.Size; c = tty->rawInBuf.theBuf[newHead]; tty->rawInBuf.Head = newHead; if(((tty->rawInBuf.Tail-newHead+tty->rawInBuf.Size) % tty->rawInBuf.Size) < tty->lowwater) { tty->flow_ctrl &= ~FL_IREQXOF; /* if tx stopped and XON should be sent... */ if (((tty->flow_ctrl & (FL_MDXON | FL_ISNTXOF)) == (FL_MDXON | FL_ISNTXOF)) && ((tty->rawOutBufState == rob_idle) || (tty->flow_ctrl & FL_OSTOP))) { /* XON should be sent now... */ (*tty->device.write)( tty->minor, (void *)&(tty->termios.c_cc[VSTART]), 1); } else if (tty->flow_ctrl & FL_MDRTS) { tty->flow_ctrl &= ~FL_IRTSOFF; /* activate RTS line */ if (tty->device.startRemoteTx != NULL) { tty->device.startRemoteTx(tty->minor); } } } /* continue processing new character */ if (tty->termios.c_lflag & ICANON) { if (siproc (c, tty)) wait = 0; } else { siproc (c, tty); if (tty->ccount >= tty->termios.c_cc[VMIN]) wait = 0; } timeout = tty->rawInBufSemaphoreTimeout; } /* * Wait for characters */ if ( wait ) { sc = rtems_semaphore_obtain( tty->rawInBuf.Semaphore, tty->rawInBufSemaphoreOptions, timeout); if (sc != RTEMS_SUCCESSFUL) break; } } return RTEMS_SUCCESSFUL; }
/* * Open a termios device */ rtems_status_code rtems_termios_open ( rtems_device_major_number major, rtems_device_minor_number minor, void *arg, const rtems_termios_callbacks *callbacks ) { rtems_status_code sc; rtems_libio_open_close_args_t *args = arg; struct rtems_termios_tty *tty; /* * See if the device has already been opened */ sc = rtems_semaphore_obtain( rtems_termios_ttyMutex, RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (sc != RTEMS_SUCCESSFUL) return sc; for (tty = rtems_termios_ttyHead ; tty != NULL ; tty = tty->forw) { if ((tty->major == major) && (tty->minor == minor)) break; } if (tty == NULL) { static char c = 'a'; /* * Create a new device */ tty = calloc (1, sizeof (struct rtems_termios_tty)); if (tty == NULL) { rtems_semaphore_release (rtems_termios_ttyMutex); return RTEMS_NO_MEMORY; } /* * allocate raw input buffer */ tty->rawInBuf.Size = RAW_INPUT_BUFFER_SIZE; tty->rawInBuf.theBuf = malloc (tty->rawInBuf.Size); if (tty->rawInBuf.theBuf == NULL) { free(tty); rtems_semaphore_release (rtems_termios_ttyMutex); return RTEMS_NO_MEMORY; } /* * allocate raw output buffer */ tty->rawOutBuf.Size = RAW_OUTPUT_BUFFER_SIZE; tty->rawOutBuf.theBuf = malloc (tty->rawOutBuf.Size); if (tty->rawOutBuf.theBuf == NULL) { free((void *)(tty->rawInBuf.theBuf)); free(tty); rtems_semaphore_release (rtems_termios_ttyMutex); return RTEMS_NO_MEMORY; } /* * allocate cooked buffer */ tty->cbuf = malloc (CBUFSIZE); if (tty->cbuf == NULL) { free((void *)(tty->rawOutBuf.theBuf)); free((void *)(tty->rawInBuf.theBuf)); free(tty); rtems_semaphore_release (rtems_termios_ttyMutex); return RTEMS_NO_MEMORY; } /* * Initialize wakeup callbacks */ tty->tty_snd.sw_pfn = NULL; tty->tty_snd.sw_arg = NULL; tty->tty_rcv.sw_pfn = NULL; tty->tty_rcv.sw_arg = NULL; tty->tty_rcvwakeup = 0; /* * link tty */ tty->forw = rtems_termios_ttyHead; tty->back = NULL; if (rtems_termios_ttyHead != NULL) rtems_termios_ttyHead->back = tty; rtems_termios_ttyHead = tty; if (rtems_termios_ttyTail == NULL) rtems_termios_ttyTail = tty; tty->minor = minor; tty->major = major; /* * Set up mutex semaphores */ sc = rtems_semaphore_create ( rtems_build_name ('T', 'R', 'i', c), 1, RTEMS_BINARY_SEMAPHORE | RTEMS_INHERIT_PRIORITY | RTEMS_PRIORITY, RTEMS_NO_PRIORITY, &tty->isem); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); sc = rtems_semaphore_create ( rtems_build_name ('T', 'R', 'o', c), 1, RTEMS_BINARY_SEMAPHORE | RTEMS_INHERIT_PRIORITY | RTEMS_PRIORITY, RTEMS_NO_PRIORITY, &tty->osem); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); sc = rtems_semaphore_create ( rtems_build_name ('T', 'R', 'x', c), 0, RTEMS_SIMPLE_BINARY_SEMAPHORE | RTEMS_FIFO, RTEMS_NO_PRIORITY, &tty->rawOutBuf.Semaphore); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); tty->rawOutBufState = rob_idle; /* * Set callbacks */ tty->device = *callbacks; rtems_interrupt_lock_initialize (&tty->interrupt_lock, "Termios"); /* * Create I/O tasks */ if (tty->device.outputUsesInterrupts == TERMIOS_TASK_DRIVEN) { sc = rtems_task_create ( rtems_build_name ('T', 'x', 'T', c), TERMIOS_TXTASK_PRIO, TERMIOS_TXTASK_STACKSIZE, RTEMS_NO_PREEMPT | RTEMS_NO_TIMESLICE | RTEMS_NO_ASR, RTEMS_NO_FLOATING_POINT | RTEMS_LOCAL, &tty->txTaskId); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); sc = rtems_task_create ( rtems_build_name ('R', 'x', 'T', c), TERMIOS_RXTASK_PRIO, TERMIOS_RXTASK_STACKSIZE, RTEMS_NO_PREEMPT | RTEMS_NO_TIMESLICE | RTEMS_NO_ASR, RTEMS_NO_FLOATING_POINT | RTEMS_LOCAL, &tty->rxTaskId); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); } if ((tty->device.pollRead == NULL) || (tty->device.outputUsesInterrupts == TERMIOS_TASK_DRIVEN)){ sc = rtems_semaphore_create ( rtems_build_name ('T', 'R', 'r', c), 0, RTEMS_SIMPLE_BINARY_SEMAPHORE | RTEMS_PRIORITY, RTEMS_NO_PRIORITY, &tty->rawInBuf.Semaphore); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); } /* * Set default parameters */ tty->termios.c_iflag = BRKINT | ICRNL | IXON | IMAXBEL; tty->termios.c_oflag = OPOST | ONLCR | XTABS; tty->termios.c_cflag = B9600 | CS8 | CREAD | CLOCAL; tty->termios.c_lflag = ISIG | ICANON | IEXTEN | ECHO | ECHOK | ECHOE | ECHOCTL; tty->termios.c_cc[VINTR] = '\003'; tty->termios.c_cc[VQUIT] = '\034'; tty->termios.c_cc[VERASE] = '\177'; tty->termios.c_cc[VKILL] = '\025'; tty->termios.c_cc[VEOF] = '\004'; tty->termios.c_cc[VEOL] = '\000'; tty->termios.c_cc[VEOL2] = '\000'; tty->termios.c_cc[VSTART] = '\021'; tty->termios.c_cc[VSTOP] = '\023'; tty->termios.c_cc[VSUSP] = '\032'; tty->termios.c_cc[VREPRINT] = '\022'; tty->termios.c_cc[VDISCARD] = '\017'; tty->termios.c_cc[VWERASE] = '\027'; tty->termios.c_cc[VLNEXT] = '\026'; /* start with no flow control, clear flow control flags */ tty->flow_ctrl = 0; /* * set low/highwater mark for XON/XOFF support */ tty->lowwater = tty->rawInBuf.Size * 1/2; tty->highwater = tty->rawInBuf.Size * 3/4; /* * Bump name characer */ if (c++ == 'z') c = 'a'; } args->iop->data1 = tty; if (!tty->refcount++) { if (tty->device.firstOpen) (*tty->device.firstOpen)(major, minor, arg); /* * start I/O tasks, if needed */ if (tty->device.outputUsesInterrupts == TERMIOS_TASK_DRIVEN) { sc = rtems_task_start( tty->rxTaskId, rtems_termios_rxdaemon, (rtems_task_argument)tty); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); sc = rtems_task_start( tty->txTaskId, rtems_termios_txdaemon, (rtems_task_argument)tty); if (sc != RTEMS_SUCCESSFUL) rtems_fatal_error_occurred (sc); } } rtems_semaphore_release (rtems_termios_ttyMutex); return RTEMS_SUCCESSFUL; }
rtems_task Init(rtems_task_argument arg) { rtems_status_code status; int sc; uintptr_t max_free_size = 13 * RTEMS_MINIMUM_STACK_SIZE; void *greedy; all_thread_created = 0; TEST_BEGIN(); puts( "Init - Semaphore 1 create - OK" ); name1 = rtems_build_name('S', 'E', 'M', '1'); sc = rtems_semaphore_create( name1, 0, RTEMS_SIMPLE_BINARY_SEMAPHORE | RTEMS_FIFO, 0, &sema1 ); rtems_test_assert( sc == RTEMS_SUCCESSFUL ); puts( "Init - Semaphore 2 create - OK" ); name2 = rtems_build_name('S', 'E', 'M', '2'); sc = rtems_semaphore_create( name2, 0, RTEMS_SIMPLE_BINARY_SEMAPHORE | RTEMS_FIFO, 0, &sema2 ); rtems_test_assert( sc == RTEMS_SUCCESSFUL ); puts( "Init - pthread Key create - OK" ); sc = pthread_key_create( &Key, NULL ); rtems_test_assert( !sc ); /* Reduce workspace size if necessary to shorten test time */ greedy = rtems_workspace_greedy_allocate( &max_free_size, 1 ); for ( ; ; ) { rtems_id task_id; sc = rtems_task_create( rtems_build_name('T','A',created_task_count, ' '), 1, RTEMS_MINIMUM_STACK_SIZE, RTEMS_DEFAULT_MODES, RTEMS_DEFAULT_ATTRIBUTES, &task_id ); rtems_test_assert( (sc == RTEMS_UNSATISFIED) || (sc == RTEMS_TOO_MANY) || (sc == RTEMS_SUCCESSFUL) ); /** * when return is RTEMS_TOO_MANY or RTEMS_UNSATISFIED, there is not * enough source to create task. */ if ( (sc == RTEMS_TOO_MANY) || (sc == RTEMS_UNSATISFIED) ) { break; } ++created_task_count; sc = rtems_task_start( task_id, test_task, 0 ); rtems_test_assert( sc == RTEMS_SUCCESSFUL ); sc = rtems_semaphore_obtain( sema1, RTEMS_WAIT, 0 ); rtems_test_assert( sc == RTEMS_SUCCESSFUL ); } rtems_workspace_greedy_free( greedy ); printf( "Init - %d tasks have been created - OK\n" "Init - %d tasks have been setted key data - OK\n", setted_task_count, created_task_count ); rtems_test_assert( created_task_count == setted_task_count ); /* unblock all created tasks to let them set key data.*/ puts( "Init - flush semaphore 2 - OK" ); sc = rtems_semaphore_flush( sema2 ); rtems_test_assert( sc == RTEMS_SUCCESSFUL ); puts( "Init - sleep to yield processor - OK" ); status = rtems_task_wake_after( RTEMS_YIELD_PROCESSOR ); directive_failed( status, "rtems_task_wake_after" ); printf( "Init - %d Tasks have been got key data - OK\n", got_task_count ); rtems_test_assert( created_task_count == got_task_count ); puts( "Init - pthread Key delete - OK" ); sc = pthread_key_delete( Key ); rtems_test_assert( sc == 0 ); puts( "Init - semaphore 1 delete - OK" ); sc = rtems_semaphore_delete( sema1 ); rtems_test_assert( !sc ); puts( "Init - semaphore 2 delete - OK" ); sc = rtems_semaphore_delete( sema2 ); rtems_test_assert( !sc ); TEST_END(); exit(0); }
/*-------------------------------------------------------------------------------------- Name: OS_unmount Purpose: unmounts a drive. and therefore makes all file descriptors pointing into the drive obsolete. Returns: OS_FS_ERR_INVALID_POINTER if name is NULL OS_FS_ERR_PATH_TOO_LONG if the absolute path given is too long OS_FS_ERROR if the OS calls failed OS_FS_SUCCESS if success ---------------------------------------------------------------------------------------*/ int32 OS_unmount (const char *mountpoint) { char local_path [OS_MAX_LOCAL_PATH_LEN]; int32 status; rtems_status_code rtems_sc; int i; if (mountpoint == NULL) { return OS_FS_ERR_INVALID_POINTER; } if (strlen(mountpoint) >= OS_MAX_PATH_LEN) { return OS_FS_ERR_PATH_TOO_LONG; } status = OS_TranslatePath(mountpoint, (char *)local_path); /* ** Lock */ rtems_sc = rtems_semaphore_obtain (OS_VolumeTableSem, RTEMS_WAIT, RTEMS_NO_TIMEOUT); for (i = 0; i < NUM_TABLE_ENTRIES; i++) { if (OS_VolumeTable[i].FreeFlag == FALSE && OS_VolumeTable[i].IsMounted == TRUE && strcmp(OS_VolumeTable[i].MountPoint, mountpoint) == 0) break; } /* make sure we found the device */ if (i >= NUM_TABLE_ENTRIES) { printf("OSAL: Error: unmount of %s failed: invalid volume table entry.\n", local_path); rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return OS_FS_ERROR; } if (OS_VolumeTable[i].VolumeType == RAM_DISK) { /* ** Try to unmount the disk */ if ( unmount(local_path) < 0) { printf("OSAL: RTEMS unmount of %s failed :%s\n",local_path, strerror(errno)); rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return OS_FS_ERROR; } /* release the information from the table */ OS_VolumeTable[i].IsMounted = FALSE; strcpy(OS_VolumeTable[i].MountPoint, ""); } else if ( OS_VolumeTable[i].VolumeType == FS_BASED ) { /* release the information from the table */ OS_VolumeTable[i].IsMounted = FALSE; strcpy(OS_VolumeTable[i].MountPoint, ""); } else { /* ** VolumeType is not supported right now */ rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return OS_FS_ERROR; } /* ** Unlock */ rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return OS_FS_SUCCESS; }/* end OS_umount */
int32 OS_mount (const char *devname, char* mountpoint) { int i; rtems_status_code rtems_sc; /* Check parameters */ if ( devname == NULL || mountpoint == NULL ) { return OS_FS_ERR_INVALID_POINTER; } /* ** Lock */ rtems_sc = rtems_semaphore_obtain (OS_VolumeTableSem, RTEMS_WAIT, RTEMS_NO_TIMEOUT); /* find the device in the table */ for (i = 0; i < NUM_TABLE_ENTRIES; i++) { if ((OS_VolumeTable[i].FreeFlag == FALSE ) && (OS_VolumeTable[i].IsMounted == FALSE ) && (strcmp(OS_VolumeTable[i].DeviceName, devname) == 0)) { break; } } /* Return an error if an un-mounted device was not found */ if (i >= NUM_TABLE_ENTRIES) { rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return OS_FS_ERROR; } if (OS_VolumeTable[i].VolumeType == RAM_DISK) { /* ** Mount the RFS Disk ** Note: This code only works with RTEMS 4.10 and up. The mount API has changed with ** RTEMS 4.10 */ if ( mount(OS_VolumeTable[i].PhysDevName, mountpoint, RTEMS_FILESYSTEM_TYPE_RFS, 0, NULL) != 0 ) { printf("OSAL: Error: mount of %s to %s failed: %s\n", OS_VolumeTable[i].PhysDevName, mountpoint, strerror(errno)); rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return OS_FS_ERROR; } /* attach the mountpoint */ strcpy(OS_VolumeTable[i].MountPoint, mountpoint); OS_VolumeTable[i].IsMounted = TRUE; } else if ( OS_VolumeTable[i].VolumeType == FS_BASED ) { /* attach the mountpoint */ strcpy(OS_VolumeTable[i].MountPoint, mountpoint); OS_VolumeTable[i].IsMounted = TRUE; } else { /* ** VolumeType is not supported right now */ rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return OS_FS_ERROR; } /* ** Unlock */ rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return OS_FS_SUCCESS; }/* end OS_mount */
/* msdos_eval_path -- * * The following routine evaluate path for a node that wishes to be * accessed. Structure 'pathloc' is returned with a pointer to the * node to be accessed. * * PARAMETERS: * pathname - path for evaluation * flags - flags * pathloc - node description (IN/OUT) * * RETURNS: * RC_OK and filled pathloc on success, or -1 if error occured * (errno set appropriately) * */ int msdos_eval_path( const char *pathname, size_t pathnamelen, int flags, rtems_filesystem_location_info_t *pathloc ) { int rc = RC_OK; rtems_status_code sc = RTEMS_SUCCESSFUL; msdos_fs_info_t *fs_info = pathloc->mt_entry->fs_info; fat_file_fd_t *fat_fd = NULL; rtems_filesystem_location_info_t newloc; int i = 0; int token_len = 0; msdos_token_types_t type = MSDOS_CURRENT_DIR; const char *token; sc = rtems_semaphore_obtain(fs_info->vol_sema, RTEMS_WAIT, MSDOS_VOLUME_SEMAPHORE_TIMEOUT); if (sc != RTEMS_SUCCESSFUL) rtems_set_errno_and_return_minus_one(EIO); if (!pathloc->node_access) { errno = ENOENT; rc = -1; goto err; } fat_fd = pathloc->node_access; rc = fat_file_reopen(fat_fd); if (rc != RC_OK) goto err; while ((type != MSDOS_NO_MORE_PATH) && (type != MSDOS_INVALID_TOKEN)) { type = msdos_get_token(&pathname[i], pathnamelen, &token, &token_len); pathnamelen -= token_len; i += token_len; fat_fd = pathloc->node_access; switch (type) { case MSDOS_UP_DIR: /* * Only a directory can be decended into. */ if (fat_fd->fat_file_type != FAT_DIRECTORY) { errno = ENOTSUP; rc = -1; goto error; } /* * Am I at the root of this mounted filesystem? */ if (pathloc->node_access == pathloc->mt_entry->mt_fs_root.node_access) { /* * Am I at the root of all filesystems? * XXX: MSDOS is not supposed to be base fs. */ if (pathloc->node_access == rtems_filesystem_root.node_access) { break; /* Throw out the .. in this case */ } else { newloc = pathloc->mt_entry->mt_point_node; *pathloc = newloc; rc = fat_file_close(pathloc->mt_entry, fat_fd); if (rc != RC_OK) goto err; rtems_semaphore_release(fs_info->vol_sema); return (*pathloc->ops->evalpath_h)(&(pathname[i-token_len]), pathnamelen + token_len, flags, pathloc); } } else { rc = msdos_find_name(pathloc, token, token_len); if (rc != RC_OK) { if (rc == MSDOS_NAME_NOT_FOUND_ERR) { errno = ENOENT; rc = -1; } goto error; } } break; case MSDOS_NAME: /* * Only a directory can be decended into. */ if (fat_fd->fat_file_type != FAT_DIRECTORY) { errno = ENOTSUP; rc = -1; goto error; } /* * Otherwise find the token name in the present location and * set the node access to the point we have found. */ rc = msdos_find_name(pathloc, token, token_len); if (rc != RC_OK) { if (rc == MSDOS_NAME_NOT_FOUND_ERR) { errno = ENOENT; rc = -1; } goto error; } break; case MSDOS_NO_MORE_PATH: case MSDOS_CURRENT_DIR: break; case MSDOS_INVALID_TOKEN: errno = ENAMETOOLONG; rc = -1; goto error; break; } } /* * Always return the root node. * * If we are at a node that is a mount point. Set loc to the * new fs root node and let let the mounted filesystem set the handlers. * * NOTE: The behavior of stat() on a mount point appears to be * questionable. * NOTE: MSDOS filesystem currently doesn't support mount functionality -> * action not implemented */ fat_fd = pathloc->node_access; msdos_set_handlers(pathloc); rtems_semaphore_release(fs_info->vol_sema); return RC_OK; error: fat_file_close(pathloc->mt_entry, fat_fd); err: rtems_semaphore_release(fs_info->vol_sema); return rc; }
static void test(void) { rtems_status_code sc; uint32_t cpu_count; int cpu; int i; cpu_set_t cpuset; /* Get the number of processors that we are using. */ cpu_count = rtems_get_processor_count(); if (cpu_count < 2) { printf("Error: Test requires at least 2 cpus\n"); return; } printf("Create Semaphore\n"); sc = rtems_semaphore_create( rtems_build_name('S', 'E', 'M', '0'), 1, /* initial count = 1 */ RTEMS_LOCAL | RTEMS_SIMPLE_BINARY_SEMAPHORE | RTEMS_NO_INHERIT_PRIORITY | RTEMS_NO_PRIORITY_CEILING | RTEMS_FIFO, 0, &task_sem ); rtems_test_assert(sc == RTEMS_SUCCESSFUL); /* * Create and start TA1 at a higher priority * than the init task. */ sc = rtems_task_create( rtems_build_name('T', 'A', '0', '1'), 4, RTEMS_MINIMUM_STACK_SIZE, RTEMS_DEFAULT_MODES, RTEMS_DEFAULT_ATTRIBUTES, &task_data.id ); rtems_test_assert(sc == RTEMS_SUCCESSFUL); printf("Start TA1\n"); sc = rtems_task_start( task_data.id, task, 0 ); rtems_test_assert(sc == RTEMS_SUCCESSFUL); /* * Verify the Init task is running on the max core. */ printf("Verify Init task is on cpu %ld\n",cpu_count-1); cpu = rtems_get_current_processor(); rtems_test_assert(cpu == (cpu_count-1)); /* Walk TA1 across all of the cores */ for(i=0; i < cpu_count; i++) { /* Set the Affinity to core i */ CPU_ZERO(&cpuset); CPU_SET(i, &cpuset); printf("Set Affinity TA1 to cpu %d\n", i); sc = rtems_task_set_affinity( task_data.id, sizeof(cpuset), &cpuset ); rtems_test_assert(sc == RTEMS_SUCCESSFUL); /* Wait a bit to be sure it has switched cores then clear the task data */ test_delay(50); while( rtems_semaphore_obtain (task_sem, RTEMS_NO_WAIT, 0) != RTEMS_SUCCESSFUL ); task_data.ran = false; task_data.expected_cpu = i; rtems_semaphore_release(task_sem); test_delay(50); /* Verify the task ran on core i */ while( rtems_semaphore_obtain (task_sem, RTEMS_NO_WAIT, 0) != RTEMS_SUCCESSFUL ); if (task_data.ran != true) printf("Error: TA01 never ran.\n"); else printf( "TA1 expected cpu: %d actual cpu %d\n", task_data.expected_cpu, task_data.actual_cpu ); rtems_test_assert(task_data.ran == true); rtems_test_assert(task_data.expected_cpu == task_data.actual_cpu); rtems_semaphore_release(task_sem); } }
__po_hi_uint8_t __po_hi_gqueue_store_in (__po_hi_task_id id, __po_hi_local_port_t port, __po_hi_request_t* request) { __po_hi_request_t* ptr; __po_hi_request_t* tmp; __po_hi_uint32_t size; #ifdef RTEMS_PURE rtems_status_code ret; #endif ptr = &__po_hi_gqueues_most_recent_values[id][port]; #ifdef __PO_HI_DEBUG if (ptr == NULL) { __DEBUGMSG ("__po_hi_gqueue_store_in : NULL POINTER\n"); } #endif #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) pthread_mutex_lock (&__po_hi_gqueues_mutexes[id]); #elif defined (XENO_NATIVE) rt_mutex_acquire (&__po_hi_gqueues_mutexes[id], TM_INFINITE); #elif defined (RTEMS_PURE) __DEBUGMSG ("[GQUEUE] Try to obtain semaphore for queue of task %d\n", id); ret = rtems_semaphore_obtain (__po_hi_gqueues_semaphores[id], RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (ret != RTEMS_SUCCESSFUL) { __DEBUGMSG ("[GQUEUE] Cannot obtain semaphore in __po_hi_gqueue_store_in()\n"); } __DEBUGMSG ("[GQUEUE] Semaphore got (id=%d)\n", id); #elif defined (_WIN32) EnterCriticalSection(&__po_hi_gqueues_cs[id]); #endif if (__po_hi_gqueues_sizes[id][port] == __PO_HI_GQUEUE_FIFO_INDATA) { memcpy(ptr,request,sizeof(*request)); } else { __DEBUGMSG ("[GQUEUE] Received message for task %d, port %d\n", id, port); if (__po_hi_gqueues_used_size[id][port] == __po_hi_gqueues_sizes[id][port]) { #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) pthread_mutex_unlock (&__po_hi_gqueues_mutexes[id]); #elif defined (XENO_NATIVE) rt_mutex_release (&__po_hi_gqueues_mutexes[id]); #elif defined (RTEMS_PURE) ret = rtems_semaphore_release (__po_hi_gqueues_semaphores[id]); if (ret != RTEMS_SUCCESSFUL) { __PO_HI_DEBUG_CRITICAL ("[GQUEUE] Cannot release semaphore in __po_hi_gqueue_store_in()\n"); } #elif defined (_WIN32) LeaveCriticalSection(&__po_hi_gqueues_cs[id]); #endif __PO_HI_DEBUG_CRITICAL ("[GQUEUE] QUEUE FULL, task-id=%d, port=%d\n", id, port); __DEBUGMSG ("[GQUEUE] Semaphore released (id=%d)\n", id); return __PO_HI_ERROR_QUEUE_FULL; } tmp = (__po_hi_request_t*) &__po_hi_gqueues[id][port]; size = __po_hi_gqueues_woffsets[id][port] + __po_hi_gqueues_first[id][port]; tmp = tmp + size; memcpy (tmp , request, sizeof (__po_hi_request_t)); __po_hi_gqueues_woffsets[id][port] = (__po_hi_gqueues_woffsets[id][port] + 1 ) % __po_hi_gqueues_sizes[id][port]; __po_hi_gqueues_used_size[id][port]++; __PO_HI_INSTRUMENTATION_VCD_WRITE("r%d p%d.%d\n", __po_hi_gqueues_used_size[id][port], id, port); __po_hi_gqueues_global_history[id][__po_hi_gqueues_global_history_woffset[id]] = port; __po_hi_gqueues_global_history_woffset[id] = (__po_hi_gqueues_global_history_woffset[id] + 1 ) % __po_hi_gqueues_total_fifo_size[id]; if (__po_hi_gqueues_port_is_empty[id][port] == 1) { __po_hi_gqueues_port_is_empty[id][port] = 0; __po_hi_gqueues_n_empty[id]--; } __po_hi_gqueues_queue_is_empty[id] = 0; } #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) pthread_mutex_unlock (&__po_hi_gqueues_mutexes[id]); int err = pthread_cond_signal (&__po_hi_gqueues_conds[id]); __DEBUGMSG("*** Releasing (%d) %d\n", id, err); #elif defined (XENO_NATIVE) rt_mutex_release (&__po_hi_gqueues_mutexes[id]); rt_cond_broadcast (&__po_hi_gqueues_conds[id]); #elif defined (_WIN32) LeaveCriticalSection(&__po_hi_gqueues_cs[id]); if (! SetEvent(__po_hi_gqueues_events[id]) ) { __DEBUGMSG("SetEvent failed (%d)\n", GetLastError()); } #elif defined (RTEMS_PURE) ret = rtems_semaphore_release (__po_hi_gqueues_semaphores[id]); if (ret != RTEMS_SUCCESSFUL) { __PO_HI_DEBUG_CRITICAL ("[GQUEUE] Cannot release semaphore in __po_hi_gqueue_store_in()\n"); } __DEBUGMSG ("[GQUEUE] Semaphore released (id=%d)\n", id); #endif __DEBUGMSG ("[GQUEUE] store_in completed\n"); return __PO_HI_SUCCESS; }
rtems_status_code bfin_twi_request(int channel, uint8_t address, bfin_twi_request_t *request, rtems_interval timeout) { rtems_status_code result; void *base; rtems_interrupt_level level; uint16_t r; uint16_t masterMode; if (channel < 0 || channel >= N_BFIN_TWI) return RTEMS_INVALID_NUMBER; result = rtems_semaphore_obtain(twi[channel].mutex, RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (result == RTEMS_SUCCESSFUL) { base = twi[channel].base; twi[channel].req = request; if (request->write) { twi[channel].dataPtr = request->data; twi[channel].count = request->count; } else twi[channel].count = 0; BFIN_REG16(base, TWI_MASTER_ADDR_OFFSET) = (uint16_t) address << TWI_MASTER_ADDR_MADDR_SHIFT; masterMode = BFIN_REG16(base, TWI_MASTER_CTL_OFFSET); masterMode |= (request->count << TWI_MASTER_CTL_DCNT_SHIFT); if (request->next) masterMode |= TWI_MASTER_CTL_RSTART; if (!request->write) masterMode |= TWI_MASTER_CTL_MDIR; masterMode |= TWI_MASTER_CTL_MEN; rtems_interrupt_disable(level); if (!twi[channel].slaveActive) { r = BFIN_REG16(base, TWI_FIFO_CTL_OFFSET); BFIN_REG16(base, TWI_FIFO_CTL_OFFSET) = r | TWI_FIFO_CTL_XMTFLUSH; BFIN_REG16(base, TWI_FIFO_CTL_OFFSET) = r; if (request->write) { while (twi[channel].count && (BFIN_REG16(base, TWI_FIFO_STAT_OFFSET) & TWI_FIFO_STAT_XMTSTAT_MASK) != TWI_FIFO_STAT_XMTSTAT_FULL) { BFIN_REG16(base, TWI_XMT_DATA8_OFFSET) = (uint16_t) *twi[channel].dataPtr++; twi[channel].count--; } } twi[channel].masterActive = true; BFIN_REG16(base, TWI_MASTER_CTL_OFFSET) = masterMode; } else { twi[channel].masterActive = false; twi[channel].masterResult = -1; /* BISON (code should be equiv to lost arbitration) */ } rtems_interrupt_enable(level); while (result == RTEMS_SUCCESSFUL && twi[channel].masterActive) result = rtems_semaphore_obtain(twi[channel].irqSem, RTEMS_WAIT, timeout); if (result == RTEMS_SUCCESSFUL) result = twi[channel].masterResult; else { /* BISON abort */ } rtems_semaphore_release(twi[channel].mutex); } return result; }
int __po_hi_gqueue_get_value (__po_hi_task_id id, __po_hi_local_port_t port, __po_hi_request_t* request) { __po_hi_request_t* ptr; #ifdef RTEMS_PURE rtems_status_code ret; #endif #ifdef _WIN32 DWORD ret; #endif ptr = &__po_hi_gqueues_most_recent_values[id][port]; #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) pthread_mutex_lock (&__po_hi_gqueues_mutexes[id]); #elif defined (XENO_NATIVE) rt_mutex_acquire (&__po_hi_gqueues_mutexes[id], TM_INFINITE); #elif defined (RTEMS_PURE) ret = rtems_semaphore_obtain (__po_hi_gqueues_semaphores[id], RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (ret != RTEMS_SUCCESSFUL) { __DEBUGMSG ("[GQUEUE] Cannot obtain semaphore in __po_hi_gqueue_store_in()\n"); } #elif defined (_WIN32) EnterCriticalSection(&__po_hi_gqueues_cs[id]); #endif /* * If the port is an event port, with no value queued, then we block * the thread. */ if (__po_hi_gqueues_sizes[id][port] != __PO_HI_GQUEUE_FIFO_INDATA) { while (__po_hi_gqueues_port_is_empty[id][port] == 1) { #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) pthread_cond_wait (&__po_hi_gqueues_conds[id], &__po_hi_gqueues_mutexes[id]); #elif defined (XENO_NATIVE) rt_cond_wait (&__po_hi_gqueues_conds[id], &__po_hi_gqueues_mutexes[id], TM_INFINITE); #elif defined (RTEMS_PURE) rtems_task_wake_after( RTEMS_YIELD_PROCESSOR ); #elif defined (_WIN32) LeaveCriticalSection(&__po_hi_gqueues_cs[id]); ret = WaitForSingleObject (__po_hi_gqueues_events[id], INFINITE); if (ret == WAIT_FAILED) { __PO_HI_DEBUG_CRITICAL ("[GQUEUE] Wait failed\n"); } EnterCriticalSection(&__po_hi_gqueues_cs[id]); #endif } } #if defined (MONITORING) update_sporadic_dispatch (id, port); #endif if (__po_hi_gqueues_used_size[id][port] == 0) { memcpy (request, ptr, sizeof (__po_hi_request_t)); //update_runtime (id, port, ptr); } else { ptr = ((__po_hi_request_t *) &__po_hi_gqueues[id][port]) + __po_hi_gqueues_first[id][port] + __po_hi_gqueues_offsets[id][port]; memcpy (request, ptr, sizeof (__po_hi_request_t)); } __PO_HI_DEBUG_INFO ("[GQUEUE] Task %d get a value on port %d\n", id, port); #if defined (POSIX) || defined (RTEMS_POSIX) || defined (XENO_POSIX) pthread_mutex_unlock (&__po_hi_gqueues_mutexes[id]); #elif defined (XENO_NATIVE) rt_mutex_release (&__po_hi_gqueues_mutexes[id]); #elif defined (RTEMS_PURE) ret = rtems_semaphore_release (__po_hi_gqueues_semaphores[id]); if (ret != RTEMS_SUCCESSFUL) { __DEBUGMSG ("[GQUEUE] Cannot release semaphore in __po_hi_gqueue_store_in()\n"); } #elif defined (_WIN32) LeaveCriticalSection(&__po_hi_gqueues_cs[id]); #endif return 0; }
void AccessLocalHw(void) { rtems_status_code Sts; #if defined(TEST_PRINT_STATISTICS) rtems_task_priority AccessPrio; /* : */ uint32_t AccessCnt; /* : */ rtems_task_priority EnterPrio; /* Statistics log */ uint32_t EnterCnt; /* : */ rtems_task_priority LeavePrio; /* : */ uint32_t LeaveCnt; /* : */ #endif #if defined(TEST_PRINT_STATISTICS) /* Store information about the current situation */ EnterPrio = _Thread_Executing->current_priority; EnterCnt = _Thread_Executing->resource_count; #endif printf(" AccessLocalHw called by %s\n", CallerName()); /* Obtain exclusive access to local HW, Start HW, Wait for completion, * Release access */ Sts = rtems_semaphore_obtain(LocalHwAccess_R, RTEMS_WAIT, RTEMS_NO_TIMEOUT); directive_failed( Sts, "rtems_semaphore_obtain(LocalHwAccess_R...)" ); StartHw = TRUE; Sts = rtems_semaphore_obtain(LocalHwSync_S, RTEMS_WAIT, RTEMS_NO_TIMEOUT); directive_failed( Sts, "rtems_semaphore_obtain(LocalHwAccess_R...)" ); #if defined(TEST_PRINT_STATISTICS) /* Store information about the current situation */ AccessPrio = _Thread_Executing->current_priority; AccessCnt = _Thread_Executing->resource_count; #endif Sts = rtems_semaphore_release(LocalHwAccess_R); directive_failed( Sts, "rtems_semaphore_release(LocalHwAccess_R)" ); #if defined(TEST_PRINT_STATISTICS) /* Store information about the current situation */ LeavePrio = _Thread_Executing->current_priority; LeaveCnt = _Thread_Executing->resource_count; printf( " AccessLocalHw from %s statistics:\n" " - Prio: %d -> %d -> %d\n - Cnt: %d -> %d -> %d\n", CallerName(), EnterPrio, AccessPrio, LeavePrio, EnterCnt, AccessCnt, LeaveCnt ); #endif printf(" AccessLocalHw returns to %s\n", CallerName()); #if defined(TEST_EXIT_AFTER_ITERATIONS) if ( ++Iterations == 10 ) { puts( "*** END OF TEST 35 ***" ); exit(0); } #endif return; }
static void test(uint32_t cpu_count) { rtems_status_code sc; uint32_t t; uint32_t c; rtems_task_argument idx; cpu_set_t cpu_set; /* Semaphore to signal end of test */ sc = rtems_semaphore_create(rtems_build_name('D', 'o', 'n', 'e'), 0, RTEMS_LOCAL | RTEMS_NO_INHERIT_PRIORITY | RTEMS_NO_PRIORITY_CEILING | RTEMS_FIFO, 0, &finished_sem); /* * Create a set of tasks per CPU. Chain them together using * semaphores so that only one task can be active at any given * time. */ for ( c = 0; c < cpu_count; c++ ) { for ( t = 0; t < TASKS_PER_CPU; t++ ) { idx = c * TASKS_PER_CPU + t; sc = rtems_task_create(rtems_build_name('T', 'A', '0' + c, '0' + t), TASK_PRIO, RTEMS_MINIMUM_STACK_SIZE, RTEMS_DEFAULT_MODES, RTEMS_DEFAULT_ATTRIBUTES, &task_data[idx].id); rtems_test_assert(sc == RTEMS_SUCCESSFUL); sc = rtems_semaphore_create(rtems_build_name('S', 'E', '0' + c, '0' + t), 0, RTEMS_LOCAL | RTEMS_SIMPLE_BINARY_SEMAPHORE | RTEMS_NO_INHERIT_PRIORITY | RTEMS_NO_PRIORITY_CEILING | RTEMS_FIFO, 0, &task_data[idx].task_sem); rtems_test_assert(sc == RTEMS_SUCCESSFUL); task_data[(idx + 1) % (cpu_count * TASKS_PER_CPU)].prev_sem = task_data[idx].task_sem; CPU_ZERO_S(sizeof(cpu_set_t), &cpu_set); CPU_SET_S(c, sizeof(cpu_set_t), &cpu_set); sc = rtems_task_set_affinity(task_data[idx].id, sizeof(cpu_set_t), &cpu_set); rtems_test_assert(sc == RTEMS_SUCCESSFUL); } } /* Start the tasks */ for ( idx = 0; idx < cpu_count * TASKS_PER_CPU; idx++ ) { sc = rtems_task_start(task_data[idx].id, task, idx); rtems_test_assert(sc == RTEMS_SUCCESSFUL); } /* Start chain */ sc = rtems_semaphore_release(task_data[0].task_sem); /* Wait until chain has completed */ for ( idx = 0; idx < cpu_count * TASKS_PER_CPU; idx++ ) { rtems_semaphore_obtain(finished_sem, 0, 0); rtems_test_assert(sc == RTEMS_SUCCESSFUL); } }
rtems_task Test_task( rtems_task_argument argument ) { uint32_t semaphore_obtain_time; uint32_t semaphore_release_time; uint32_t semaphore_obtain_no_wait_time; uint32_t semaphore_obtain_loop_time; uint32_t semaphore_release_loop_time; uint32_t index; uint32_t iterations; rtems_name name; rtems_id smid; rtems_status_code status; name = rtems_build_name( 'S', 'M', '1', ' ' ); semaphore_obtain_time = 0; semaphore_release_time = 0; semaphore_obtain_no_wait_time = 0; semaphore_obtain_loop_time = 0; semaphore_release_loop_time = 0; /* Time one invocation of rtems_semaphore_create */ benchmark_timer_initialize(); (void) rtems_semaphore_create( name, OPERATION_COUNT, RTEMS_DEFAULT_MODES, RTEMS_NO_PRIORITY, &smid ); end_time = benchmark_timer_read(); put_time( "rtems_semaphore_create", end_time, 1, 0, CALLING_OVERHEAD_SEMAPHORE_CREATE ); /* Time one invocation of rtems_semaphore_delete */ benchmark_timer_initialize(); (void) rtems_semaphore_delete( smid ); end_time = benchmark_timer_read(); put_time( "rtems_semaphore_delete", end_time, 1, 0, CALLING_OVERHEAD_SEMAPHORE_CREATE ); status = rtems_semaphore_create( name, OPERATION_COUNT, RTEMS_DEFAULT_ATTRIBUTES, RTEMS_NO_PRIORITY, &smid ); for ( iterations=OPERATION_COUNT ; iterations ; iterations-- ) { benchmark_timer_initialize(); for ( index = 1 ; index<=OPERATION_COUNT ; index++ ) (void) benchmark_timer_empty_function(); end_time = benchmark_timer_read(); semaphore_obtain_loop_time += end_time; semaphore_release_loop_time += end_time; /* rtems_semaphore_obtain (available) */ benchmark_timer_initialize(); for ( index = 1 ; index<=OPERATION_COUNT ; index++ ) (void) rtems_semaphore_obtain( smid, RTEMS_DEFAULT_OPTIONS, RTEMS_NO_TIMEOUT ); end_time = benchmark_timer_read(); semaphore_obtain_time += end_time; /* rtems_semaphore_release */ benchmark_timer_initialize(); for ( index = 1 ; index<=OPERATION_COUNT ; index++ ) (void) rtems_semaphore_release( smid ); end_time = benchmark_timer_read(); semaphore_release_time += end_time; /* semaphore obtain (RTEMS_NO_WAIT) */ benchmark_timer_initialize(); for ( index = 1 ; index<=OPERATION_COUNT ; index++ ) rtems_semaphore_obtain( smid, RTEMS_NO_WAIT, RTEMS_NO_TIMEOUT ); semaphore_obtain_no_wait_time += benchmark_timer_read(); benchmark_timer_initialize(); for ( index = 1 ; index<=OPERATION_COUNT ; index++ ) rtems_semaphore_release( smid ); end_time = benchmark_timer_read(); semaphore_release_time += end_time; } put_time( "rtems_semaphore_obtain: available", semaphore_obtain_time, OPERATION_COUNT * OPERATION_COUNT, semaphore_obtain_loop_time, CALLING_OVERHEAD_SEMAPHORE_OBTAIN ); put_time( "rtems_semaphore_obtain: not available -- NO_WAIT", semaphore_obtain_no_wait_time, OPERATION_COUNT * OPERATION_COUNT, semaphore_obtain_loop_time, CALLING_OVERHEAD_SEMAPHORE_OBTAIN ); put_time( "rtems_semaphore_release: no waiting tasks", semaphore_release_time, OPERATION_COUNT * OPERATION_COUNT * 2, semaphore_release_loop_time * 2, CALLING_OVERHEAD_SEMAPHORE_RELEASE ); puts( "*** END OF TEST 1 ***" ); rtems_test_exit( 0 ); }
/* ADC/DAC Task */ void adcdac_task1( int argument ) { struct gradcdac_config cfg; unsigned short adc_value, adcvals[MAX_CHANS][10]; int ret; int i=0; unsigned int status, oldstatus; int chan, chansel; memset(adcvals,0,sizeof(adcvals)); printf("ADC/DAC task running\n"); #ifdef ADC_USE_INTERRUPT /* Connect ADC/DAC to Interrupt service routine 'adcdac_isr' */ gradcdac_install_irq_handler(adc_hand, GRADCDAC_ISR_ADC, adc_isr, 0); gradcdac_install_irq_handler(dac_hand, GRADCDAC_ISR_DAC, dac_isr, 0); #endif /* Get ADC/DAC configuration */ gradcdac_get_config(adc_hand, &cfg); /* Change ADC/DAC Configuration 0xfafc42 */ cfg.dac_ws = 0x1f; cfg.wr_pol = 0; cfg.dac_dw = 2; cfg.adc_ws = 0x1f; cfg.rc_pol = 1; cfg.cs_mode = 0; cfg.cs_pol = 0; cfg.ready_mode = 1; cfg.ready_pol = 0; cfg.trigg_pol = 0; cfg.trigg_mode = 0; cfg.adc_dw = 2; /* Set ADC/DAC Configurations */ gradcdac_set_config(adc_hand, &cfg); printf("Making DAC conversion\n"); /* Convert a Digital sample to an analogue Value, * in this test, the ADC input may be connected * to the DAC output. * * First the Address bit 6 (12/8) must be set. * */ gradcdac_set_dataoutput(adc_hand, 0); gradcdac_set_datadir(adc_hand, 0); gradcdac_set_adrdir(adc_hand, 0); gradcdac_set_adrdir(adc_hand, 0xff); gradcdac_set_adroutput(adc_hand, 0x40); gradcdac_dac_convert(adc_hand, 0x400); /* Wait for DAC to finish */ status = 0; do { oldstatus = status; rtems_task_wake_after(1); status = gradcdac_get_status(adc_hand); } while ( gradcdac_DAC_isOngoing(status) ); if ( gradcdac_DAC_ReqRej(status) ) { printf("DAC: rejected\n"); exit(-1); } if ( !gradcdac_DAC_isCompleted(status) ) { printf("DAC: didn't complete 0x%x prev 0x%x\n", status, oldstatus); status = gradcdac_get_status(adc_hand); printf("DAC: Status afterwards: 0x%x\n", status); exit(-1); } printf("DAC conversion complete\n"); chan=0; while (1) { #ifdef ADC_USE_INTERRUPT rtems_task_wake_after(20); /* sleep(1);*/ /* Clear semaphore */ rtems_semaphore_obtain(adcdac_sem, RTEMS_NO_WAIT, RTEMS_NO_TIMEOUT); #endif /* Select ADC channel */ switch (chan) { default: case 0: chansel = 0; break; case 1: chansel = 2; break; case 2: chansel = 1; break; case 3: chansel = 3; break; } gradcdac_set_adroutput(adc_hand, (0x40 | (chansel<<4)) ); rtems_task_wake_after(1); /* Start single Analog to Digital conversion */ gradcdac_adc_convert_start(adc_hand); wait_conversion_complete: #ifdef ADC_USE_INTERRUPT /* Wait for conversion to complete, the interrupt will signal * semaphore. */ rtems_semaphore_obtain(adcdac_sem, RTEMS_WAIT, RTEMS_NO_TIMEOUT); /* Do Work ... */ adcdac_wakeups++; #else sleep(1); #endif /* Get converted value */ adc_value=0xffff; ret = gradcdac_adc_convert_try(adc_hand, &adc_value); if ( ret == 0 ) { /* Move old values */ for(i=8; i>=0; i--){ adcvals[chan][i+1] = adcvals[chan][i]; } adcvals[chan][0] = adc_value; /* Filter the input ADC Value */ adc_filtered_val[chan] = adc_calc(&adcvals[chan][0]); adc_last_val[chan] = adc_value; } else if ( ret < 0 ) { printf("ADC: Failed\n"); } else { /* skip triggering a new conversion */ goto wait_conversion_complete; } if ( ++chan >= MAX_CHANS ) chan = 0; } }
rtems_task Init( rtems_task_argument argument ) { int i; char ch; int cpu_num; rtems_id id; rtems_status_code status; char str[80]; locked_print_initialize(); locked_printf( "\n\n*** SMP02 TEST ***\n" ); /* Create/verify synchronisation semaphore */ status = rtems_semaphore_create( rtems_build_name ('S', 'E', 'M', '1'), 1, RTEMS_LOCAL | RTEMS_SIMPLE_BINARY_SEMAPHORE | RTEMS_PRIORITY, 1, &Semaphore); directive_failed( status, "rtems_semaphore_create" ); /* Lock semaphore */ status = rtems_semaphore_obtain( Semaphore, RTEMS_WAIT, 0); directive_failed( status,"rtems_semaphore_obtain of SEM1\n"); for ( i=1; i < rtems_smp_get_number_of_processors(); i++ ){ /* Create and start tasks for each CPU */ ch = '0' + i; status = rtems_task_create( rtems_build_name( 'T', 'A', ch, ' ' ), 1, RTEMS_MINIMUM_STACK_SIZE, RTEMS_DEFAULT_MODES, RTEMS_DEFAULT_ATTRIBUTES, &id ); cpu_num = bsp_smp_processor_id(); locked_printf(" CPU %d start task TA%c\n", cpu_num, ch); status = rtems_task_start( id, Test_task, i+1 ); directive_failed( status, str ); } /* * Release the semaphore, allowing the blocked tasks to start. */ status = rtems_semaphore_release( Semaphore ); directive_failed( status,"rtems_semaphore_release of SEM1\n"); /* * Wait for log full. print the log and end the program. */ while (Log_index < LOG_SIZE) ; for (i=0; i< LOG_SIZE; i++) { if ( Log[i].IsLocked ) { locked_printf( " CPU %d Task TA%" PRIu32 " Obtain\n", Log[i].cpu_num, Log[i].task_index ); } else { locked_printf( " CPU %d Task TA%" PRIu32 " Release\n", Log[i].cpu_num, Log[i].task_index ); } } locked_printf( "*** END OF TEST SMP02 ***\n" ); rtems_test_exit( 0 ); }
void Screen6() { rtems_status_code status; status = rtems_semaphore_obtain( 100, RTEMS_DEFAULT_OPTIONS, RTEMS_NO_TIMEOUT ); fatal_directive_status( status, RTEMS_INVALID_ID, "rtems_semaphore_obtain with illegal id" ); puts( "TA1 - rtems_semaphore_obtain - RTEMS_INVALID_ID" ); status = rtems_semaphore_obtain( Semaphore_id[ 1 ], RTEMS_DEFAULT_OPTIONS, RTEMS_NO_TIMEOUT ); directive_failed( status, "rtems_semaphore_obtain successful" ); puts( "TA1 - rtems_semaphore_obtain - got sem 1 - RTEMS_SUCCESSFUL" ); status = rtems_semaphore_obtain( Semaphore_id[ 1 ], RTEMS_NO_WAIT, RTEMS_NO_TIMEOUT ); fatal_directive_status( status, RTEMS_UNSATISFIED, "rtems_semaphore_obtain not available" ); puts( "TA1 - rtems_semaphore_obtain - RTEMS_UNSATISFIED" ); puts( "TA1 - rtems_semaphore_obtain - timeout in 3 seconds" ); status = rtems_semaphore_obtain( Semaphore_id[ 1 ], RTEMS_DEFAULT_OPTIONS, 3 * TICKS_PER_SECOND ); fatal_directive_status( status, RTEMS_TIMEOUT, "rtems_semaphore_obtain timeout" ); puts( "TA1 - rtems_semaphore_obtain - woke up with RTEMS_TIMEOUT" ); status = rtems_semaphore_release( Semaphore_id[ 2 ] ); fatal_directive_status( status, RTEMS_NOT_OWNER_OF_RESOURCE, "rtems_semaphore_release and not owner" ); puts( "TA1 - rtems_semaphore_release - RTEMS_NOT_OWNER_OF_RESOURCE" ); status = rtems_semaphore_release( 100 ); fatal_directive_status( status, RTEMS_INVALID_ID, "rtems_semaphore_release with illegal id" ); puts( "TA1 - rtems_semaphore_release - RTEMS_INVALID_ID" ); puts( "TA1 - rtems_task_start - start TA2 - RTEMS_SUCCESSFUL" ); status = rtems_task_start( Task_id[ 2 ], Task_2, 0 ); directive_failed( status, "rtems_task_start of TA2" ); puts( "TA1 - rtems_task_wake_after - yield processor - RTEMS_SUCCESSFUL" ); status = rtems_task_wake_after( RTEMS_YIELD_PROCESSOR ); directive_failed( status, "rtems_task_wake_after (yield)" ); puts( "TA1 - rtems_semaphore_delete - delete sem 1 - RTEMS_SUCCESSFUL" ); status = rtems_semaphore_delete( Semaphore_id[ 1 ] ); directive_failed( status, "rtems_semaphore_delete of SM1" ); puts( "TA1 - rtems_semaphore_obtain - binary semaphore" ); status = rtems_semaphore_obtain( Semaphore_id[ 2 ], RTEMS_DEFAULT_OPTIONS, RTEMS_NO_TIMEOUT ); directive_failed( status, "rtems_semaphore_obtain"); puts( "TA1 - rtems_semaphore_delete - delete sem 2 - RTEMS_RESOURCE_IN_USE" ); status = rtems_semaphore_delete( Semaphore_id[ 2 ] ); fatal_directive_status( status, RTEMS_RESOURCE_IN_USE, "rtems_semaphore_delete of SM2" ); puts( "TA1 - rtems_task_wake_after - yield processor - RTEMS_SUCCESSFUL" ); status = rtems_task_wake_after( RTEMS_YIELD_PROCESSOR ); directive_failed( status, "rtems_task_wake_after (yield)" ); status = rtems_task_delete( Task_id[ 2 ] ); fatal_directive_status( status, RTEMS_INVALID_ID, "rtems_task_delete after the task has been deleted" ); }
/** * @brief Writes @a n characters from @a out to bus @a bus and synchronously stores the received data in @a in. * * eDMA channel usage for transmission: * @dot * digraph push { * push [label="Push Register"]; * push_data [label="Push Data"]; * idle_push_data [label="Idle Push Data"]; * out [shape=box,label="Output Buffer"]; * edge [color=red,fontcolor=red]; * push -> idle_push_data [label="Transmit Request",URL="\ref mpc55xx_dspi_bus_entry::edma_transmit"]; * push -> out [label="Transmit Request",URL="\ref mpc55xx_dspi_bus_entry::edma_transmit"]; * out -> push_data [label="Channel Link",URL="\ref mpc55xx_dspi_bus_entry::edma_push"]; * edge [color=blue,fontcolor=blue]; * out -> push_data [label="Data"]; * push_data -> push [label="Data"]; * idle_push_data -> push [label="Data"]; * } * @enddot * * eDMA channel usage for receiving: * @dot * digraph pop { * pop [label="Pop Register"]; * nirvana [label="Nirvana"]; * in [shape=box,label="Input Buffer"]; * edge [color=red,fontcolor=red]; * pop -> nirvana [label="Receive Request",URL="\ref mpc55xx_dspi_bus_entry::edma_receive"]; * pop -> in [label="Receive Request",URL="\ref mpc55xx_dspi_bus_entry::edma_receive"]; * edge [color=blue,fontcolor=blue]; * pop -> nirvana [label="Data"]; * pop -> in [label="Data"]; * } * @enddot */ static int mpc55xx_dspi_read_write( rtems_libi2c_bus_t *bus, unsigned char *in, const unsigned char *out, int n) { mpc55xx_dspi_bus_entry *e = (mpc55xx_dspi_bus_entry *) bus; /* Non cache aligned characters */ int n_nc = n; /* Cache aligned characters */ int n_c = 0; /* Register addresses */ volatile void *push = &e->regs->PUSHR.R; volatile void *pop = &e->regs->POPR.R; volatile union DSPI_SR_tag *status = &e->regs->SR; /* Push and pop data */ union DSPI_PUSHR_tag push_data = e->push_data; union DSPI_POPR_tag pop_data; /* Status register */ union DSPI_SR_tag sr; /* Read and write indices */ int r = 0; int w = 0; if (n == 0) { return 0; } else if (in == NULL && out == NULL) { return -RTEMS_INVALID_ADDRESS; } if (n > MPC55XX_DSPI_EDMA_MAGIC_SIZE) { n_nc = (int) mpc55xx_non_cache_aligned_size( in); n_c = (int) mpc55xx_cache_aligned_size( in, (size_t) n); if (n_c > EDMA_TCD_BITER_LINKED_SIZE) { RTEMS_SYSLOG_WARNING( "buffer size out of range, cannot use eDMA\n"); n_nc = n; n_c = 0; } else if (n_nc + n_c != n) { RTEMS_SYSLOG_WARNING( "input buffer not proper cache aligned, cannot use eDMA\n"); n_nc = n; n_c = 0; } } #ifdef DEBUG if (e->regs->SR.B.TXCTR != e->regs->SR.B.RXCTR) { RTEMS_SYSLOG_WARNING( "FIFO counter not equal\n"); } #endif /* DEBUG */ /* Direct IO */ if (out == NULL) { push_data.B.TXDATA = e->idle_char; while (r < n_nc || w < n_nc) { /* Wait for available FIFO */ do { sr.R = status->R; } while (sr.B.TXCTR == MPC55XX_DSPI_FIFO_SIZE && sr.B.RXCTR == 0); /* Write */ if (w < n_nc && (w - r) < MPC55XX_DSPI_FIFO_SIZE && sr.B.TXCTR != MPC55XX_DSPI_FIFO_SIZE) { ++w; ppc_write_word( push_data.R, push); } /* Read */ if (r < n_nc && sr.B.RXCTR != 0) { pop_data.R = ppc_read_word( pop); in [r] = (unsigned char) pop_data.B.RXDATA; ++r; } } } else if (in == NULL) { while (r < n_nc || w < n_nc) { /* Wait for available FIFO */ do { sr.R = status->R; } while (sr.B.TXCTR == MPC55XX_DSPI_FIFO_SIZE && sr.B.RXCTR == 0); /* Write */ if (w < n_nc && (w - r) < MPC55XX_DSPI_FIFO_SIZE && sr.B.TXCTR != MPC55XX_DSPI_FIFO_SIZE) { push_data.B.TXDATA = out [w]; ++w; ppc_write_word( push_data.R, push); } /* Read */ if (r < n_nc && sr.B.RXCTR != 0) { pop_data.R = ppc_read_word( pop); ++r; } } } else { while (r < n_nc || w < n_nc) { /* Wait for available FIFO */ do { sr.R = status->R; } while (sr.B.TXCTR == MPC55XX_DSPI_FIFO_SIZE && sr.B.RXCTR == 0); /* Write */ if (w < n_nc && (w - r) < MPC55XX_DSPI_FIFO_SIZE && sr.B.TXCTR != MPC55XX_DSPI_FIFO_SIZE) { push_data.B.TXDATA = out [w]; ++w; ppc_write_word( push_data.R, push); } /* Read */ if (r < n_nc && sr.B.RXCTR != 0) { pop_data.R = ppc_read_word( pop); in [r] = (unsigned char) pop_data.B.RXDATA; ++r; } } } /* eDMA transfers */ if (n_c > 0) { rtems_status_code sc = RTEMS_SUCCESSFUL; unsigned char *in_c = in + n_nc; const unsigned char *out_c = out + n_nc; struct tcd_t tcd_transmit = EDMA_TCD_DEFAULT; struct tcd_t tcd_receive = EDMA_TCD_DEFAULT; /* Cache operations */ rtems_cache_flush_multiple_data_lines( out_c, (size_t) n_c); rtems_cache_invalidate_multiple_data_lines( in_c, (size_t) n_c); /* Set transmit TCD */ if (out == NULL) { e->push_data.B.TXDATA = e->idle_char; mpc55xx_dspi_store_push_data( e); tcd_transmit.SADDR = mpc55xx_dspi_push_data_address( e); tcd_transmit.SDF.B.SSIZE = 2; tcd_transmit.SDF.B.SOFF = 0; tcd_transmit.DADDR = (uint32_t) push; tcd_transmit.SDF.B.DSIZE = 2; tcd_transmit.CDF.B.DOFF = 0; tcd_transmit.NBYTES = 4; tcd_transmit.CDF.B.CITER = n_c; tcd_transmit.BMF.B.BITER = n_c; } else { EDMA.CDSBR.R = e->edma_transmit.channel; tcd_transmit.SADDR = (uint32_t) out_c; tcd_transmit.SDF.B.SSIZE = 0; tcd_transmit.SDF.B.SOFF = 1; tcd_transmit.DADDR = mpc55xx_dspi_push_data_address( e) + 3; tcd_transmit.SDF.B.DSIZE = 0; tcd_transmit.CDF.B.DOFF = 0; tcd_transmit.NBYTES = 1; tcd_transmit.CDF.B.CITERE_LINK = 1; tcd_transmit.BMF.B.BITERE_LINK = 1; tcd_transmit.BMF.B.MAJORLINKCH = e->edma_push.channel; tcd_transmit.CDF.B.CITER = EDMA_TCD_LINK_AND_BITER( e->edma_push.channel, n_c); tcd_transmit.BMF.B.BITER = EDMA_TCD_LINK_AND_BITER( e->edma_push.channel, n_c); tcd_transmit.BMF.B.MAJORE_LINK = 1; } tcd_transmit.BMF.B.D_REQ = 1; tcd_transmit.BMF.B.INT_MAJ = 1; EDMA.TCD [e->edma_transmit.channel] = tcd_transmit; /* Set receive TCD */ if (in == NULL) { tcd_receive.CDF.B.DOFF = 0; tcd_receive.DADDR = mpc55xx_dspi_nirvana_address( e); } else { tcd_receive.CDF.B.DOFF = 1; tcd_receive.DADDR = (uint32_t) in_c; } tcd_receive.SADDR = (uint32_t) pop + 3; tcd_receive.SDF.B.SSIZE = 0; tcd_receive.SDF.B.SOFF = 0; tcd_receive.SDF.B.DSIZE = 0; tcd_receive.NBYTES = 1; tcd_receive.BMF.B.D_REQ = 1; tcd_receive.BMF.B.INT_MAJ = 1; tcd_receive.CDF.B.CITER = n_c; tcd_receive.BMF.B.BITER = n_c; EDMA.TCD [e->edma_receive.channel] = tcd_receive; /* Clear request flags */ sr.R = 0; sr.B.TFFF = 1; sr.B.RFDF = 1; status->R = sr.R; /* Enable hardware requests */ mpc55xx_edma_enable_hardware_requests( e->edma_receive.channel, true); mpc55xx_edma_enable_hardware_requests( e->edma_transmit.channel, true); /* Wait for transmit update */ sc = rtems_semaphore_obtain( e->edma_transmit.id, RTEMS_WAIT, RTEMS_NO_TIMEOUT); RTEMS_CHECK_SC_RV( sc, "transmit update"); /* Wait for receive update */ sc = rtems_semaphore_obtain( e->edma_receive.id, RTEMS_WAIT, RTEMS_NO_TIMEOUT); RTEMS_CHECK_SC_RV( sc, "receive update"); } return n; }
/* * FIXME: Should cbuf be static? It could be if we put the mutex * around the entire body of this routine. Then we wouldn't * have to worry about blowing stacks with a local variable * that large. Could make cbuf bigger, too. */ void vsyslog (int pri, const char *fmt, va_list ap) { int cnt; char *cp; char *msgp, cbuf[200]; int sent; if (pri & ~(LOG_PRIMASK|LOG_FACMASK)) { syslog (LOG_ERR|LOG_CONS|LOG_PERROR|LOG_PID, "syslog: unknown facility/priority: %#x", pri); pri &= LOG_PRIMASK|LOG_FACMASK; } if (!(LOG_MASK(LOG_PRI(pri)) & LogMask)) return; if ((pri & LOG_FACMASK) == 0) pri |= LogFacility; cnt = sprintf (cbuf, "<%d>", pri); cp = msgp = cbuf + cnt; if (LogTag) { const char *lp = LogTag; while ((*cp = *lp++) != '\0') cp++; } if (LogStatus & LOG_PID) { rtems_id tid; rtems_task_ident (RTEMS_SELF, 0, &tid); cnt = sprintf (cp, "[%#lx]", (unsigned long)tid); cp += cnt; } if (LogTag) { *cp++ = ':'; *cp++ = ' '; } cnt = vsprintf (cp, fmt, ap); cnt += cp - cbuf; if (cbuf[cnt-1] == '\n') cbuf[--cnt] = '\0'; if (LogStatus & LOG_PERROR) printf ("%s\n", cbuf); /* * Grab the mutex */ sent = 0; if ((rtems_bsdnet_log_host_address.s_addr != INADDR_ANY) && (LogFd >= 0) && (rtems_semaphore_obtain (LogSemaphore, RTEMS_WAIT, RTEMS_NO_TIMEOUT) == RTEMS_SUCCESSFUL)) { /* * Set the destination address/port */ struct sockaddr_in farAddress; farAddress.sin_family = AF_INET; farAddress.sin_port = htons (SYSLOG_PORT); farAddress.sin_addr = rtems_bsdnet_log_host_address; memset (farAddress.sin_zero, '\0', sizeof farAddress.sin_zero); /* * Send the message */ if (sendto (LogFd, cbuf, cnt, 0, (struct sockaddr *)&farAddress, sizeof farAddress) >= 0) sent = 1; rtems_semaphore_release (LogSemaphore); } if (!sent && (LogStatus & LOG_CONS) && !(LogStatus & LOG_PERROR)) printf ("%s\n", msgp); }
/* msdos_eval4make -- * The following routine evaluate path for a new node to be created. * 'pathloc' is returned with a pointer to the parent of the new node. * 'name' is returned with a pointer to the first character in the * new node name. The parent node is verified to be a directory. * * PARAMETERS: * path - path for evaluation * pathloc - IN/OUT (start point for evaluation/parent directory for * creation) * name - new node name * * RETURNS: * RC_OK, filled pathloc for parent directory and name of new node on * success, or -1 if error occured (errno set appropriately) */ int msdos_eval4make( const char *path, rtems_filesystem_location_info_t *pathloc, const char **name ) { int rc = RC_OK; rtems_status_code sc = RTEMS_SUCCESSFUL; msdos_fs_info_t *fs_info = pathloc->mt_entry->fs_info; fat_file_fd_t *fat_fd = NULL; rtems_filesystem_location_info_t newloc; msdos_token_types_t type; int i = 0; int token_len; const char *token; bool done = false; sc = rtems_semaphore_obtain(fs_info->vol_sema, RTEMS_WAIT, MSDOS_VOLUME_SEMAPHORE_TIMEOUT); if (sc != RTEMS_SUCCESSFUL) rtems_set_errno_and_return_minus_one(EIO); if (!pathloc->node_access) { errno = ENOENT; rc = -1; goto err; } fat_fd = pathloc->node_access; rc = fat_file_reopen(fat_fd); if (rc != RC_OK) goto err; while (!done) { type = msdos_get_token(&path[i], strlen(&path[i]), &token, &token_len); i += token_len; fat_fd = pathloc->node_access; switch (type) { case MSDOS_UP_DIR: /* * Only a directory can be decended into. */ if (fat_fd->fat_file_type != FAT_DIRECTORY) { errno = ENOTDIR; rc = -1; goto error; } /* * Am I at the root of this mounted filesystem? */ if (pathloc->node_access == pathloc->mt_entry->mt_fs_root.node_access) { /* * Am I at the root of all filesystems? * XXX: MSDOS is not supposed to be base fs. */ if (pathloc->node_access == rtems_filesystem_root.node_access) { break; /* Throw out the .. in this case */ } else { newloc = pathloc->mt_entry->mt_point_node; *pathloc = newloc; rc = fat_file_close(pathloc->mt_entry, fat_fd); if (rc != RC_OK) goto err; rtems_semaphore_release(fs_info->vol_sema); return (*pathloc->ops->evalformake_h)(&path[i-token_len], pathloc, name); } } else { rc = msdos_find_name(pathloc, token, token_len); if (rc != RC_OK) { if (rc == MSDOS_NAME_NOT_FOUND_ERR) { errno = ENOENT; rc = -1; } goto error; } } break; case MSDOS_NAME: /* * Only a directory can be decended into. */ if (fat_fd->fat_file_type != FAT_DIRECTORY) { errno = ENOTDIR; rc = -1; goto error; } /* * Otherwise find the token name in the present location and * set the node access to the point we have found. */ rc = msdos_find_name(pathloc, token, token_len); if (rc) { if (rc != MSDOS_NAME_NOT_FOUND_ERR) { errno = ENOENT; rc = -1; goto error; } else done = true; } break; case MSDOS_NO_MORE_PATH: errno = EEXIST; rc = -1; goto error; break; case MSDOS_CURRENT_DIR: break; case MSDOS_INVALID_TOKEN: errno = ENAMETOOLONG; rc = -1; goto error; break; } } *name = &path[i - token_len]; /* * We have evaluated the path as far as we can. * Verify there is not any invalid stuff at the end of the name. */ for( ; path[i] != '\0'; i++) { if (!msdos_is_separator(path[i])) { errno = ENOENT; rc = -1; goto error; } } fat_fd = pathloc->node_access; if (fat_fd->fat_file_type != FAT_DIRECTORY) { errno = ENOTDIR; rc = -1; goto error; } msdos_set_handlers(pathloc); rtems_semaphore_release(fs_info->vol_sema); return RC_OK; error: fat_file_close(pathloc->mt_entry, fat_fd); err: rtems_semaphore_release(fs_info->vol_sema); return rc; }
/*=========================================================================*\ | Function: | \*-------------------------------------------------------------------------*/ static int m360_spi_wait ( /*-------------------------------------------------------------------------*\ | Purpose: | | wait for spi to become idle | +---------------------------------------------------------------------------+ | Input Parameters: | \*-------------------------------------------------------------------------*/ m360_spi_softc_t *softc_ptr /* handle */ ) /*-------------------------------------------------------------------------*\ | Return Value: | | o = ok or error code | \*=========================================================================*/ { uint16_t act_status; rtems_status_code rc; uint32_t tout; #if defined(DEBUG) printk("m360_spi_wait called... "); #endif if (softc_ptr->initialized) { /* * allow interrupts, when receiver is not empty */ m360.spim = (M360_SPIE_TXE | M360_SPIE_TXB | M360_SPIE_BSY | M360_SPIE_MME); rc = rtems_semaphore_obtain(softc_ptr->irq_sema_id, RTEMS_WAIT, RTEMS_NO_TIMEOUT); if (rc != RTEMS_SUCCESSFUL) { return rc; } } else { tout = 0; do { if (tout++ > 1000000) { #if defined(DEBUG) printk("... exit with RTEMS_TIMEOUT\r\n"); #endif return RTEMS_TIMEOUT; } /* * wait for SPI to terminate */ } while (!(m360.spie & M360_SPIE_TXB)); } act_status = m360.spie; if ((act_status & (M360_SPIE_TXE | M360_SPIE_TXB | M360_SPIE_BSY | M360_SPIE_MME))!= M360_SPIE_TXB) { #if defined(DEBUG) printk("... exit with RTEMS_IO_ERROR," "act_status=0x%04x,mask=0x%04x,desired_status=0x%04x\r\n", act_status,status_mask,desired_status); #endif return RTEMS_IO_ERROR; } #if defined(DEBUG) printk("... exit OK\r\n"); #endif return RTEMS_SUCCESSFUL; }
/*--------------------------------------------------------------------------------------- Name: OS_mkfs Purpose: Makes a RAM disk on the target with the RTEMS RFS file system Returns: OS_FS_ERR_INVALID_POINTER if devname is NULL OS_FS_ERR_DRIVE_NOT_CREATED if the OS calls to create the the drive failed OS_FS_ERR_DEVICE_NOT_FREE if the volume table is full OS_FS_SUCCESS on creating the disk Note: if address == 0, then a malloc will be called to create the disk ---------------------------------------------------------------------------------------*/ int32 OS_mkfs (char *address, char *devname,char * volname, uint32 blocksize, uint32 numblocks) { int i; uint32 ReturnCode; rtems_rfs_format_config config; rtems_status_code rtems_sc; /* ** Check parameters */ if ( devname == NULL || volname == NULL ) { return OS_FS_ERR_INVALID_POINTER; } /* ** Lock */ rtems_sc = rtems_semaphore_obtain (OS_VolumeTableSem, RTEMS_WAIT, RTEMS_NO_TIMEOUT); /* find an open entry in the Volume Table */ for (i = 0; i < NUM_TABLE_ENTRIES; i++) { if (OS_VolumeTable[i].FreeFlag == TRUE && OS_VolumeTable[i].IsMounted == FALSE && strcmp(OS_VolumeTable[i].DeviceName, devname) == 0) break; } if (i >= NUM_TABLE_ENTRIES) { rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return OS_FS_ERR_DEVICE_NOT_FREE; } /* ** Create the RAM disk and format it with the RFS file system. ** This requires RTEMS 4.10 */ if (OS_VolumeTable[i].VolumeType == RAM_DISK) { /* ** Create the RAM disk device */ ReturnCode = rtems_setup_ramdisk (OS_VolumeTable[i].PhysDevName, (uint32 *)address, blocksize, numblocks); if ( ReturnCode == OS_FS_ERROR ) { ReturnCode = OS_FS_ERR_DRIVE_NOT_CREATED; } else { /* ** Format the RAM disk with the RFS file system */ memset (&config, 0, sizeof(rtems_rfs_format_config)); if ( rtems_rfs_format ( OS_VolumeTable[i].PhysDevName, &config ) < 0 ) { printf("OSAL: Error: RFS format of %s failed: %s\n", OS_VolumeTable[i].PhysDevName, strerror(errno)); ReturnCode = OS_FS_ERR_DRIVE_NOT_CREATED; } else { /* ** Success */ OS_VolumeTable[i].FreeFlag = FALSE; strcpy(OS_VolumeTable[i].VolumeName, volname); OS_VolumeTable[i].BlockSize = blocksize; ReturnCode = OS_FS_SUCCESS; } } } else if (OS_VolumeTable[i].VolumeType == FS_BASED) { /* ** FS_BASED will map the OSAL Volume to an already mounted host filesystem */ /* ** Enter the info in the table */ OS_VolumeTable[i].FreeFlag = FALSE; strcpy(OS_VolumeTable[i].VolumeName, volname); OS_VolumeTable[i].BlockSize = blocksize; ReturnCode = OS_FS_SUCCESS; } else { /* ** The VolumeType is something else that is not supported right now */ ReturnCode = OS_FS_ERROR; } /* ** Unlock */ rtems_sc = rtems_semaphore_release (OS_VolumeTableSem); return ReturnCode; } /* end OS_mkfs */