diff --git a/FSW-qt/Makefile b/FSW-qt/Makefile --- a/FSW-qt/Makefile +++ b/FSW-qt/Makefile @@ -1,6 +1,6 @@ ############################################################################# # Makefile for building: bin/fsw -# Generated by qmake (2.01a) (Qt 4.8.5) on: Tue Mar 4 13:06:39 2014 +# Generated by qmake (2.01a) (Qt 4.8.5) on: Tue Mar 11 15:58:37 2014 # Project: fsw-qt.pro # Template: app # Command: /usr/bin/qmake-qt4 -spec /usr/lib64/qt4/mkspecs/linux-g++ -o Makefile fsw-qt.pro @@ -10,7 +10,7 @@ CC = sparc-rtems-gcc CXX = sparc-rtems-g++ -DEFINES = -DSW_VERSION_N1=1 -DSW_VERSION_N2=0 -DSW_VERSION_N3=0 -DSW_VERSION_N4=3 -DPRINT_MESSAGES_ON_CONSOLE +DEFINES = -DSW_VERSION_N1=1 -DSW_VERSION_N2=0 -DSW_VERSION_N3=0 -DSW_VERSION_N4=3 -DPRINT_MESSAGES_ON_CONSOLE -DDEBUG_MESSAGES CFLAGS = -pipe -O3 -Wall $(DEFINES) CXXFLAGS = -pipe -O3 -Wall $(DEFINES) INCPATH = -I/usr/lib64/qt4/mkspecs/linux-g++ -I. -I../src -I../header -I../../LFR_basic-parameters diff --git a/FSW-qt/fsw-qt.pro b/FSW-qt/fsw-qt.pro --- a/FSW-qt/fsw-qt.pro +++ b/FSW-qt/fsw-qt.pro @@ -1,7 +1,7 @@ TEMPLATE = app # CONFIG += console v8 sim -# CONFIG options = verbose *** boot_messages *** debug_messages *** cpu_usage_report *** stack_report -CONFIG += console verbose +# CONFIG options = verbose *** boot_messages *** debug_messages *** cpu_usage_report *** stack_report *** vhdl_dev +CONFIG += console verbose debug_messages CONFIG -= qt include(./sparc.pri) @@ -13,6 +13,10 @@ DEFINES += SW_VERSION_N2=0 # minor DEFINES += SW_VERSION_N3=0 # patch DEFINES += SW_VERSION_N4=3 # internal +contains( CONFIG, vhdl_dev ) { + DEFINES += VHDL_DEV +} + contains( CONFIG, verbose ) { DEFINES += PRINT_MESSAGES_ON_CONSOLE } diff --git a/FSW-qt/fsw-qt.pro.user b/FSW-qt/fsw-qt.pro.user --- a/FSW-qt/fsw-qt.pro.user +++ b/FSW-qt/fsw-qt.pro.user @@ -1,6 +1,6 @@ - + ProjectExplorer.Project.ActiveTarget diff --git a/header/fsw_params.h b/header/fsw_params.h --- a/header/fsw_params.h +++ b/header/fsw_params.h @@ -35,9 +35,6 @@ typedef struct ring_node #define NB_RING_NODES_F0 3 // AT LEAST 3 #define NB_RING_NODES_F1 5 // AT LEAST 3 #define NB_RING_NODES_F2 5 // AT LEAST 3 -#define NB_RING_NODES_ASM_F0 12 // AT LEAST 3 -#define NB_RING_NODES_ASM_F1 2 // AT LEAST 3 -#define NB_RING_NODES_ASM_F2 2 // AT LEAST 3 //********** // LFR MODES @@ -107,8 +104,14 @@ typedef struct ring_node #define REGS_ADDR_GPTIMER 0x80000300 #define REGS_ADDR_GRSPW 0x80000500 #define REGS_ADDR_TIME_MANAGEMENT 0x80000600 + +#ifdef VHDL_DEV +#define REGS_ADDR_SPECTRAL_MATRIX 0x80000f00 +#define REGS_ADDR_WAVEFORM_PICKER 0x80000f40 +#else #define REGS_ADDR_SPECTRAL_MATRIX 0x80000f00 #define REGS_ADDR_WAVEFORM_PICKER 0x80000f20 +#endif #define APBUART_CTRL_REG_MASK_DB 0xfffff7ff #define APBUART_CTRL_REG_MASK_TE 0x00000002 @@ -161,9 +164,9 @@ typedef struct ring_node #define TASK_PRIORITY_HOUS 30 #define TASK_PRIORITY_CWF1 35 // CWF1 and CWF2 are never running together #define TASK_PRIORITY_CWF2 35 // +#define TASK_PRIORITY_SWBD 37 // SWBD has a lower priority than WFRM, this is to extract the snapshot before sending it #define TASK_PRIORITY_WFRM 40 #define TASK_PRIORITY_CWF3 40 // there is a printf in this function, be careful with its priority wrt CWF1 -#define TASK_PRIORITY_SWBD 40 #define TASK_PRIORITY_SEND 45 #define TASK_PRIORITY_RECV 50 #define TASK_PRIORITY_ACTN 50 diff --git a/header/fsw_params_processing.h b/header/fsw_params_processing.h --- a/header/fsw_params_processing.h +++ b/header/fsw_params_processing.h @@ -1,10 +1,13 @@ #ifndef FSW_PARAMS_PROCESSING_H #define FSW_PARAMS_PROCESSING_H -#define NB_BINS_PER_SM 128 // -#define NB_VALUES_PER_SM 25 // -#define TOTAL_SIZE_SM 3200 // 25 * 128 -#define SM_HEADER 0 // +#define NB_BINS_PER_SM 128 +#define NB_VALUES_PER_SM 25 +#define TOTAL_SIZE_SM 3200 // 25 * 128 +// +#define NB_RING_NODES_ASM_F0 12 // AT LEAST 3 +#define NB_RING_NODES_ASM_F1 2 // AT LEAST 3 +#define NB_RING_NODES_ASM_F2 2 // AT LEAST 3 // #define NB_BINS_PER_ASM_F0 88 #define NB_BINS_PER_PKT_ASM_F0 44 diff --git a/header/fsw_processing.h b/header/fsw_processing.h --- a/header/fsw_processing.h +++ b/header/fsw_processing.h @@ -12,9 +12,9 @@ #include "fsw_spacewire.h" #include "basic_parameters.h" -extern volatile int sm_f0[ ][ TIME_OFFSET + TOTAL_SIZE_SM ]; -extern volatile int sm_f1[ ][ TIME_OFFSET + TOTAL_SIZE_SM ]; -extern volatile int sm_f2[ ][ TIME_OFFSET + TOTAL_SIZE_SM ]; +extern volatile int sm_f0[ ]; +extern volatile int sm_f1[ ]; +extern volatile int sm_f2[ ]; // parameters extern struct param_local_str param_local; diff --git a/header/grlib_regs.h b/header/grlib_regs.h --- a/header/grlib_regs.h +++ b/header/grlib_regs.h @@ -81,6 +81,15 @@ typedef struct { volatile int matrixFO_Address1; volatile int matrixF1_Address; volatile int matrixF2_Address; + volatile int coarse_time_F0_0; + volatile int coarse_time_F0_1; + volatile int coarse_time_F1; + volatile int coarse_time_F2; + volatile int fine_time_FO_0; + volatile int fine_time_F0_1; + volatile int fine_time_F1; + volatile int fine_time_F2; + volatile int debug; } spectral_matrix_regs_t; #endif // GRLIB_REGS_H_INCLUDED diff --git a/header/tc_handler.h b/header/tc_handler.h --- a/header/tc_handler.h +++ b/header/tc_handler.h @@ -39,8 +39,8 @@ int restart_science_tasks(); int suspend_science_tasks(); void launch_waveform_picker( unsigned char mode ); void launch_spectral_matrix( unsigned char mode ); -void enable_irq_on_new_ready_matrix( void ); -void disable_irq_on_new_ready_matrix( void ); +void set_irq_on_new_ready_matrix(unsigned char value ); +void set_run_matrix_spectral( unsigned char value ); void launch_spectral_matrix_simu( unsigned char mode ); // other functions diff --git a/header/wf_handler.h b/header/wf_handler.h --- a/header/wf_handler.h +++ b/header/wf_handler.h @@ -42,6 +42,7 @@ extern unsigned char lfrCurrentMode; //********** // RTEMS_ISR +void reset_extractSWF( void ); rtems_isr waveforms_isr( rtems_vector_number vector ); //*********** @@ -69,7 +70,8 @@ int send_waveform_CWF3_light( volatile i // void compute_acquisition_time(unsigned int coarseTime, unsigned int fineTime, unsigned int sid, unsigned char pa_lfr_pkt_nr, unsigned char *acquisitionTime ); -void build_snapshot_from_ring( void ); +void build_snapshot_from_ring(ring_node *ring_node_to_send , unsigned char frequencyChannel ); +void build_acquisition_time( unsigned long long int * acquisitionTimeAslong, ring_node *current_ring_node ); // rtems_id get_pkts_queue_id( void ); diff --git a/src/fsw_globals.c b/src/fsw_globals.c --- a/src/fsw_globals.c +++ b/src/fsw_globals.c @@ -46,9 +46,10 @@ volatile int wf_cont_f3_b [ (NB_SAMPL char wf_cont_f3_light[ (NB_SAMPLES_PER_SNAPSHOT) * NB_BYTES_CWF3_LIGHT_BLK + TIME_OFFSET_IN_BYTES ] __attribute__((aligned(0x100))); // SPECTRAL MATRICES GLOBAL VARIABLES -volatile int sm_f0[ NB_RING_NODES_ASM_F0 ][ TIME_OFFSET + TOTAL_SIZE_SM + 62 ] __attribute__((aligned(0x100))); -volatile int sm_f1[ NB_RING_NODES_ASM_F1 ][ TIME_OFFSET + TOTAL_SIZE_SM + 62 ] __attribute__((aligned(0x100))); -volatile int sm_f2[ NB_RING_NODES_ASM_F2 ][ TIME_OFFSET + TOTAL_SIZE_SM + 62 ] __attribute__((aligned(0x100))); +// alignment constraints for the spectral matrices buffers => the first data after the time (8 bytes) shall be aligned on 0x00 +volatile int sm_f0[ NB_RING_NODES_ASM_F0 * TOTAL_SIZE_SM ] __attribute__((aligned(0x100))); +volatile int sm_f1[ NB_RING_NODES_ASM_F1 * TOTAL_SIZE_SM ] __attribute__((aligned(0x100))); +volatile int sm_f2[ NB_RING_NODES_ASM_F2 * TOTAL_SIZE_SM ] __attribute__((aligned(0x100))); // APB CONFIGURATION REGISTERS time_management_regs_t *time_management_regs = (time_management_regs_t*) REGS_ADDR_TIME_MANAGEMENT; diff --git a/src/fsw_processing.c b/src/fsw_processing.c --- a/src/fsw_processing.c +++ b/src/fsw_processing.c @@ -36,20 +36,63 @@ void init_sm_rings( void ) // F0 RING sm_ring_f0[0].next = (ring_node*) &sm_ring_f0[1]; sm_ring_f0[0].previous = (ring_node*) &sm_ring_f0[NB_RING_NODES_ASM_F0-1]; - sm_ring_f0[0].buffer_address = (int) &sm_f0[0][0]; + sm_ring_f0[0].buffer_address = + (int) &sm_f0[ 0 ]; sm_ring_f0[NB_RING_NODES_ASM_F0-1].next = (ring_node*) &sm_ring_f0[0]; sm_ring_f0[NB_RING_NODES_ASM_F0-1].previous = (ring_node*) &sm_ring_f0[NB_RING_NODES_ASM_F0-2]; - sm_ring_f0[NB_RING_NODES_ASM_F0-1].buffer_address = (int) &sm_f0[NB_RING_NODES_ASM_F0-1][0]; + sm_ring_f0[NB_RING_NODES_ASM_F0-1].buffer_address = + (int) &sm_f0[ (NB_RING_NODES_ASM_F0-1) * TOTAL_SIZE_SM ]; for(i=1; imatrixF0_Address0 = sm_ring_f0[0].buffer_address; DEBUG_PRINTF1("spectral_matrix_regs->matrixF0_Address0 @%x\n", spectral_matrix_regs->matrixF0_Address0) @@ -57,7 +100,10 @@ void init_sm_rings( void ) void reset_current_sm_ring_nodes( void ) { - current_ring_node_sm_f0 = sm_ring_f0; + current_ring_node_sm_f0 = sm_ring_f0; + current_ring_node_sm_f1 = sm_ring_f1; + current_ring_node_sm_f2 = sm_ring_f2; + ring_node_for_averaging_sm_f0 = sm_ring_f0; } @@ -112,31 +158,6 @@ rtems_isr spectral_matrices_isr( rtems_v rtems_isr spectral_matrices_isr_simu( rtems_vector_number vector ) { - rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_8 ); - - if ( (spectral_matrix_regs->status & 0x1) == 0x01) - { - current_ring_node_sm_f0 = current_ring_node_sm_f0->next; - spectral_matrix_regs->matrixF0_Address0 = current_ring_node_sm_f0->buffer_address; - spectral_matrix_regs->status = spectral_matrix_regs->status & 0xfffffffe; // 1110 - nb_sm_f0 = nb_sm_f0 + 1; - } - else if ( (spectral_matrix_regs->status & 0x2) == 0x02) - { - current_ring_node_sm_f0 = current_ring_node_sm_f0->next; - spectral_matrix_regs->matrixFO_Address1 = current_ring_node_sm_f0->buffer_address; - spectral_matrix_regs->status = spectral_matrix_regs->status & 0xfffffffd; // 1101 - nb_sm_f0 = nb_sm_f0 + 1; - } - - if ( (spectral_matrix_regs->status & 0x30) != 0x00) - { - rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_8 ); - spectral_matrix_regs->status = spectral_matrix_regs->status & 0xffffffcf; // 1100 1111 - } - - spectral_matrix_regs->status = spectral_matrix_regs->status & 0xfffffff3; // 0011 - if (nb_sm_f0 == (NB_SM_TO_RECEIVE_BEFORE_AVF0-1) ) { ring_node_for_averaging_sm_f0 = current_ring_node_sm_f0; diff --git a/src/tc_handler.c b/src/tc_handler.c --- a/src/tc_handler.c +++ b/src/tc_handler.c @@ -403,9 +403,13 @@ int stop_current_mode(void) LEON_Clear_interrupt( IRQ_SPECTRAL_MATRIX ); // clear spectral matrix interrupt // (3) reset registers + // waveform picker reset_wfp_burst_enable(); // reset burst and enable bits reset_wfp_status(); // reset all the status bits - disable_irq_on_new_ready_matrix(); // stop the spectral matrices + // spectral matrices + set_irq_on_new_ready_matrix( 0 ); // stop the spectral matrices + set_run_matrix_spectral( 0 ); // run_matrix_spectral is set to 0 + reset_extractSWF(); // reset the extractSWF flag to false // LEON_Mask_interrupt( IRQ_SM_SIMULATOR ); // mask spectral matrix interrupt simulator @@ -605,8 +609,10 @@ void launch_waveform_picker( unsigned ch reset_current_ring_nodes(); reset_waveform_picker_regs(); set_wfp_burst_enable_register( mode ); + LEON_Clear_interrupt( IRQ_WAVEFORM_PICKER ); LEON_Unmask_interrupt( IRQ_WAVEFORM_PICKER ); + startDate = time_management_regs->coarse_time + 2; waveform_picker_regs->run_burst_enable = waveform_picker_regs->run_burst_enable | 0x80; // [1000 0000] waveform_picker_regs->start_date = startDate; @@ -618,23 +624,43 @@ void launch_spectral_matrix( unsigned ch reset_current_sm_ring_nodes(); reset_spectral_matrix_regs(); - enable_irq_on_new_ready_matrix(); - +#ifdef VHDL_DEV + set_irq_on_new_ready_matrix( 1 ); LEON_Clear_interrupt( IRQ_SPECTRAL_MATRIX ); LEON_Unmask_interrupt( IRQ_SPECTRAL_MATRIX ); + set_run_matrix_spectral( 1 ); +#else + // Spectral Matrices simulator + timer_start( (gptimer_regs_t*) REGS_ADDR_GPTIMER, TIMER_SM_SIMULATOR ); + LEON_Clear_interrupt( IRQ_SM_SIMULATOR ); + LEON_Unmask_interrupt( IRQ_SM_SIMULATOR ); +#endif } -void enable_irq_on_new_ready_matrix( void ) +void set_irq_on_new_ready_matrix( unsigned char value ) { - spectral_matrix_regs->config = spectral_matrix_regs->config | 0x01; + if (value == 1) + { + spectral_matrix_regs->config = spectral_matrix_regs->config | 0x01; + } + else + { + spectral_matrix_regs->config = spectral_matrix_regs->config & 0xfffffffe; // 1110 + } } -void disable_irq_on_new_ready_matrix( void ) +void set_run_matrix_spectral( unsigned char value ) { - spectral_matrix_regs->config = spectral_matrix_regs->config & 0xfffffffe; // 1110 + if (value == 1) + { + spectral_matrix_regs->config = spectral_matrix_regs->config | 0x4; // 0100 set run_matrix spectral to 1 + } + else + { + spectral_matrix_regs->config = spectral_matrix_regs->config & 0xfffffffb; // 1011 set run_matrix spectral to 0 + } } - void launch_spectral_matrix_simu( unsigned char mode ) { reset_nb_sm_f0(); diff --git a/src/wf_handler.c b/src/wf_handler.c --- a/src/wf_handler.c +++ b/src/wf_handler.c @@ -37,8 +37,22 @@ ring_node *ring_node_to_send_swf_f2; ring_node *ring_node_to_send_cwf_f2; bool extractSWF = false; +bool swf_f0_ready = false; +bool swf_f1_ready = false; +bool swf_f2_ready = false; -int wf_snap_f1_extracted[ (NB_SAMPLES_PER_SNAPSHOT * NB_WORDS_SWF_BLK) + TIME_OFFSET ]; +int wf_snap_extracted[ (NB_SAMPLES_PER_SNAPSHOT * NB_WORDS_SWF_BLK) + TIME_OFFSET ]; + +//********************* +// Interrupt SubRoutine + +void reset_extractSWF( void ) +{ + extractSWF = false; + swf_f0_ready = false; + swf_f1_ready = false; + swf_f2_ready = false; +} rtems_isr waveforms_isr( rtems_vector_number vector ) { @@ -50,6 +64,7 @@ rtems_isr waveforms_isr( rtems_vector_nu * */ + rtems_status_code status; static unsigned char nb_swf = 0; if ( (lfrCurrentMode == LFR_MODE_NORMAL) @@ -143,29 +158,36 @@ rtems_isr waveforms_isr( rtems_vector_nu if (extractSWF == true) { ring_node_to_send_swf_f1 = current_ring_node_f1; - if (rtems_event_send( Task_id[TASKID_SWBD], RTEMS_EVENT_0 ) != RTEMS_SUCCESSFUL) { - rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_2 ); - } + // extract the snapshot + status = rtems_event_send( Task_id[TASKID_SWBD], RTEMS_EVENT_MODE_SBM1 ); extractSWF = false; + swf_f1_ready = true; } // (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 - if (rtems_event_send( Task_id[TASKID_CWF1], RTEMS_EVENT_MODE_SBM1 ) != RTEMS_SUCCESSFUL) { - rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_2 ); + 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 (swf_f0_ready == true) + { + extractSWF = true; + swf_f0_ready = false; } - waveform_picker_regs->status = waveform_picker_regs->status & 0xfffffddd; // [1111 1101 1101 1101] f1 bits = 0 + if ((swf_f1_ready == true) && (swf_f2_ready == true)) + { + status = rtems_event_send( Task_id[TASKID_WFRM], RTEMS_EVENT_MODE_SBM1 ); + swf_f1_ready = false; + swf_f2_ready = false; + } } if ( (waveform_picker_regs->status & 0x01) == 0x01 ) { // [0001] check the f0 full bit - extractSWF = true; + 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 - if (rtems_event_send( Task_id[TASKID_WFRM], RTEMS_EVENT_MODE_SBM1 ) != RTEMS_SUCCESSFUL) { - rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_2 ); - } + swf_f2_ready = true; waveform_picker_regs->status = waveform_picker_regs->status & 0xfffffbbb; // [1111 1011 1011 1011] f2 bits = 0 } break; @@ -174,24 +196,38 @@ rtems_isr waveforms_isr( rtems_vector_nu // SBM2 case(LFR_MODE_SBM2): if ( (waveform_picker_regs->status & 0x04) == 0x04 ){ // [0100] check the f2 full bit + // (0) launch snapshot extraction if needed + if (extractSWF == true) + { + ring_node_to_send_swf_f2 = current_ring_node_f2; + // extract the snapshot + status = rtems_event_send( Task_id[TASKID_SWBD], RTEMS_EVENT_MODE_SBM2 ); + // send the snapshot when build, SWBD priority < WFRM priority + status = rtems_event_send( Task_id[TASKID_WFRM], RTEMS_EVENT_MODE_SBM2 ); + extractSWF = false; + } // (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_SBM2 ) != RTEMS_SUCCESSFUL) { - rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_2 ); + 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 + // (3) check whether swf_fo and swf_f& are ready or not + if (swf_f0_ready && swf_f1_ready) + { + extractSWF = true; + swf_f0_ready = false; + swf_f1_ready = false; } - 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 - ring_node_to_send_swf_f2 = current_ring_node_f2->previous; + 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 - 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 & 0xfffffccc; // [1111 1100 1100 1100] f1, f0 bits = 0 + swf_f1_ready = true; + waveform_picker_regs->status = waveform_picker_regs->status & 0xfffffddd; // [1111 1101 1101 1101] f1, f0 bits = 0 } break; @@ -202,6 +238,9 @@ rtems_isr waveforms_isr( rtems_vector_nu } } +//************ +// RTEMS TASKS + rtems_task wfrm_task(rtems_task_argument argument) //used with the waveform picker VHDL IP { /** This RTEMS task is dedicated to the transmission of snapshots of the NORMAL mode. @@ -240,18 +279,25 @@ rtems_task wfrm_task(rtems_task_argument RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out); if (event_out == RTEMS_EVENT_MODE_NORMAL) { - PRINTF("WFRM received RTEMS_EVENT_MODE_NORMAL\n") + DEBUG_PRINTF("WFRM received RTEMS_EVENT_MODE_NORMAL\n") send_waveform_SWF((volatile int*) ring_node_to_send_swf_f0->buffer_address, SID_NORM_SWF_F0, headerSWF_F0, queue_id); send_waveform_SWF((volatile int*) ring_node_to_send_swf_f1->buffer_address, SID_NORM_SWF_F1, headerSWF_F1, queue_id); send_waveform_SWF((volatile int*) ring_node_to_send_swf_f2->buffer_address, SID_NORM_SWF_F2, headerSWF_F2, queue_id); } if (event_out == RTEMS_EVENT_MODE_SBM1) { - PRINTF("WFRM received RTEMS_EVENT_MODE_SBM1\n") + DEBUG_PRINTF("WFRM received RTEMS_EVENT_MODE_SBM1\n") send_waveform_SWF((volatile int*) ring_node_to_send_swf_f0->buffer_address, SID_NORM_SWF_F0, headerSWF_F0, queue_id); - send_waveform_SWF((volatile int*) wf_snap_f1_extracted , SID_NORM_SWF_F1, headerSWF_F1, queue_id); + send_waveform_SWF((volatile int*) wf_snap_extracted , SID_NORM_SWF_F1, headerSWF_F1, queue_id); send_waveform_SWF((volatile int*) ring_node_to_send_swf_f2->buffer_address, SID_NORM_SWF_F2, headerSWF_F2, queue_id); } + if (event_out == RTEMS_EVENT_MODE_SBM2) + { + DEBUG_PRINTF("WFRM received RTEMS_EVENT_MODE_SBM2\n") + send_waveform_SWF((volatile int*) ring_node_to_send_swf_f0->buffer_address, SID_NORM_SWF_F0, headerSWF_F0, queue_id); + send_waveform_SWF((volatile int*) ring_node_to_send_swf_f1->buffer_address, SID_NORM_SWF_F1, headerSWF_F1, queue_id); + send_waveform_SWF((volatile int*) wf_snap_extracted , SID_NORM_SWF_F2, headerSWF_F2, queue_id); + } } } @@ -407,9 +453,20 @@ rtems_task swbd_task(rtems_task_argument while(1){ // wait for an RTEMS_EVENT - rtems_event_receive( RTEMS_EVENT_0, + rtems_event_receive( RTEMS_EVENT_MODE_SBM1 | RTEMS_EVENT_MODE_SBM2, RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out); - build_snapshot_from_ring(); + if (event_out == RTEMS_EVENT_MODE_SBM1) + { + build_snapshot_from_ring( ring_node_to_send_swf_f1, 1 ); + } + else if (event_out == RTEMS_EVENT_MODE_SBM2) + { + build_snapshot_from_ring( ring_node_to_send_swf_f2, 2 ); + } + else + { + PRINTF1("in SWBD *** unexpected rtems event received %x\n", (int) event_out) + } } } @@ -677,9 +734,6 @@ int send_waveform_SWF( volatile int *wav ret = LFR_DEFAULT; - DEBUG_PRINTF1("sid = %d, ", sid) - DEBUG_PRINTF2("coarse = %x, fine = %x\n", waveform[0], waveform[1]) - coarseTime = waveform[0]; fineTime = waveform[1]; @@ -935,45 +989,91 @@ void compute_acquisition_time( unsigned } -void build_snapshot_from_ring( void ) +void build_snapshot_from_ring( ring_node *ring_node_to_send, unsigned char frequencyChannel ) { unsigned int i; unsigned long long int centerTime_asLong; unsigned long long int acquisitionTimeF0_asLong; - unsigned long long int acquisitionTimeF1_asLong; - unsigned char *acquisitionTimeF0; - unsigned char *acquisitionTimeF1; + unsigned long long int acquisitionTime_asLong; + unsigned long long int bufferAcquisitionTime_asLong; unsigned char *ptr1; unsigned char *ptr2; + unsigned char nb_ring_nodes; + unsigned long long int frequency_asLong; + unsigned long long int nbTicksPerSample_asLong; + unsigned long long int nbSamplesPart1_asLong; + unsigned long long int sampleOffset_asLong; - unsigned int deltaT; + unsigned int deltaT_F0; + unsigned int deltaT_F1; + unsigned long long int deltaT_F2; - deltaT = 2731; // (2048. / 24576. / 2.) * 65536. = 2730.667; + deltaT_F0 = 2731; // (2048. / 24576. / 2.) * 65536. = 2730.667; + deltaT_F1 = 16384; // (2048. / 4096. / 2.) * 65536. = 16384; + deltaT_F2 = 262144; // (2048. / 256. / 2.) * 65536. = 262144; + sampleOffset_asLong = 0x00; - acquisitionTimeF0 = (unsigned char*) current_ring_node_f0->buffer_address; - acquisitionTimeF1 = (unsigned char*) ring_node_to_send_cwf_f1->buffer_address; + // get the f0 acquisition time + build_acquisition_time( &acquisitionTimeF0_asLong, current_ring_node_f0 ); + PRINTF1("acquisitionTimeF0_asLong %llx \n", acquisitionTimeF0_asLong) + + // compute the central reference time + centerTime_asLong = acquisitionTimeF0_asLong + deltaT_F0; + PRINTF1("centerTime_asLong %llx \n", centerTime_asLong) - acquisitionTimeF0_asLong = 0x00; - acquisitionTimeF1_asLong = 0x00; - acquisitionTimeF0_asLong = ( acquisitionTimeF0[0] << 24 ) - + ( acquisitionTimeF0[1] << 16 ) - + ( (unsigned long long int) acquisitionTimeF0[2] << 40 ) - + ( (unsigned long long int) acquisitionTimeF0[3] << 32 ) - + ( acquisitionTimeF0[4] << 8 ) - + ( acquisitionTimeF0[5] ); + // compute the acquisition time of the current snapshot + switch(frequencyChannel) + { + case 1: // 1 is for F1 = 4096 Hz + acquisitionTime_asLong = centerTime_asLong - deltaT_F1; + nb_ring_nodes = NB_RING_NODES_F1; + frequency_asLong = 4096; + nbTicksPerSample_asLong = 16; // 65536 / 4096; + break; + case 2: // 2 is for F2 = 256 Hz + acquisitionTime_asLong = centerTime_asLong - deltaT_F2; + nb_ring_nodes = NB_RING_NODES_F2; + frequency_asLong = 256; + nbTicksPerSample_asLong = 256; // 65536 / 256; + break; + default: + acquisitionTime_asLong = centerTime_asLong; + frequency_asLong = 256; + nbTicksPerSample_asLong = 256; + break; + } + PRINTF1("acquisitionTime_asLong %llx\n", acquisitionTime_asLong) - acquisitionTimeF1_asLong = ( acquisitionTimeF1[0] << 24 ) - + ( acquisitionTimeF1[1] << 16 ) - + ( (unsigned long long int) acquisitionTimeF1[2] << 40 ) - + ( (unsigned long long int) acquisitionTimeF1[3] << 32 ) - + ( acquisitionTimeF1[4] << 8 ) - + ( acquisitionTimeF1[5] ); + //**************************************************************************** + // 1) search the ring_node with the acquisition time <= acquisitionTime_asLong + for (i=0; iprevious; + } - centerTime_asLong = acquisitionTimeF0_asLong + deltaT; + //************************************************* + // (2) once the buffer is found, build the snapshot + + // compute the number of samples to take in the current buffer + sampleOffset_asLong = ((acquisitionTime_asLong - bufferAcquisitionTime_asLong) * frequency_asLong ) >> 16; + nbSamplesPart1_asLong = NB_SAMPLES_PER_SNAPSHOT - sampleOffset_asLong; + PRINTF2("sampleOffset_asLong = %lld, nbSamplesPart1 = %lld\n", sampleOffset_asLong, nbSamplesPart1_asLong) - ptr1 = (unsigned char*) &acquisitionTimeF1_asLong; - ptr2 = (unsigned char*) wf_snap_f1_extracted; + // compute the final acquisition time + acquisitionTime_asLong = bufferAcquisitionTime_asLong + + sampleOffset_asLong * nbTicksPerSample_asLong; + PRINTF1("FINAL acquisitionTime_asLong %llx\n\n", acquisitionTime_asLong) + // copy the acquisition time at the beginning of the extrated snapshot + ptr1 = (unsigned char*) &acquisitionTime_asLong; + ptr2 = (unsigned char*) wf_snap_extracted; ptr2[0] = ptr1[ 2 + 2 ]; ptr2[1] = ptr1[ 3 + 2 ]; ptr2[2] = ptr1[ 0 + 2 ]; @@ -981,12 +1081,39 @@ void build_snapshot_from_ring( void ) ptr2[4] = ptr1[ 4 + 2 ]; ptr2[5] = ptr1[ 5 + 2 ]; - for (i=0; i<(NB_SAMPLES_PER_SNAPSHOT * NB_WORDS_SWF_BLK); i++ ) + // re set the synchronization bit + + + // copy the part 1 of the snapshot in the extracted buffer + for ( i = 0; i < (nbSamplesPart1_asLong * NB_WORDS_SWF_BLK); i++ ) + { + wf_snap_extracted[i + TIME_OFFSET] = + ((int*) ring_node_to_send->buffer_address)[i + (sampleOffset_asLong * NB_WORDS_SWF_BLK) + TIME_OFFSET]; + } + // copy the part 2 of the snapshot in the extracted buffer + ring_node_to_send = ring_node_to_send->next; + for ( i = (nbSamplesPart1_asLong * NB_WORDS_SWF_BLK); i < (NB_SAMPLES_PER_SNAPSHOT * NB_WORDS_SWF_BLK); i++ ) { - wf_snap_f1_extracted[i + TIME_OFFSET] = ((int*)(ring_node_to_send_cwf_f1->buffer_address))[i + TIME_OFFSET]; + wf_snap_extracted[i + TIME_OFFSET] = + ((int*) ring_node_to_send->buffer_address)[(i-(nbSamplesPart1_asLong * NB_WORDS_SWF_BLK)) + TIME_OFFSET]; } } +void build_acquisition_time( unsigned long long int *acquisitionTimeAslong, ring_node *current_ring_node ) +{ + unsigned char *acquisitionTimeCharPtr; + + acquisitionTimeCharPtr = (unsigned char*) current_ring_node->buffer_address; + + *acquisitionTimeAslong = 0x00; + *acquisitionTimeAslong = ( acquisitionTimeCharPtr[0] << 24 ) + + ( acquisitionTimeCharPtr[1] << 16 ) + + ( (unsigned long long int) (acquisitionTimeCharPtr[2] & 0x7f) << 40 ) // [0111 1111] mask the synchronization bit + + ( (unsigned long long int) acquisitionTimeCharPtr[3] << 32 ) + + ( acquisitionTimeCharPtr[4] << 8 ) + + ( acquisitionTimeCharPtr[5] ); +} + //************** // wfp registers void reset_wfp_burst_enable(void)