@@ -1,131 +1,131 | |||||
1 | #ifndef FSW_MISC_H_INCLUDED |
|
1 | #ifndef FSW_MISC_H_INCLUDED | |
2 | #define FSW_MISC_H_INCLUDED |
|
2 | #define FSW_MISC_H_INCLUDED | |
3 |
|
3 | |||
4 | #include <rtems.h> |
|
4 | #include <rtems.h> | |
5 | #include <stdio.h> |
|
5 | #include <stdio.h> | |
6 | #include <grspw.h> |
|
6 | #include <grspw.h> | |
7 | #include <grlib_regs.h> |
|
7 | #include <grlib_regs.h> | |
8 |
|
8 | |||
9 | #include "fsw_params.h" |
|
9 | #include "fsw_params.h" | |
10 | #include "fsw_spacewire.h" |
|
10 | #include "fsw_spacewire.h" | |
11 | #include "lfr_cpu_usage_report.h" |
|
11 | #include "lfr_cpu_usage_report.h" | |
12 |
|
12 | |||
13 | #define LFR_RESET_CAUSE_UNKNOWN_CAUSE 0 |
|
13 | #define LFR_RESET_CAUSE_UNKNOWN_CAUSE 0 | |
14 | #define WATCHDOG_LOOP_PRINTF 10 |
|
14 | #define WATCHDOG_LOOP_PRINTF 10 | |
15 | #define WATCHDOG_LOOP_DEBUG 3 |
|
15 | #define WATCHDOG_LOOP_DEBUG 3 | |
16 |
|
16 | |||
17 | #define DUMB_MESSAGE_NB 15 |
|
17 | #define DUMB_MESSAGE_NB 15 | |
18 | #define NB_RTEMS_EVENTS 32 |
|
18 | #define NB_RTEMS_EVENTS 32 | |
19 | #define EVENT_12 12 |
|
19 | #define EVENT_12 12 | |
20 | #define EVENT_13 13 |
|
20 | #define EVENT_13 13 | |
21 | #define EVENT_14 14 |
|
21 | #define EVENT_14 14 | |
22 | #define DUMB_MESSAGE_0 "in DUMB *** default" |
|
22 | #define DUMB_MESSAGE_0 "in DUMB *** default" | |
23 | #define DUMB_MESSAGE_1 "in DUMB *** timecode_irq_handler" |
|
23 | #define DUMB_MESSAGE_1 "in DUMB *** timecode_irq_handler" | |
24 | #define DUMB_MESSAGE_2 "in DUMB *** f3 buffer changed" |
|
24 | #define DUMB_MESSAGE_2 "in DUMB *** f3 buffer changed" | |
25 | #define DUMB_MESSAGE_3 "in DUMB *** in SMIQ *** Error sending event to AVF0" |
|
25 | #define DUMB_MESSAGE_3 "in DUMB *** in SMIQ *** Error sending event to AVF0" | |
26 | #define DUMB_MESSAGE_4 "in DUMB *** spectral_matrices_isr *** Error sending event to SMIQ" |
|
26 | #define DUMB_MESSAGE_4 "in DUMB *** spectral_matrices_isr *** Error sending event to SMIQ" | |
27 | #define DUMB_MESSAGE_5 "in DUMB *** waveforms_simulator_isr" |
|
27 | #define DUMB_MESSAGE_5 "in DUMB *** waveforms_simulator_isr" | |
28 | #define DUMB_MESSAGE_6 "VHDL SM *** two buffers f0 ready" |
|
28 | #define DUMB_MESSAGE_6 "VHDL SM *** two buffers f0 ready" | |
29 | #define DUMB_MESSAGE_7 "ready for dump" |
|
29 | #define DUMB_MESSAGE_7 "ready for dump" | |
30 | #define DUMB_MESSAGE_8 "VHDL ERR *** spectral matrix" |
|
30 | #define DUMB_MESSAGE_8 "VHDL ERR *** spectral matrix" | |
31 | #define DUMB_MESSAGE_9 "tick" |
|
31 | #define DUMB_MESSAGE_9 "tick" | |
32 | #define DUMB_MESSAGE_10 "VHDL ERR *** waveform picker" |
|
32 | #define DUMB_MESSAGE_10 "VHDL ERR *** waveform picker" | |
33 | #define DUMB_MESSAGE_11 "VHDL ERR *** unexpected ready matrix values" |
|
33 | #define DUMB_MESSAGE_11 "VHDL ERR *** unexpected ready matrix values" | |
34 | #define DUMB_MESSAGE_12 "WATCHDOG timer" |
|
34 | #define DUMB_MESSAGE_12 "WATCHDOG timer" | |
35 | #define DUMB_MESSAGE_13 "TIMECODE timer" |
|
35 | #define DUMB_MESSAGE_13 "TIMECODE timer" | |
36 | #define DUMB_MESSAGE_14 "TIMECODE ISR" |
|
36 | #define DUMB_MESSAGE_14 "TIMECODE ISR" | |
37 |
|
37 | |||
38 | enum lfr_reset_cause_t{ |
|
38 | enum lfr_reset_cause_t{ | |
39 | UNKNOWN_CAUSE, |
|
39 | UNKNOWN_CAUSE, | |
40 | POWER_ON, |
|
40 | POWER_ON, | |
41 | TC_RESET, |
|
41 | TC_RESET, | |
42 | WATCHDOG, |
|
42 | WATCHDOG, | |
43 | ERROR_RESET, |
|
43 | ERROR_RESET, | |
44 | UNEXP_RESET |
|
44 | UNEXP_RESET | |
45 | }; |
|
45 | }; | |
46 |
|
46 | |||
47 | typedef struct{ |
|
47 | typedef struct{ | |
48 | unsigned char dpu_spw_parity; |
|
48 | unsigned char dpu_spw_parity; | |
49 | unsigned char dpu_spw_disconnect; |
|
49 | unsigned char dpu_spw_disconnect; | |
50 | unsigned char dpu_spw_escape; |
|
50 | unsigned char dpu_spw_escape; | |
51 | unsigned char dpu_spw_credit; |
|
51 | unsigned char dpu_spw_credit; | |
52 | unsigned char dpu_spw_write_sync; |
|
52 | unsigned char dpu_spw_write_sync; | |
53 | unsigned char timecode_erroneous; |
|
53 | unsigned char timecode_erroneous; | |
54 | unsigned char timecode_missing; |
|
54 | unsigned char timecode_missing; | |
55 | unsigned char timecode_invalid; |
|
55 | unsigned char timecode_invalid; | |
56 | unsigned char time_timecode_it; |
|
56 | unsigned char time_timecode_it; | |
57 | unsigned char time_not_synchro; |
|
57 | unsigned char time_not_synchro; | |
58 | unsigned char time_timecode_ctr; |
|
58 | unsigned char time_timecode_ctr; | |
59 | unsigned char ahb_correctable; |
|
59 | unsigned char ahb_correctable; | |
60 | } hk_lfr_le_t; |
|
60 | } hk_lfr_le_t; | |
61 |
|
61 | |||
62 | typedef struct{ |
|
62 | typedef struct{ | |
63 | unsigned char dpu_spw_early_eop; |
|
63 | unsigned char dpu_spw_early_eop; | |
64 | unsigned char dpu_spw_invalid_addr; |
|
64 | unsigned char dpu_spw_invalid_addr; | |
65 | unsigned char dpu_spw_eep; |
|
65 | unsigned char dpu_spw_eep; | |
66 | unsigned char dpu_spw_rx_too_big; |
|
66 | unsigned char dpu_spw_rx_too_big; | |
67 | } hk_lfr_me_t; |
|
67 | } hk_lfr_me_t; | |
68 |
|
68 | |||
69 | extern gptimer_regs_t *gptimer_regs; |
|
69 | extern gptimer_regs_t *gptimer_regs; | |
70 | extern void ASR16_get_FPRF_IURF_ErrorCounters( unsigned int*, unsigned int* ); |
|
70 | extern void ASR16_get_FPRF_IURF_ErrorCounters( unsigned int*, unsigned int* ); | |
71 | extern void CCR_getInstructionAndDataErrorCounters( unsigned int*, unsigned int* ); |
|
71 | extern void CCR_getInstructionAndDataErrorCounters( unsigned int*, unsigned int* ); | |
72 |
|
72 | |||
73 |
rtems_name name_hk_rate_monotonic |
|
73 | extern rtems_name name_hk_rate_monotonic; // name of the HK rate monotonic | |
74 |
rtems_id HK_id |
|
74 | extern rtems_id HK_id;// id of the HK rate monotonic period | |
75 |
rtems_name name_avgv_rate_monotonic |
|
75 | extern rtems_name name_avgv_rate_monotonic; // name of the AVGV rate monotonic | |
76 |
rtems_id AVGV_id |
|
76 | extern rtems_id AVGV_id;// id of the AVGV rate monotonic period | |
77 |
|
77 | |||
78 | void timer_configure( unsigned char timer, unsigned int clock_divider, |
|
78 | void timer_configure( unsigned char timer, unsigned int clock_divider, | |
79 | unsigned char interrupt_level, rtems_isr (*timer_isr)() ); |
|
79 | unsigned char interrupt_level, rtems_isr (*timer_isr)() ); | |
80 | void timer_start( unsigned char timer ); |
|
80 | void timer_start( unsigned char timer ); | |
81 | void timer_stop( unsigned char timer ); |
|
81 | void timer_stop( unsigned char timer ); | |
82 | void timer_set_clock_divider(unsigned char timer, unsigned int clock_divider); |
|
82 | void timer_set_clock_divider(unsigned char timer, unsigned int clock_divider); | |
83 |
|
83 | |||
84 | // WATCHDOG |
|
84 | // WATCHDOG | |
85 | rtems_isr watchdog_isr( rtems_vector_number vector ); |
|
85 | rtems_isr watchdog_isr( rtems_vector_number vector ); | |
86 | void watchdog_configure(void); |
|
86 | void watchdog_configure(void); | |
87 | void watchdog_stop(void); |
|
87 | void watchdog_stop(void); | |
88 | void watchdog_reload(void); |
|
88 | void watchdog_reload(void); | |
89 | void watchdog_start(void); |
|
89 | void watchdog_start(void); | |
90 |
|
90 | |||
91 | // SERIAL LINK |
|
91 | // SERIAL LINK | |
92 | int send_console_outputs_on_apbuart_port( void ); |
|
92 | int send_console_outputs_on_apbuart_port( void ); | |
93 | int enable_apbuart_transmitter( void ); |
|
93 | int enable_apbuart_transmitter( void ); | |
94 | void set_apbuart_scaler_reload_register(unsigned int regs, unsigned int value); |
|
94 | void set_apbuart_scaler_reload_register(unsigned int regs, unsigned int value); | |
95 |
|
95 | |||
96 | // RTEMS TASKS |
|
96 | // RTEMS TASKS | |
97 | rtems_task load_task( rtems_task_argument argument ); |
|
97 | rtems_task load_task( rtems_task_argument argument ); | |
98 | rtems_task hous_task( rtems_task_argument argument ); |
|
98 | rtems_task hous_task( rtems_task_argument argument ); | |
99 | rtems_task avgv_task( rtems_task_argument argument ); |
|
99 | rtems_task avgv_task( rtems_task_argument argument ); | |
100 | rtems_task dumb_task( rtems_task_argument unused ); |
|
100 | rtems_task dumb_task( rtems_task_argument unused ); | |
101 |
|
101 | |||
102 | void init_housekeeping_parameters( void ); |
|
102 | void init_housekeeping_parameters( void ); | |
103 | void increment_seq_counter(unsigned short *packetSequenceControl); |
|
103 | void increment_seq_counter(unsigned short *packetSequenceControl); | |
104 | void getTime( unsigned char *time); |
|
104 | void getTime( unsigned char *time); | |
105 | unsigned long long int getTimeAsUnsignedLongLongInt( ); |
|
105 | unsigned long long int getTimeAsUnsignedLongLongInt( ); | |
106 | void send_dumb_hk( void ); |
|
106 | void send_dumb_hk( void ); | |
107 | void get_temperatures( unsigned char *temperatures ); |
|
107 | void get_temperatures( unsigned char *temperatures ); | |
108 | void get_v_e1_e2_f3( unsigned char *spacecraft_potential ); |
|
108 | void get_v_e1_e2_f3( unsigned char *spacecraft_potential ); | |
109 | void get_cpu_load( unsigned char *resource_statistics ); |
|
109 | void get_cpu_load( unsigned char *resource_statistics ); | |
110 | void set_hk_lfr_sc_potential_flag( bool state ); |
|
110 | void set_hk_lfr_sc_potential_flag( bool state ); | |
111 | void set_sy_lfr_pas_filter_enabled( bool state ); |
|
111 | void set_sy_lfr_pas_filter_enabled( bool state ); | |
112 | void set_sy_lfr_watchdog_enabled( bool state ); |
|
112 | void set_sy_lfr_watchdog_enabled( bool state ); | |
113 | void set_hk_lfr_calib_enable( bool state ); |
|
113 | void set_hk_lfr_calib_enable( bool state ); | |
114 | void set_hk_lfr_reset_cause( enum lfr_reset_cause_t lfr_reset_cause ); |
|
114 | void set_hk_lfr_reset_cause( enum lfr_reset_cause_t lfr_reset_cause ); | |
115 | void hk_lfr_le_me_he_update(); |
|
115 | void hk_lfr_le_me_he_update(); | |
116 | void set_hk_lfr_time_not_synchro(); |
|
116 | void set_hk_lfr_time_not_synchro(); | |
117 |
|
117 | |||
118 | extern int sched_yield( void ); |
|
118 | extern int sched_yield( void ); | |
119 | extern void rtems_cpu_usage_reset(); |
|
119 | extern void rtems_cpu_usage_reset(); | |
120 | extern ring_node *current_ring_node_f3; |
|
120 | extern ring_node *current_ring_node_f3; | |
121 | extern ring_node *ring_node_to_send_cwf_f3; |
|
121 | extern ring_node *ring_node_to_send_cwf_f3; | |
122 | extern ring_node waveform_ring_f3[]; |
|
122 | extern ring_node waveform_ring_f3[]; | |
123 | extern unsigned short sequenceCounterHK; |
|
123 | extern unsigned short sequenceCounterHK; | |
124 |
|
124 | |||
125 | extern unsigned char hk_lfr_q_sd_fifo_size_max; |
|
125 | extern unsigned char hk_lfr_q_sd_fifo_size_max; | |
126 | extern unsigned char hk_lfr_q_rv_fifo_size_max; |
|
126 | extern unsigned char hk_lfr_q_rv_fifo_size_max; | |
127 | extern unsigned char hk_lfr_q_p0_fifo_size_max; |
|
127 | extern unsigned char hk_lfr_q_p0_fifo_size_max; | |
128 | extern unsigned char hk_lfr_q_p1_fifo_size_max; |
|
128 | extern unsigned char hk_lfr_q_p1_fifo_size_max; | |
129 | extern unsigned char hk_lfr_q_p2_fifo_size_max; |
|
129 | extern unsigned char hk_lfr_q_p2_fifo_size_max; | |
130 |
|
130 | |||
131 | #endif // FSW_MISC_H_INCLUDED |
|
131 | #endif // FSW_MISC_H_INCLUDED |
@@ -1,102 +1,106 | |||||
1 | /** Global variables of the LFR flight software. |
|
1 | /** Global variables of the LFR flight software. | |
2 | * |
|
2 | * | |
3 | * @file |
|
3 | * @file | |
4 | * @author P. LEROY |
|
4 | * @author P. LEROY | |
5 | * |
|
5 | * | |
6 | * Among global variables, there are: |
|
6 | * Among global variables, there are: | |
7 | * - RTEMS names and id. |
|
7 | * - RTEMS names and id. | |
8 | * - APB configuration registers. |
|
8 | * - APB configuration registers. | |
9 | * - waveforms global buffers, used by the waveform picker hardware module to store data. |
|
9 | * - waveforms global buffers, used by the waveform picker hardware module to store data. | |
10 | * - spectral matrices buffesr, used by the hardware module to store data. |
|
10 | * - spectral matrices buffesr, used by the hardware module to store data. | |
11 | * - variable related to LFR modes parameters. |
|
11 | * - variable related to LFR modes parameters. | |
12 | * - the global HK packet buffer. |
|
12 | * - the global HK packet buffer. | |
13 | * - the global dump parameter buffer. |
|
13 | * - the global dump parameter buffer. | |
14 | * |
|
14 | * | |
15 | */ |
|
15 | */ | |
16 |
|
16 | |||
17 | #include <rtems.h> |
|
17 | #include <rtems.h> | |
18 | #include <grspw.h> |
|
18 | #include <grspw.h> | |
19 |
|
19 | |||
20 | #include "ccsds_types.h" |
|
20 | #include "ccsds_types.h" | |
21 | #include "grlib_regs.h" |
|
21 | #include "grlib_regs.h" | |
22 | #include "fsw_params.h" |
|
22 | #include "fsw_params.h" | |
23 | #include "fsw_params_wf_handler.h" |
|
23 | #include "fsw_params_wf_handler.h" | |
24 |
|
24 | |||
25 | #define NB_OF_TASKS 20 |
|
25 | #define NB_OF_TASKS 20 | |
26 | #define NB_OF_MISC_NAMES 5 |
|
26 | #define NB_OF_MISC_NAMES 5 | |
27 |
|
27 | |||
28 | // RTEMS GLOBAL VARIABLES |
|
28 | // RTEMS GLOBAL VARIABLES | |
29 | rtems_name misc_name[NB_OF_MISC_NAMES] = {0}; |
|
29 | rtems_name misc_name[NB_OF_MISC_NAMES] = {0}; | |
30 | rtems_name Task_name[NB_OF_TASKS] = {0}; /* array of task names */ |
|
30 | rtems_name Task_name[NB_OF_TASKS] = {0}; /* array of task names */ | |
31 | rtems_id Task_id[NB_OF_TASKS] = {0}; /* array of task ids */ |
|
31 | rtems_id Task_id[NB_OF_TASKS] = {0}; /* array of task ids */ | |
32 |
rtems_name timecode_timer_name = |
|
32 | rtems_name timecode_timer_name = 0; | |
33 |
rtems_id timecode_timer_id = |
|
33 | rtems_id timecode_timer_id = RTEMS_ID_NONE; | |
|
34 | rtems_name name_hk_rate_monotonic = 0; // name of the HK rate monotonic | |||
|
35 | rtems_id HK_id = RTEMS_ID_NONE;// id of the HK rate monotonic period | |||
|
36 | rtems_name name_avgv_rate_monotonic = 0; // name of the AVGV rate monotonic | |||
|
37 | rtems_id AVGV_id = RTEMS_ID_NONE;// id of the AVGV rate monotonic period | |||
34 | int fdSPW = 0; |
|
38 | int fdSPW = 0; | |
35 | int fdUART = 0; |
|
39 | int fdUART = 0; | |
36 | unsigned char lfrCurrentMode = 0; |
|
40 | unsigned char lfrCurrentMode = 0; | |
37 | unsigned char pa_bia_status_info = 0; |
|
41 | unsigned char pa_bia_status_info = 0; | |
38 | unsigned char thisIsAnASMRestart = 0; |
|
42 | unsigned char thisIsAnASMRestart = 0; | |
39 | unsigned char oneTcLfrUpdateTimeReceived = 0; |
|
43 | unsigned char oneTcLfrUpdateTimeReceived = 0; | |
40 |
|
44 | |||
41 | // WAVEFORMS GLOBAL VARIABLES // 2048 * 3 * 4 + 2 * 4 = 24576 + 8 bytes = 24584 |
|
45 | // WAVEFORMS GLOBAL VARIABLES // 2048 * 3 * 4 + 2 * 4 = 24576 + 8 bytes = 24584 | |
42 | // 97 * 256 = 24832 => delta = 248 bytes = 62 words |
|
46 | // 97 * 256 = 24832 => delta = 248 bytes = 62 words | |
43 | // WAVEFORMS GLOBAL VARIABLES // 2688 * 3 * 4 + 2 * 4 = 32256 + 8 bytes = 32264 |
|
47 | // WAVEFORMS GLOBAL VARIABLES // 2688 * 3 * 4 + 2 * 4 = 32256 + 8 bytes = 32264 | |
44 | // 127 * 256 = 32512 => delta = 248 bytes = 62 words |
|
48 | // 127 * 256 = 32512 => delta = 248 bytes = 62 words | |
45 | // F0 F1 F2 F3 |
|
49 | // F0 F1 F2 F3 | |
46 | volatile int wf_buffer_f0[ NB_RING_NODES_F0 * WFRM_BUFFER ] __attribute__((aligned(0x100))) = {0}; |
|
50 | volatile int wf_buffer_f0[ NB_RING_NODES_F0 * WFRM_BUFFER ] __attribute__((aligned(0x100))) = {0}; | |
47 | volatile int wf_buffer_f1[ NB_RING_NODES_F1 * WFRM_BUFFER ] __attribute__((aligned(0x100))) = {0}; |
|
51 | volatile int wf_buffer_f1[ NB_RING_NODES_F1 * WFRM_BUFFER ] __attribute__((aligned(0x100))) = {0}; | |
48 | volatile int wf_buffer_f2[ NB_RING_NODES_F2 * WFRM_BUFFER ] __attribute__((aligned(0x100))) = {0}; |
|
52 | volatile int wf_buffer_f2[ NB_RING_NODES_F2 * WFRM_BUFFER ] __attribute__((aligned(0x100))) = {0}; | |
49 | volatile int wf_buffer_f3[ NB_RING_NODES_F3 * WFRM_BUFFER ] __attribute__((aligned(0x100))) = {0}; |
|
53 | volatile int wf_buffer_f3[ NB_RING_NODES_F3 * WFRM_BUFFER ] __attribute__((aligned(0x100))) = {0}; | |
50 |
|
54 | |||
51 | //*********************************** |
|
55 | //*********************************** | |
52 | // SPECTRAL MATRICES GLOBAL VARIABLES |
|
56 | // SPECTRAL MATRICES GLOBAL VARIABLES | |
53 |
|
57 | |||
54 | // alignment constraints for the spectral matrices buffers => the first data after the time (8 bytes) shall be aligned on 0x00 |
|
58 | // alignment constraints for the spectral matrices buffers => the first data after the time (8 bytes) shall be aligned on 0x00 | |
55 | volatile int sm_f0[ NB_RING_NODES_SM_F0 * TOTAL_SIZE_SM ] __attribute__((aligned(0x100))) = {0}; |
|
59 | volatile int sm_f0[ NB_RING_NODES_SM_F0 * TOTAL_SIZE_SM ] __attribute__((aligned(0x100))) = {0}; | |
56 | volatile int sm_f1[ NB_RING_NODES_SM_F1 * TOTAL_SIZE_SM ] __attribute__((aligned(0x100))) = {0}; |
|
60 | volatile int sm_f1[ NB_RING_NODES_SM_F1 * TOTAL_SIZE_SM ] __attribute__((aligned(0x100))) = {0}; | |
57 | volatile int sm_f2[ NB_RING_NODES_SM_F2 * TOTAL_SIZE_SM ] __attribute__((aligned(0x100))) = {0}; |
|
61 | volatile int sm_f2[ NB_RING_NODES_SM_F2 * TOTAL_SIZE_SM ] __attribute__((aligned(0x100))) = {0}; | |
58 |
|
62 | |||
59 | // APB CONFIGURATION REGISTERS |
|
63 | // APB CONFIGURATION REGISTERS | |
60 | time_management_regs_t *time_management_regs = (time_management_regs_t*) REGS_ADDR_TIME_MANAGEMENT; |
|
64 | time_management_regs_t *time_management_regs = (time_management_regs_t*) REGS_ADDR_TIME_MANAGEMENT; | |
61 | gptimer_regs_t *gptimer_regs = (gptimer_regs_t *) REGS_ADDR_GPTIMER; |
|
65 | gptimer_regs_t *gptimer_regs = (gptimer_regs_t *) REGS_ADDR_GPTIMER; | |
62 | waveform_picker_regs_0_1_18_t *waveform_picker_regs = (waveform_picker_regs_0_1_18_t*) REGS_ADDR_WAVEFORM_PICKER; |
|
66 | waveform_picker_regs_0_1_18_t *waveform_picker_regs = (waveform_picker_regs_0_1_18_t*) REGS_ADDR_WAVEFORM_PICKER; | |
63 | spectral_matrix_regs_t *spectral_matrix_regs = (spectral_matrix_regs_t*) REGS_ADDR_SPECTRAL_MATRIX; |
|
67 | spectral_matrix_regs_t *spectral_matrix_regs = (spectral_matrix_regs_t*) REGS_ADDR_SPECTRAL_MATRIX; | |
64 |
|
68 | |||
65 | // MODE PARAMETERS |
|
69 | // MODE PARAMETERS | |
66 | Packet_TM_LFR_PARAMETER_DUMP_t parameter_dump_packet = {0}; |
|
70 | Packet_TM_LFR_PARAMETER_DUMP_t parameter_dump_packet = {0}; | |
67 | struct param_local_str param_local = {0}; |
|
71 | struct param_local_str param_local = {0}; | |
68 | unsigned int lastValidEnterModeTime = {0}; |
|
72 | unsigned int lastValidEnterModeTime = {0}; | |
69 |
|
73 | |||
70 | // HK PACKETS |
|
74 | // HK PACKETS | |
71 | Packet_TM_LFR_HK_t housekeeping_packet = {0}; |
|
75 | Packet_TM_LFR_HK_t housekeeping_packet = {0}; | |
72 | unsigned char cp_rpw_sc_rw_f_flags = 0; |
|
76 | unsigned char cp_rpw_sc_rw_f_flags = 0; | |
73 | // message queues occupancy |
|
77 | // message queues occupancy | |
74 | unsigned char hk_lfr_q_sd_fifo_size_max = 0; |
|
78 | unsigned char hk_lfr_q_sd_fifo_size_max = 0; | |
75 | unsigned char hk_lfr_q_rv_fifo_size_max = 0; |
|
79 | unsigned char hk_lfr_q_rv_fifo_size_max = 0; | |
76 | unsigned char hk_lfr_q_p0_fifo_size_max = 0; |
|
80 | unsigned char hk_lfr_q_p0_fifo_size_max = 0; | |
77 | unsigned char hk_lfr_q_p1_fifo_size_max = 0; |
|
81 | unsigned char hk_lfr_q_p1_fifo_size_max = 0; | |
78 | unsigned char hk_lfr_q_p2_fifo_size_max = 0; |
|
82 | unsigned char hk_lfr_q_p2_fifo_size_max = 0; | |
79 | // sequence counters are incremented by APID (PID + CAT) and destination ID |
|
83 | // sequence counters are incremented by APID (PID + CAT) and destination ID | |
80 | unsigned short sequenceCounters_SCIENCE_NORMAL_BURST = 0; |
|
84 | unsigned short sequenceCounters_SCIENCE_NORMAL_BURST = 0; | |
81 | unsigned short sequenceCounters_SCIENCE_SBM1_SBM2 = 0; |
|
85 | unsigned short sequenceCounters_SCIENCE_SBM1_SBM2 = 0; | |
82 | unsigned short sequenceCounters_TC_EXE[SEQ_CNT_NB_DEST_ID] = {0}; |
|
86 | unsigned short sequenceCounters_TC_EXE[SEQ_CNT_NB_DEST_ID] = {0}; | |
83 | unsigned short sequenceCounters_TM_DUMP[SEQ_CNT_NB_DEST_ID] = {0}; |
|
87 | unsigned short sequenceCounters_TM_DUMP[SEQ_CNT_NB_DEST_ID] = {0}; | |
84 | unsigned short sequenceCounterHK; |
|
88 | unsigned short sequenceCounterHK; | |
85 | spw_stats grspw_stats = {0}; |
|
89 | spw_stats grspw_stats = {0}; | |
86 |
|
90 | |||
87 | // TC_LFR_UPDATE_INFO |
|
91 | // TC_LFR_UPDATE_INFO | |
88 | float cp_rpw_sc_rw1_f1 = INIT_FLOAT; |
|
92 | float cp_rpw_sc_rw1_f1 = INIT_FLOAT; | |
89 | float cp_rpw_sc_rw1_f2 = INIT_FLOAT; |
|
93 | float cp_rpw_sc_rw1_f2 = INIT_FLOAT; | |
90 | float cp_rpw_sc_rw2_f1 = INIT_FLOAT; |
|
94 | float cp_rpw_sc_rw2_f1 = INIT_FLOAT; | |
91 | float cp_rpw_sc_rw2_f2 = INIT_FLOAT; |
|
95 | float cp_rpw_sc_rw2_f2 = INIT_FLOAT; | |
92 | float cp_rpw_sc_rw3_f1 = INIT_FLOAT; |
|
96 | float cp_rpw_sc_rw3_f1 = INIT_FLOAT; | |
93 | float cp_rpw_sc_rw3_f2 = INIT_FLOAT; |
|
97 | float cp_rpw_sc_rw3_f2 = INIT_FLOAT; | |
94 | float cp_rpw_sc_rw4_f1 = INIT_FLOAT; |
|
98 | float cp_rpw_sc_rw4_f1 = INIT_FLOAT; | |
95 | float cp_rpw_sc_rw4_f2 = INIT_FLOAT; |
|
99 | float cp_rpw_sc_rw4_f2 = INIT_FLOAT; | |
96 |
|
100 | |||
97 | // TC_LFR_LOAD_FILTER_PAR |
|
101 | // TC_LFR_LOAD_FILTER_PAR | |
98 | filterPar_t filterPar = {0}; |
|
102 | filterPar_t filterPar = {0}; | |
99 |
|
103 | |||
100 | fbins_masks_t fbins_masks = {0}; |
|
104 | fbins_masks_t fbins_masks = {0}; | |
101 | unsigned int acquisitionDurations[NB_ACQUISITION_DURATION] |
|
105 | unsigned int acquisitionDurations[NB_ACQUISITION_DURATION] | |
102 | = {ACQUISITION_DURATION_F0, ACQUISITION_DURATION_F1, ACQUISITION_DURATION_F2}; |
|
106 | = {ACQUISITION_DURATION_F0, ACQUISITION_DURATION_F1, ACQUISITION_DURATION_F2}; |
@@ -1,1631 +1,1631 | |||||
1 | /** Functions related to the SpaceWire interface. |
|
1 | /** Functions related to the SpaceWire interface. | |
2 | * |
|
2 | * | |
3 | * @file |
|
3 | * @file | |
4 | * @author P. LEROY |
|
4 | * @author P. LEROY | |
5 | * |
|
5 | * | |
6 | * A group of functions to handle SpaceWire transmissions: |
|
6 | * A group of functions to handle SpaceWire transmissions: | |
7 | * - configuration of the SpaceWire link |
|
7 | * - configuration of the SpaceWire link | |
8 | * - SpaceWire related interruption requests processing |
|
8 | * - SpaceWire related interruption requests processing | |
9 | * - transmission of TeleMetry packets by a dedicated RTEMS task |
|
9 | * - transmission of TeleMetry packets by a dedicated RTEMS task | |
10 | * - reception of TeleCommands by a dedicated RTEMS task |
|
10 | * - reception of TeleCommands by a dedicated RTEMS task | |
11 | * |
|
11 | * | |
12 | */ |
|
12 | */ | |
13 |
|
13 | |||
14 | #include "fsw_spacewire.h" |
|
14 | #include "fsw_spacewire.h" | |
15 |
|
15 | |||
16 | rtems_name semq_name = 0; |
|
16 | rtems_name semq_name = 0; | |
17 | rtems_id semq_id = RTEMS_ID_NONE; |
|
17 | rtems_id semq_id = RTEMS_ID_NONE; | |
18 |
|
18 | |||
19 | //***************** |
|
19 | //***************** | |
20 | // waveform headers |
|
20 | // waveform headers | |
21 | Header_TM_LFR_SCIENCE_CWF_t headerCWF = {0}; |
|
21 | Header_TM_LFR_SCIENCE_CWF_t headerCWF = {0}; | |
22 |
Header_TM_LFR_SCIENCE_SWF_t headerSW |
|
22 | Header_TM_LFR_SCIENCE_SWF_t headerSWF = {0}; | |
23 | Header_TM_LFR_SCIENCE_ASM_t headerASM = {0}; |
|
23 | Header_TM_LFR_SCIENCE_ASM_t headerASM = {0}; | |
24 |
|
24 | |||
25 | unsigned char previousTimecodeCtr = 0; |
|
25 | unsigned char previousTimecodeCtr = 0; | |
26 | unsigned int *grspwPtr = (unsigned int *) (REGS_ADDR_GRSPW + APB_OFFSET_GRSPW_TIME_REGISTER); |
|
26 | unsigned int *grspwPtr = (unsigned int *) (REGS_ADDR_GRSPW + APB_OFFSET_GRSPW_TIME_REGISTER); | |
27 |
|
27 | |||
28 | //*********** |
|
28 | //*********** | |
29 | // RTEMS TASK |
|
29 | // RTEMS TASK | |
30 | rtems_task spiq_task(rtems_task_argument unused) |
|
30 | rtems_task spiq_task(rtems_task_argument unused) | |
31 | { |
|
31 | { | |
32 | /** This RTEMS task is awaken by an rtems_event sent by the interruption subroutine of the SpaceWire driver. |
|
32 | /** This RTEMS task is awaken by an rtems_event sent by the interruption subroutine of the SpaceWire driver. | |
33 | * |
|
33 | * | |
34 | * @param unused is the starting argument of the RTEMS task |
|
34 | * @param unused is the starting argument of the RTEMS task | |
35 | * |
|
35 | * | |
36 | */ |
|
36 | */ | |
37 |
|
37 | |||
38 | rtems_event_set event_out; |
|
38 | rtems_event_set event_out; | |
39 | rtems_status_code status; |
|
39 | rtems_status_code status; | |
40 | int linkStatus; |
|
40 | int linkStatus; | |
41 |
|
41 | |||
42 | event_out = EVENT_SETS_NONE_PENDING; |
|
42 | event_out = EVENT_SETS_NONE_PENDING; | |
43 | linkStatus = 0; |
|
43 | linkStatus = 0; | |
44 |
|
44 | |||
45 | BOOT_PRINTF("in SPIQ *** \n") |
|
45 | BOOT_PRINTF("in SPIQ *** \n") | |
46 |
|
46 | |||
47 | while(true){ |
|
47 | while(true){ | |
48 | rtems_event_receive(SPW_LINKERR_EVENT, RTEMS_WAIT, RTEMS_NO_TIMEOUT, &event_out); // wait for an SPW_LINKERR_EVENT |
|
48 | rtems_event_receive(SPW_LINKERR_EVENT, RTEMS_WAIT, RTEMS_NO_TIMEOUT, &event_out); // wait for an SPW_LINKERR_EVENT | |
49 | PRINTF("in SPIQ *** got SPW_LINKERR_EVENT\n") |
|
49 | PRINTF("in SPIQ *** got SPW_LINKERR_EVENT\n") | |
50 |
|
50 | |||
51 | // [0] SUSPEND RECV AND SEND TASKS |
|
51 | // [0] SUSPEND RECV AND SEND TASKS | |
52 | status = rtems_task_suspend( Task_id[ TASKID_RECV ] ); |
|
52 | status = rtems_task_suspend( Task_id[ TASKID_RECV ] ); | |
53 | if ( status != RTEMS_SUCCESSFUL ) { |
|
53 | if ( status != RTEMS_SUCCESSFUL ) { | |
54 | PRINTF("in SPIQ *** ERR suspending RECV Task\n") |
|
54 | PRINTF("in SPIQ *** ERR suspending RECV Task\n") | |
55 | } |
|
55 | } | |
56 | status = rtems_task_suspend( Task_id[ TASKID_SEND ] ); |
|
56 | status = rtems_task_suspend( Task_id[ TASKID_SEND ] ); | |
57 | if ( status != RTEMS_SUCCESSFUL ) { |
|
57 | if ( status != RTEMS_SUCCESSFUL ) { | |
58 | PRINTF("in SPIQ *** ERR suspending SEND Task\n") |
|
58 | PRINTF("in SPIQ *** ERR suspending SEND Task\n") | |
59 | } |
|
59 | } | |
60 |
|
60 | |||
61 | // [1] CHECK THE LINK |
|
61 | // [1] CHECK THE LINK | |
62 | status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status (1) |
|
62 | status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status (1) | |
63 | if ( linkStatus != SPW_LINK_OK) { |
|
63 | if ( linkStatus != SPW_LINK_OK) { | |
64 | PRINTF1("in SPIQ *** linkStatus %d, wait...\n", linkStatus) |
|
64 | PRINTF1("in SPIQ *** linkStatus %d, wait...\n", linkStatus) | |
65 | status = rtems_task_wake_after( SY_LFR_DPU_CONNECT_TIMEOUT ); // wait SY_LFR_DPU_CONNECT_TIMEOUT 1000 ms |
|
65 | status = rtems_task_wake_after( SY_LFR_DPU_CONNECT_TIMEOUT ); // wait SY_LFR_DPU_CONNECT_TIMEOUT 1000 ms | |
66 | } |
|
66 | } | |
67 |
|
67 | |||
68 | // [2] RECHECK THE LINK AFTER SY_LFR_DPU_CONNECT_TIMEOUT |
|
68 | // [2] RECHECK THE LINK AFTER SY_LFR_DPU_CONNECT_TIMEOUT | |
69 | status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status (2) |
|
69 | status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status (2) | |
70 | if ( linkStatus != SPW_LINK_OK ) // [2.a] not in run state, reset the link |
|
70 | if ( linkStatus != SPW_LINK_OK ) // [2.a] not in run state, reset the link | |
71 | { |
|
71 | { | |
72 | spacewire_read_statistics(); |
|
72 | spacewire_read_statistics(); | |
73 | status = spacewire_several_connect_attemps( ); |
|
73 | status = spacewire_several_connect_attemps( ); | |
74 | } |
|
74 | } | |
75 | else // [2.b] in run state, start the link |
|
75 | else // [2.b] in run state, start the link | |
76 | { |
|
76 | { | |
77 | status = spacewire_stop_and_start_link( fdSPW ); // start the link |
|
77 | status = spacewire_stop_and_start_link( fdSPW ); // start the link | |
78 | if ( status != RTEMS_SUCCESSFUL) |
|
78 | if ( status != RTEMS_SUCCESSFUL) | |
79 | { |
|
79 | { | |
80 | PRINTF1("in SPIQ *** ERR spacewire_stop_and_start_link %d\n", status) |
|
80 | PRINTF1("in SPIQ *** ERR spacewire_stop_and_start_link %d\n", status) | |
81 | } |
|
81 | } | |
82 | } |
|
82 | } | |
83 |
|
83 | |||
84 | // [3] COMPLETE RECOVERY ACTION AFTER SY_LFR_DPU_CONNECT_ATTEMPTS |
|
84 | // [3] COMPLETE RECOVERY ACTION AFTER SY_LFR_DPU_CONNECT_ATTEMPTS | |
85 | if ( status == RTEMS_SUCCESSFUL ) // [3.a] the link is in run state and has been started successfully |
|
85 | if ( status == RTEMS_SUCCESSFUL ) // [3.a] the link is in run state and has been started successfully | |
86 | { |
|
86 | { | |
87 | status = rtems_task_restart( Task_id[ TASKID_SEND ], 1 ); |
|
87 | status = rtems_task_restart( Task_id[ TASKID_SEND ], 1 ); | |
88 | if ( status != RTEMS_SUCCESSFUL ) { |
|
88 | if ( status != RTEMS_SUCCESSFUL ) { | |
89 | PRINTF("in SPIQ *** ERR resuming SEND Task\n") |
|
89 | PRINTF("in SPIQ *** ERR resuming SEND Task\n") | |
90 | } |
|
90 | } | |
91 | status = rtems_task_restart( Task_id[ TASKID_RECV ], 1 ); |
|
91 | status = rtems_task_restart( Task_id[ TASKID_RECV ], 1 ); | |
92 | if ( status != RTEMS_SUCCESSFUL ) { |
|
92 | if ( status != RTEMS_SUCCESSFUL ) { | |
93 | PRINTF("in SPIQ *** ERR resuming RECV Task\n") |
|
93 | PRINTF("in SPIQ *** ERR resuming RECV Task\n") | |
94 | } |
|
94 | } | |
95 | } |
|
95 | } | |
96 | else // [3.b] the link is not in run state, go in STANDBY mode |
|
96 | else // [3.b] the link is not in run state, go in STANDBY mode | |
97 | { |
|
97 | { | |
98 | status = enter_mode_standby(); |
|
98 | status = enter_mode_standby(); | |
99 | if ( status != RTEMS_SUCCESSFUL ) |
|
99 | if ( status != RTEMS_SUCCESSFUL ) | |
100 | { |
|
100 | { | |
101 | PRINTF1("in SPIQ *** ERR enter_standby_mode *** code %d\n", status) |
|
101 | PRINTF1("in SPIQ *** ERR enter_standby_mode *** code %d\n", status) | |
102 | } |
|
102 | } | |
103 | { |
|
103 | { | |
104 | updateLFRCurrentMode( LFR_MODE_STANDBY ); |
|
104 | updateLFRCurrentMode( LFR_MODE_STANDBY ); | |
105 | } |
|
105 | } | |
106 | // wake the LINK task up to wait for the link recovery |
|
106 | // wake the LINK task up to wait for the link recovery | |
107 | status = rtems_event_send ( Task_id[TASKID_LINK], RTEMS_EVENT_0 ); |
|
107 | status = rtems_event_send ( Task_id[TASKID_LINK], RTEMS_EVENT_0 ); | |
108 | status = rtems_task_suspend( RTEMS_SELF ); |
|
108 | status = rtems_task_suspend( RTEMS_SELF ); | |
109 | } |
|
109 | } | |
110 | } |
|
110 | } | |
111 | } |
|
111 | } | |
112 |
|
112 | |||
113 | rtems_task recv_task( rtems_task_argument unused ) |
|
113 | rtems_task recv_task( rtems_task_argument unused ) | |
114 | { |
|
114 | { | |
115 | /** This RTEMS task is dedicated to the reception of incoming TeleCommands. |
|
115 | /** This RTEMS task is dedicated to the reception of incoming TeleCommands. | |
116 | * |
|
116 | * | |
117 | * @param unused is the starting argument of the RTEMS task |
|
117 | * @param unused is the starting argument of the RTEMS task | |
118 | * |
|
118 | * | |
119 | * The RECV task blocks on a call to the read system call, waiting for incoming SpaceWire data. When unblocked: |
|
119 | * The RECV task blocks on a call to the read system call, waiting for incoming SpaceWire data. When unblocked: | |
120 | * 1. It reads the incoming data. |
|
120 | * 1. It reads the incoming data. | |
121 | * 2. Launches the acceptance procedure. |
|
121 | * 2. Launches the acceptance procedure. | |
122 | * 3. If the Telecommand is valid, sends it to a dedicated RTEMS message queue. |
|
122 | * 3. If the Telecommand is valid, sends it to a dedicated RTEMS message queue. | |
123 | * |
|
123 | * | |
124 | */ |
|
124 | */ | |
125 |
|
125 | |||
126 | int len; |
|
126 | int len; | |
127 | ccsdsTelecommandPacket_t currentTC; |
|
127 | ccsdsTelecommandPacket_t currentTC; | |
128 | unsigned char computed_CRC[ BYTES_PER_CRC ]; |
|
128 | unsigned char computed_CRC[ BYTES_PER_CRC ]; | |
129 | unsigned char currentTC_LEN_RCV[ BYTES_PER_PKT_LEN ]; |
|
129 | unsigned char currentTC_LEN_RCV[ BYTES_PER_PKT_LEN ]; | |
130 | unsigned char destinationID; |
|
130 | unsigned char destinationID; | |
131 | unsigned int estimatedPacketLength; |
|
131 | unsigned int estimatedPacketLength; | |
132 | unsigned int parserCode; |
|
132 | unsigned int parserCode; | |
133 | rtems_status_code status; |
|
133 | rtems_status_code status; | |
134 | rtems_id queue_recv_id; |
|
134 | rtems_id queue_recv_id; | |
135 | rtems_id queue_send_id; |
|
135 | rtems_id queue_send_id; | |
136 |
|
136 | |||
137 | memset( ¤tTC, 0, sizeof(ccsdsTelecommandPacket_t) ); |
|
137 | memset( ¤tTC, 0, sizeof(ccsdsTelecommandPacket_t) ); | |
138 | destinationID = 0; |
|
138 | destinationID = 0; | |
139 | queue_recv_id = RTEMS_ID_NONE; |
|
139 | queue_recv_id = RTEMS_ID_NONE; | |
140 | queue_send_id = RTEMS_ID_NONE; |
|
140 | queue_send_id = RTEMS_ID_NONE; | |
141 |
|
141 | |||
142 | initLookUpTableForCRC(); // the table is used to compute Cyclic Redundancy Codes |
|
142 | initLookUpTableForCRC(); // the table is used to compute Cyclic Redundancy Codes | |
143 |
|
143 | |||
144 | status = get_message_queue_id_recv( &queue_recv_id ); |
|
144 | status = get_message_queue_id_recv( &queue_recv_id ); | |
145 | if (status != RTEMS_SUCCESSFUL) |
|
145 | if (status != RTEMS_SUCCESSFUL) | |
146 | { |
|
146 | { | |
147 | PRINTF1("in RECV *** ERR get_message_queue_id_recv %d\n", status) |
|
147 | PRINTF1("in RECV *** ERR get_message_queue_id_recv %d\n", status) | |
148 | } |
|
148 | } | |
149 |
|
149 | |||
150 | status = get_message_queue_id_send( &queue_send_id ); |
|
150 | status = get_message_queue_id_send( &queue_send_id ); | |
151 | if (status != RTEMS_SUCCESSFUL) |
|
151 | if (status != RTEMS_SUCCESSFUL) | |
152 | { |
|
152 | { | |
153 | PRINTF1("in RECV *** ERR get_message_queue_id_send %d\n", status) |
|
153 | PRINTF1("in RECV *** ERR get_message_queue_id_send %d\n", status) | |
154 | } |
|
154 | } | |
155 |
|
155 | |||
156 | BOOT_PRINTF("in RECV *** \n") |
|
156 | BOOT_PRINTF("in RECV *** \n") | |
157 |
|
157 | |||
158 | while(1) |
|
158 | while(1) | |
159 | { |
|
159 | { | |
160 | len = read( fdSPW, (char*) ¤tTC, CCSDS_TC_PKT_MAX_SIZE ); // the call to read is blocking |
|
160 | len = read( fdSPW, (char*) ¤tTC, CCSDS_TC_PKT_MAX_SIZE ); // the call to read is blocking | |
161 | if (len == -1){ // error during the read call |
|
161 | if (len == -1){ // error during the read call | |
162 | PRINTF1("in RECV *** last read call returned -1, ERRNO %d\n", errno) |
|
162 | PRINTF1("in RECV *** last read call returned -1, ERRNO %d\n", errno) | |
163 | } |
|
163 | } | |
164 | else { |
|
164 | else { | |
165 | if ( (len+1) < CCSDS_TC_PKT_MIN_SIZE ) { |
|
165 | if ( (len+1) < CCSDS_TC_PKT_MIN_SIZE ) { | |
166 | PRINTF("in RECV *** packet lenght too short\n") |
|
166 | PRINTF("in RECV *** packet lenght too short\n") | |
167 | } |
|
167 | } | |
168 | else { |
|
168 | else { | |
169 | estimatedPacketLength = (unsigned int) (len - CCSDS_TC_TM_PACKET_OFFSET - PROTID_RES_APP); // => -3 is for Prot ID, Reserved and User App bytes |
|
169 | estimatedPacketLength = (unsigned int) (len - CCSDS_TC_TM_PACKET_OFFSET - PROTID_RES_APP); // => -3 is for Prot ID, Reserved and User App bytes | |
170 | //PRINTF1("incoming TC with Length (byte): %d\n", len - 3); |
|
170 | //PRINTF1("incoming TC with Length (byte): %d\n", len - 3); | |
171 | currentTC_LEN_RCV[ 0 ] = (unsigned char) (estimatedPacketLength >> SHIFT_1_BYTE); |
|
171 | currentTC_LEN_RCV[ 0 ] = (unsigned char) (estimatedPacketLength >> SHIFT_1_BYTE); | |
172 | currentTC_LEN_RCV[ 1 ] = (unsigned char) (estimatedPacketLength ); |
|
172 | currentTC_LEN_RCV[ 1 ] = (unsigned char) (estimatedPacketLength ); | |
173 | // CHECK THE TC |
|
173 | // CHECK THE TC | |
174 | parserCode = tc_parser( ¤tTC, estimatedPacketLength, computed_CRC ) ; |
|
174 | parserCode = tc_parser( ¤tTC, estimatedPacketLength, computed_CRC ) ; | |
175 | if ( (parserCode == ILLEGAL_APID) || (parserCode == WRONG_LEN_PKT) |
|
175 | if ( (parserCode == ILLEGAL_APID) || (parserCode == WRONG_LEN_PKT) | |
176 | || (parserCode == INCOR_CHECKSUM) || (parserCode == ILL_TYPE) |
|
176 | || (parserCode == INCOR_CHECKSUM) || (parserCode == ILL_TYPE) | |
177 | || (parserCode == ILL_SUBTYPE) || (parserCode == WRONG_APP_DATA) |
|
177 | || (parserCode == ILL_SUBTYPE) || (parserCode == WRONG_APP_DATA) | |
178 | || (parserCode == WRONG_SRC_ID) ) |
|
178 | || (parserCode == WRONG_SRC_ID) ) | |
179 | { // send TM_LFR_TC_EXE_CORRUPTED |
|
179 | { // send TM_LFR_TC_EXE_CORRUPTED | |
180 | PRINTF1("TC corrupted received, with code: %d\n", parserCode); |
|
180 | PRINTF1("TC corrupted received, with code: %d\n", parserCode); | |
181 | if ( !( (currentTC.serviceType==TC_TYPE_TIME) && (currentTC.serviceSubType==TC_SUBTYPE_UPDT_TIME) ) |
|
181 | if ( !( (currentTC.serviceType==TC_TYPE_TIME) && (currentTC.serviceSubType==TC_SUBTYPE_UPDT_TIME) ) | |
182 | && |
|
182 | && | |
183 | !( (currentTC.serviceType==TC_TYPE_GEN) && (currentTC.serviceSubType==TC_SUBTYPE_UPDT_INFO)) |
|
183 | !( (currentTC.serviceType==TC_TYPE_GEN) && (currentTC.serviceSubType==TC_SUBTYPE_UPDT_INFO)) | |
184 | ) |
|
184 | ) | |
185 | { |
|
185 | { | |
186 | if ( parserCode == WRONG_SRC_ID ) |
|
186 | if ( parserCode == WRONG_SRC_ID ) | |
187 | { |
|
187 | { | |
188 | destinationID = SID_TC_GROUND; |
|
188 | destinationID = SID_TC_GROUND; | |
189 | } |
|
189 | } | |
190 | else |
|
190 | else | |
191 | { |
|
191 | { | |
192 | destinationID = currentTC.sourceID; |
|
192 | destinationID = currentTC.sourceID; | |
193 | } |
|
193 | } | |
194 | send_tm_lfr_tc_exe_corrupted( ¤tTC, queue_send_id, |
|
194 | send_tm_lfr_tc_exe_corrupted( ¤tTC, queue_send_id, | |
195 | computed_CRC, currentTC_LEN_RCV, |
|
195 | computed_CRC, currentTC_LEN_RCV, | |
196 | destinationID ); |
|
196 | destinationID ); | |
197 | } |
|
197 | } | |
198 | } |
|
198 | } | |
199 | else |
|
199 | else | |
200 | { // send valid TC to the action launcher |
|
200 | { // send valid TC to the action launcher | |
201 | status = rtems_message_queue_send( queue_recv_id, ¤tTC, |
|
201 | status = rtems_message_queue_send( queue_recv_id, ¤tTC, | |
202 | estimatedPacketLength + CCSDS_TC_TM_PACKET_OFFSET + PROTID_RES_APP); |
|
202 | estimatedPacketLength + CCSDS_TC_TM_PACKET_OFFSET + PROTID_RES_APP); | |
203 | } |
|
203 | } | |
204 | } |
|
204 | } | |
205 | } |
|
205 | } | |
206 |
|
206 | |||
207 | update_queue_max_count( queue_recv_id, &hk_lfr_q_rv_fifo_size_max ); |
|
207 | update_queue_max_count( queue_recv_id, &hk_lfr_q_rv_fifo_size_max ); | |
208 |
|
208 | |||
209 | } |
|
209 | } | |
210 | } |
|
210 | } | |
211 |
|
211 | |||
212 | rtems_task send_task( rtems_task_argument argument) |
|
212 | rtems_task send_task( rtems_task_argument argument) | |
213 | { |
|
213 | { | |
214 | /** This RTEMS task is dedicated to the transmission of TeleMetry packets. |
|
214 | /** This RTEMS task is dedicated to the transmission of TeleMetry packets. | |
215 | * |
|
215 | * | |
216 | * @param unused is the starting argument of the RTEMS task |
|
216 | * @param unused is the starting argument of the RTEMS task | |
217 | * |
|
217 | * | |
218 | * The SEND task waits for a message to become available in the dedicated RTEMS queue. When a message arrives: |
|
218 | * The SEND task waits for a message to become available in the dedicated RTEMS queue. When a message arrives: | |
219 | * - if the first byte is equal to CCSDS_DESTINATION_ID, the message is sent as is using the write system call. |
|
219 | * - if the first byte is equal to CCSDS_DESTINATION_ID, the message is sent as is using the write system call. | |
220 | * - if the first byte is not equal to CCSDS_DESTINATION_ID, the message is handled as a spw_ioctl_pkt_send. After |
|
220 | * - if the first byte is not equal to CCSDS_DESTINATION_ID, the message is handled as a spw_ioctl_pkt_send. After | |
221 | * analyzis, the packet is sent either using the write system call or using the ioctl call SPACEWIRE_IOCTRL_SEND, depending on the |
|
221 | * analyzis, the packet is sent either using the write system call or using the ioctl call SPACEWIRE_IOCTRL_SEND, depending on the | |
222 | * data it contains. |
|
222 | * data it contains. | |
223 | * |
|
223 | * | |
224 | */ |
|
224 | */ | |
225 |
|
225 | |||
226 | rtems_status_code status; // RTEMS status code |
|
226 | rtems_status_code status; // RTEMS status code | |
227 | char incomingData[MSG_QUEUE_SIZE_SEND]; // incoming data buffer |
|
227 | char incomingData[MSG_QUEUE_SIZE_SEND]; // incoming data buffer | |
228 | ring_node *incomingRingNodePtr; |
|
228 | ring_node *incomingRingNodePtr; | |
229 | int ring_node_address; |
|
229 | int ring_node_address; | |
230 | char *charPtr; |
|
230 | char *charPtr; | |
231 | spw_ioctl_pkt_send *spw_ioctl_send; |
|
231 | spw_ioctl_pkt_send *spw_ioctl_send; | |
232 | size_t size; // size of the incoming TC packet |
|
232 | size_t size; // size of the incoming TC packet | |
233 | rtems_id queue_send_id; |
|
233 | rtems_id queue_send_id; | |
234 | unsigned int sid; |
|
234 | unsigned int sid; | |
235 | unsigned char sidAsUnsignedChar; |
|
235 | unsigned char sidAsUnsignedChar; | |
236 | unsigned char type; |
|
236 | unsigned char type; | |
237 |
|
237 | |||
238 | incomingRingNodePtr = NULL; |
|
238 | incomingRingNodePtr = NULL; | |
239 | ring_node_address = 0; |
|
239 | ring_node_address = 0; | |
240 | charPtr = (char *) &ring_node_address; |
|
240 | charPtr = (char *) &ring_node_address; | |
241 | size = 0; |
|
241 | size = 0; | |
242 | queue_send_id = RTEMS_ID_NONE; |
|
242 | queue_send_id = RTEMS_ID_NONE; | |
243 | sid = 0; |
|
243 | sid = 0; | |
244 | sidAsUnsignedChar = 0; |
|
244 | sidAsUnsignedChar = 0; | |
245 |
|
245 | |||
246 | init_header_cwf( &headerCWF ); |
|
246 | init_header_cwf( &headerCWF ); | |
247 | init_header_swf( &headerSWF ); |
|
247 | init_header_swf( &headerSWF ); | |
248 | init_header_asm( &headerASM ); |
|
248 | init_header_asm( &headerASM ); | |
249 |
|
249 | |||
250 | status = get_message_queue_id_send( &queue_send_id ); |
|
250 | status = get_message_queue_id_send( &queue_send_id ); | |
251 | if (status != RTEMS_SUCCESSFUL) |
|
251 | if (status != RTEMS_SUCCESSFUL) | |
252 | { |
|
252 | { | |
253 | PRINTF1("in HOUS *** ERR get_message_queue_id_send %d\n", status) |
|
253 | PRINTF1("in HOUS *** ERR get_message_queue_id_send %d\n", status) | |
254 | } |
|
254 | } | |
255 |
|
255 | |||
256 | BOOT_PRINTF("in SEND *** \n") |
|
256 | BOOT_PRINTF("in SEND *** \n") | |
257 |
|
257 | |||
258 | while(1) |
|
258 | while(1) | |
259 | { |
|
259 | { | |
260 | status = rtems_message_queue_receive( queue_send_id, incomingData, &size, |
|
260 | status = rtems_message_queue_receive( queue_send_id, incomingData, &size, | |
261 | RTEMS_WAIT, RTEMS_NO_TIMEOUT ); |
|
261 | RTEMS_WAIT, RTEMS_NO_TIMEOUT ); | |
262 |
|
262 | |||
263 | if (status!=RTEMS_SUCCESSFUL) |
|
263 | if (status!=RTEMS_SUCCESSFUL) | |
264 | { |
|
264 | { | |
265 | PRINTF1("in SEND *** (1) ERR = %d\n", status) |
|
265 | PRINTF1("in SEND *** (1) ERR = %d\n", status) | |
266 | } |
|
266 | } | |
267 | else |
|
267 | else | |
268 | { |
|
268 | { | |
269 | if ( size == sizeof(ring_node*) ) |
|
269 | if ( size == sizeof(ring_node*) ) | |
270 | { |
|
270 | { | |
271 | charPtr[0] = incomingData[0]; |
|
271 | charPtr[0] = incomingData[0]; | |
272 | charPtr[1] = incomingData[1]; |
|
272 | charPtr[1] = incomingData[1]; | |
273 | charPtr[BYTE_2] = incomingData[BYTE_2]; |
|
273 | charPtr[BYTE_2] = incomingData[BYTE_2]; | |
274 | charPtr[BYTE_3] = incomingData[BYTE_3]; |
|
274 | charPtr[BYTE_3] = incomingData[BYTE_3]; | |
275 | incomingRingNodePtr = (ring_node*) ring_node_address; |
|
275 | incomingRingNodePtr = (ring_node*) ring_node_address; | |
276 | sid = incomingRingNodePtr->sid; |
|
276 | sid = incomingRingNodePtr->sid; | |
277 | if ( (sid==SID_NORM_CWF_LONG_F3) |
|
277 | if ( (sid==SID_NORM_CWF_LONG_F3) | |
278 | || (sid==SID_BURST_CWF_F2 ) |
|
278 | || (sid==SID_BURST_CWF_F2 ) | |
279 | || (sid==SID_SBM1_CWF_F1 ) |
|
279 | || (sid==SID_SBM1_CWF_F1 ) | |
280 | || (sid==SID_SBM2_CWF_F2 )) |
|
280 | || (sid==SID_SBM2_CWF_F2 )) | |
281 | { |
|
281 | { | |
282 | spw_send_waveform_CWF( incomingRingNodePtr, &headerCWF ); |
|
282 | spw_send_waveform_CWF( incomingRingNodePtr, &headerCWF ); | |
283 | } |
|
283 | } | |
284 | else if ( (sid==SID_NORM_SWF_F0) || (sid== SID_NORM_SWF_F1) || (sid==SID_NORM_SWF_F2) ) |
|
284 | else if ( (sid==SID_NORM_SWF_F0) || (sid== SID_NORM_SWF_F1) || (sid==SID_NORM_SWF_F2) ) | |
285 | { |
|
285 | { | |
286 | spw_send_waveform_SWF( incomingRingNodePtr, &headerSWF ); |
|
286 | spw_send_waveform_SWF( incomingRingNodePtr, &headerSWF ); | |
287 | } |
|
287 | } | |
288 | else if ( (sid==SID_NORM_CWF_F3) ) |
|
288 | else if ( (sid==SID_NORM_CWF_F3) ) | |
289 | { |
|
289 | { | |
290 | spw_send_waveform_CWF3_light( incomingRingNodePtr, &headerCWF ); |
|
290 | spw_send_waveform_CWF3_light( incomingRingNodePtr, &headerCWF ); | |
291 | } |
|
291 | } | |
292 | else if (sid==SID_NORM_ASM_F0) |
|
292 | else if (sid==SID_NORM_ASM_F0) | |
293 | { |
|
293 | { | |
294 | spw_send_asm_f0( incomingRingNodePtr, &headerASM ); |
|
294 | spw_send_asm_f0( incomingRingNodePtr, &headerASM ); | |
295 | } |
|
295 | } | |
296 | else if (sid==SID_NORM_ASM_F1) |
|
296 | else if (sid==SID_NORM_ASM_F1) | |
297 | { |
|
297 | { | |
298 | spw_send_asm_f1( incomingRingNodePtr, &headerASM ); |
|
298 | spw_send_asm_f1( incomingRingNodePtr, &headerASM ); | |
299 | } |
|
299 | } | |
300 | else if (sid==SID_NORM_ASM_F2) |
|
300 | else if (sid==SID_NORM_ASM_F2) | |
301 | { |
|
301 | { | |
302 | spw_send_asm_f2( incomingRingNodePtr, &headerASM ); |
|
302 | spw_send_asm_f2( incomingRingNodePtr, &headerASM ); | |
303 | } |
|
303 | } | |
304 | else if ( sid==TM_CODE_K_DUMP ) |
|
304 | else if ( sid==TM_CODE_K_DUMP ) | |
305 | { |
|
305 | { | |
306 | spw_send_k_dump( incomingRingNodePtr ); |
|
306 | spw_send_k_dump( incomingRingNodePtr ); | |
307 | } |
|
307 | } | |
308 | else |
|
308 | else | |
309 | { |
|
309 | { | |
310 | PRINTF1("unexpected sid = %d\n", sid); |
|
310 | PRINTF1("unexpected sid = %d\n", sid); | |
311 | } |
|
311 | } | |
312 | } |
|
312 | } | |
313 | else if ( incomingData[0] == CCSDS_DESTINATION_ID ) // the incoming message is a ccsds packet |
|
313 | else if ( incomingData[0] == CCSDS_DESTINATION_ID ) // the incoming message is a ccsds packet | |
314 | { |
|
314 | { | |
315 | sidAsUnsignedChar = (unsigned char) incomingData[ PACKET_POS_PA_LFR_SID_PKT ]; |
|
315 | sidAsUnsignedChar = (unsigned char) incomingData[ PACKET_POS_PA_LFR_SID_PKT ]; | |
316 | sid = sidAsUnsignedChar; |
|
316 | sid = sidAsUnsignedChar; | |
317 | type = (unsigned char) incomingData[ PACKET_POS_SERVICE_TYPE ]; |
|
317 | type = (unsigned char) incomingData[ PACKET_POS_SERVICE_TYPE ]; | |
318 | if (type == TM_TYPE_LFR_SCIENCE) // this is a BP packet, all other types are handled differently |
|
318 | if (type == TM_TYPE_LFR_SCIENCE) // this is a BP packet, all other types are handled differently | |
319 | // SET THE SEQUENCE_CNT PARAMETER IN CASE OF BP0 OR BP1 PACKETS |
|
319 | // SET THE SEQUENCE_CNT PARAMETER IN CASE OF BP0 OR BP1 PACKETS | |
320 | { |
|
320 | { | |
321 | increment_seq_counter_source_id( (unsigned char*) &incomingData[ PACKET_POS_SEQUENCE_CNT ], sid ); |
|
321 | increment_seq_counter_source_id( (unsigned char*) &incomingData[ PACKET_POS_SEQUENCE_CNT ], sid ); | |
322 | } |
|
322 | } | |
323 |
|
323 | |||
324 | status = write( fdSPW, incomingData, size ); |
|
324 | status = write( fdSPW, incomingData, size ); | |
325 | if (status == -1){ |
|
325 | if (status == -1){ | |
326 | PRINTF2("in SEND *** (2.a) ERRNO = %d, size = %d\n", errno, size) |
|
326 | PRINTF2("in SEND *** (2.a) ERRNO = %d, size = %d\n", errno, size) | |
327 | } |
|
327 | } | |
328 | } |
|
328 | } | |
329 | else // the incoming message is a spw_ioctl_pkt_send structure |
|
329 | else // the incoming message is a spw_ioctl_pkt_send structure | |
330 | { |
|
330 | { | |
331 | spw_ioctl_send = (spw_ioctl_pkt_send*) incomingData; |
|
331 | spw_ioctl_send = (spw_ioctl_pkt_send*) incomingData; | |
332 | status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, spw_ioctl_send ); |
|
332 | status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, spw_ioctl_send ); | |
333 | if (status == -1){ |
|
333 | if (status == -1){ | |
334 | PRINTF2("in SEND *** (2.b) ERRNO = %d, RTEMS = %d\n", errno, status) |
|
334 | PRINTF2("in SEND *** (2.b) ERRNO = %d, RTEMS = %d\n", errno, status) | |
335 | } |
|
335 | } | |
336 | } |
|
336 | } | |
337 | } |
|
337 | } | |
338 |
|
338 | |||
339 | update_queue_max_count( queue_send_id, &hk_lfr_q_sd_fifo_size_max ); |
|
339 | update_queue_max_count( queue_send_id, &hk_lfr_q_sd_fifo_size_max ); | |
340 |
|
340 | |||
341 | } |
|
341 | } | |
342 | } |
|
342 | } | |
343 |
|
343 | |||
344 | rtems_task link_task( rtems_task_argument argument ) |
|
344 | rtems_task link_task( rtems_task_argument argument ) | |
345 | { |
|
345 | { | |
346 | rtems_event_set event_out; |
|
346 | rtems_event_set event_out; | |
347 | rtems_status_code status; |
|
347 | rtems_status_code status; | |
348 | int linkStatus; |
|
348 | int linkStatus; | |
349 |
|
349 | |||
350 | event_out = EVENT_SETS_NONE_PENDING; |
|
350 | event_out = EVENT_SETS_NONE_PENDING; | |
351 | linkStatus = 0; |
|
351 | linkStatus = 0; | |
352 |
|
352 | |||
353 | BOOT_PRINTF("in LINK ***\n") |
|
353 | BOOT_PRINTF("in LINK ***\n") | |
354 |
|
354 | |||
355 | while(1) |
|
355 | while(1) | |
356 | { |
|
356 | { | |
357 | // wait for an RTEMS_EVENT |