##// END OF EJS Templates
Creation of a spool task (SPOO) to handle
Creation of a spool task (SPOO) to handle

File last commit:

r165:c9daaae78ba2 spool
r165:c9daaae78ba2 spool
Show More
fsw_spool.c
276 lines | 10.4 KiB | text/x-c | CLexer
/** Functions and tasks related to waveform packet generation.
*
* @file
* @author P. LEROY
*
* A group of functions to handle waveforms, in snapshot or continuous format.\n
*
*/
#include "fsw_spool.h"
//*********************
// Interrupt SubRoutine
void spool_waveforms( void )
{
/** This is the interrupt sub routine called by the waveform picker core.
*
* This ISR launch different actions depending mainly on two pieces of information:
* 1. the values read in the registers of the waveform picker.
* 2. the current LFR mode.
*
*/
rtems_status_code status;
if ( (lfrCurrentMode == LFR_MODE_NORMAL) || (lfrCurrentMode == LFR_MODE_BURST) // in BURST the data are used to place v, e1 and e2 in the HK packet
|| (lfrCurrentMode == LFR_MODE_SBM1) || (lfrCurrentMode == LFR_MODE_SBM2) )
{ // in modes other than STANDBY and BURST, send the CWF_F3 data
if ((waveform_picker_regs->status & 0x08) == 0x08){ // [1000] f3 is full
// (1) change the receiving buffer for the waveform picker
ring_node_to_send_cwf_f3 = current_ring_node_f3;
current_ring_node_f3 = current_ring_node_f3->next;
waveform_picker_regs->addr_data_f3 = current_ring_node_f3->buffer_address;
// (2) send an event for the waveforms transmission
if (rtems_event_send( Task_id[TASKID_CWF3], RTEMS_EVENT_0 ) != RTEMS_SUCCESSFUL) {
rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_2 );
}
rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_2);
waveform_picker_regs->status = waveform_picker_regs->status & 0xfffff777; // reset f3 bits to 0, [1111 0111 0111 0111]
}
}
switch(lfrCurrentMode)
{
//********
// STANDBY
case(LFR_MODE_STANDBY):
break;
//******
// NORMAL
case(LFR_MODE_NORMAL):
if ( (waveform_picker_regs->status & 0xff8) != 0x00) // [1000] check the error bits
{
rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_2 );
}
if ( (waveform_picker_regs->status & 0x07) == 0x07) // [0111] check the f2, f1, f0 full bits
{
// change F0 ring node
ring_node_to_send_swf_f0 = current_ring_node_f0;
current_ring_node_f0 = current_ring_node_f0->next;
waveform_picker_regs->addr_data_f0 = current_ring_node_f0->buffer_address;
// change F1 ring node
ring_node_to_send_swf_f1 = current_ring_node_f1;
current_ring_node_f1 = current_ring_node_f1->next;
waveform_picker_regs->addr_data_f1 = current_ring_node_f1->buffer_address;
// change F2 ring node
ring_node_to_send_swf_f2 = current_ring_node_f2;
current_ring_node_f2 = current_ring_node_f2->next;
waveform_picker_regs->addr_data_f2 = current_ring_node_f2->buffer_address;
//
if (rtems_event_send( Task_id[TASKID_WFRM], RTEMS_EVENT_MODE_NORMAL ) != RTEMS_SUCCESSFUL)
{
rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_2 );
}
waveform_picker_regs->status = waveform_picker_regs->status & 0xfffff888; // [1000 1000 1000]
}
break;
//******
// BURST
case(LFR_MODE_BURST):
if ( (waveform_picker_regs->status & 0x04) == 0x04 ){ // [0100] check the f2 full bit
// (1) change the receiving buffer for the waveform picker
ring_node_to_send_cwf_f2 = current_ring_node_f2;
current_ring_node_f2 = current_ring_node_f2->next;
waveform_picker_regs->addr_data_f2 = current_ring_node_f2->buffer_address;
// (2) send an event for the waveforms transmission
if (rtems_event_send( Task_id[TASKID_CWF2], RTEMS_EVENT_MODE_BURST ) != RTEMS_SUCCESSFUL) {
rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_2 );
}
waveform_picker_regs->status = waveform_picker_regs->status & 0xfffffbbb; // [1111 1011 1011 1011] f2 bit = 0
}
break;
//*****
// SBM1
case(LFR_MODE_SBM1):
if ( (waveform_picker_regs->status & 0x02) == 0x02 ) { // [0010] check the f1 full bit
// (1) change the receiving buffer for the waveform picker
ring_node_to_send_cwf_f1 = current_ring_node_f1;
current_ring_node_f1 = current_ring_node_f1->next;
waveform_picker_regs->addr_data_f1 = current_ring_node_f1->buffer_address;
// (2) send an event for the the CWF1 task for transmission (and snapshot extraction if needed)
status = rtems_event_send( Task_id[TASKID_CWF1], RTEMS_EVENT_MODE_SBM1 );
waveform_picker_regs->status = waveform_picker_regs->status & 0xfffffddd; // [1111 1101 1101 1101] f1 bits = 0
}
if ( (waveform_picker_regs->status & 0x01) == 0x01 ) { // [0001] check the f0 full bit
swf_f0_ready = true;
waveform_picker_regs->status = waveform_picker_regs->status & 0xfffffeee; // [1111 1110 1110 1110] f0 bits = 0
}
if ( (waveform_picker_regs->status & 0x04) == 0x04 ) { // [0100] check the f2 full bit
swf_f2_ready = true;
waveform_picker_regs->status = waveform_picker_regs->status & 0xfffffbbb; // [1111 1011 1011 1011] f2 bits = 0
}
break;
//*****
// SBM2
case(LFR_MODE_SBM2):
if ( (waveform_picker_regs->status & 0x04) == 0x04 ){ // [0100] check the f2 full bit
// (1) change the receiving buffer for the waveform picker
ring_node_to_send_cwf_f2 = current_ring_node_f2;
current_ring_node_f2 = current_ring_node_f2->next;
waveform_picker_regs->addr_data_f2 = current_ring_node_f2->buffer_address;
// (2) send an event for the waveforms transmission
status = rtems_event_send( Task_id[TASKID_CWF2], RTEMS_EVENT_MODE_SBM2 );
waveform_picker_regs->status = waveform_picker_regs->status & 0xfffffbbb; // [1111 1011 1011 1011] f2 bit = 0
}
if ( (waveform_picker_regs->status & 0x01) == 0x01 ) { // [0001] check the f0 full bit
swf_f0_ready = true;
waveform_picker_regs->status = waveform_picker_regs->status & 0xfffffeee; // [1111 1110 1110 1110] f0 bits = 0
}
if ( (waveform_picker_regs->status & 0x02) == 0x02 ) { // [0010] check the f1 full bit
swf_f1_ready = true;
waveform_picker_regs->status = waveform_picker_regs->status & 0xfffffddd; // [1111 1101 1101 1101] f1, f0 bits = 0
}
break;
//********
// DEFAULT
default:
break;
}
}
void spool_waveforms_alt( void )
{
// WFRM
if (wake_up_task_wfrm == true)
{
rtems_event_send( Task_id[TASKID_WFRM], RTEMS_EVENT_MODE_NORMAL );
wake_up_task_wfrm = false;
}
// CWF_F1
if (wake_up_task_cwf_f1 == true)
{
rtems_event_send( Task_id[TASKID_CWF1], RTEMS_EVENT_MODE_SBM1 );
wake_up_task_cwf_f1 = false;
}
// CWF_F2 BURST
if (wake_up_task_cwf_f2_burst == true)
{
rtems_event_send( Task_id[TASKID_CWF2], RTEMS_EVENT_MODE_BURST );
wake_up_task_cwf_f2_burst = false;
}
// CWF_F2 SBM2
if (wake_up_task_cwf_f2_sbm2 == true)
{
rtems_event_send( Task_id[TASKID_CWF2], RTEMS_EVENT_MODE_SBM2 );
wake_up_task_cwf_f2_sbm2 = false;
}
// CWF_F3
if (wake_up_task_cwf_f3 == true)
{
rtems_event_send( Task_id[TASKID_CWF3], RTEMS_EVENT_0 );
wake_up_task_cwf_f3 = false;
}
}
void spool_spectral_matrices( void )
{
// STATUS REGISTER
// input_fifo_write(2) *** input_fifo_write(1) *** input_fifo_write(0)
// 10 9 8
// buffer_full ** bad_component_err ** f2_1 ** f2_0 ** f1_1 ** f1_0 ** f0_1 ** f0_0
// 7 6 5 4 3 2 1 0
unsigned char status_f0;
unsigned char status_f1;
unsigned char status_f2;
static unsigned int counter = 0;
rtems_interrupt_level level;
rtems_interrupt_disable( level );
status_f0 = spectral_matrix_regs->status & 0x03; // [0011] get the status_ready_matrix_f0_x bits
status_f1 = (spectral_matrix_regs->status & 0x0c) >> 2; // [0011] get the status_ready_matrix_f0_x bits
status_f2 = (spectral_matrix_regs->status & 0x30) >> 4; // [0011] get the status_ready_matrix_f0_x bits
// if ( status_f0 == 0x03)
// {
// printf("%d \n", counter);
// }
if ( status_f1 == 0x03)
{
printf("f1 %d \n", counter);
}
if ( status_f2 == 0x03)
{
printf("f2 %d \n", counter);
}
spectral_matrices_isr_f0();
spectral_matrices_isr_f1();
spectral_matrices_isr_f2();
spectral_matrix_isr_error_handler();
rtems_interrupt_enable( level );
counter = counter + 1;
}
//************
// RTEMS TASKS
rtems_task spoo_task(rtems_task_argument argument)
{
rtems_status_code status;
BOOT_PRINTF("in SPOOL ***\n")
if (rtems_rate_monotonic_ident( name_spool_rate_monotonic, &spool_period_id) != RTEMS_SUCCESSFUL) {
status = rtems_rate_monotonic_create( name_spool_rate_monotonic, &spool_period_id );
if( status != RTEMS_SUCCESSFUL ) {
PRINTF1( "in SPOO *** rtems_rate_monotonic_create failed with status %d\n", status )
}
}
status = rtems_rate_monotonic_cancel( spool_period_id );
if( status != RTEMS_SUCCESSFUL )
{
PRINTF1( "ERR *** in SPOOL *** rtems_rate_monotonic_cancel(spool_period_id) ***code: %d\n", status )
}
else
{
DEBUG_PRINTF("OK *** in SPOOL *** rtems_rate_monotonic_cancel(spool_period_id)\n")
}
while(1){ // launch the rate monotonic task
// status = rtems_rate_monotonic_period( spool_period_id, SPOOL_TIMEOUT_in_ticks );
rtems_task_wake_after( SPOOL_TIMEOUT_in_ticks / 2 );
spool_waveforms_alt();
spool_spectral_matrices();
// if ( status != RTEMS_SUCCESSFUL )
// {
// PRINTF1( "in SPOOL *** ERR period: %d\n", status);
// }
// else
// {
// spool_waveforms();
// spool_spectral_matrices();
// }
}
PRINTF("in SPOOL *** deleting task\n")
status = rtems_task_delete( RTEMS_SELF ); // should not return
printf( "rtems_task_delete returned with status of %d.\n", status );
return;
}