##// END OF EJS Templates
Snapshot resynchro rewritten, drift is measured one snapshot in two...
paul -
r253:cc5f75e74b54 R3a
parent child
Show More
@@ -1,192 +1,192
1 #ifndef GSCMEMORY_HPP_
1 #ifndef GSCMEMORY_HPP_
2 #define GSCMEMORY_HPP_
2 #define GSCMEMORY_HPP_
3
3
4 #ifndef LEON3
4 #ifndef LEON3
5 #define LEON3
5 #define LEON3
6 #endif
6 #endif
7
7
8 #define REGS_ADDR_PLUGANDPLAY 0xFFFFF000
8 #define REGS_ADDR_PLUGANDPLAY 0xFFFFF000
9 #define ASR16_REG_ADDRESS 0x90400040 // Ancillary State Register 16 = Register protection control register (FT only)
9 #define ASR16_REG_ADDRESS 0x90400040 // Ancillary State Register 16 = Register protection control register (FT only)
10
10
11 #define DEVICEID_LEON3 0x003
11 #define DEVICEID_LEON3 0x003
12 #define DEVICEID_LEON3FT 0x053
12 #define DEVICEID_LEON3FT 0x053
13 #define VENDORID_GAISLER 0x01
13 #define VENDORID_GAISLER 0x01
14
14
15 // CCR
15 // CCR
16 #define POS_ITE 12
16 #define POS_ITE 12
17 #define COUNTER_FIELD_ITE 0x00003000 // 0000 0000 0000 0000 0011 0000 0000 0000
17 #define COUNTER_FIELD_ITE 0x00003000 // 0000 0000 0000 0000 0011 0000 0000 0000
18 #define COUNTER_MASK_ITE 0xffffcfff // 1111 1111 1111 1111 1100 1111 1111 1111
18 #define COUNTER_MASK_ITE 0xffffcfff // 1111 1111 1111 1111 1100 1111 1111 1111
19 #define POS_IDE 10
19 #define POS_IDE 10
20 #define COUNTER_FIELD_IDE 0x00000c00 // 0000 0000 0000 0000 0000 1100 0000 0000
20 #define COUNTER_FIELD_IDE 0x00000c00 // 0000 0000 0000 0000 0000 1100 0000 0000
21 #define COUNTER_MASK_IDE 0xfffff3ff // 1111 1111 1111 1111 1111 0011 1111 1111
21 #define COUNTER_MASK_IDE 0xfffff3ff // 1111 1111 1111 1111 1111 0011 1111 1111
22 //
22 //
23 #define POS_DTE 8
23 #define POS_DTE 8
24 #define COUNTER_FIELD_DTE 0x00000300 // 0000 0000 0000 0000 0000 0011 0000 0000
24 #define COUNTER_FIELD_DTE 0x00000300 // 0000 0000 0000 0000 0000 0011 0000 0000
25 #define COUNTER_MASK_DTE 0xfffffcff // 1111 1111 1111 1111 1111 1100 1111 1111
25 #define COUNTER_MASK_DTE 0xfffffcff // 1111 1111 1111 1111 1111 1100 1111 1111
26 #define POS_DDE 6
26 #define POS_DDE 6
27 #define COUNTER_FIELD_DDE 0x000000c0 // 0000 0000 0000 0000 0000 0000 1100 0000
27 #define COUNTER_FIELD_DDE 0x000000c0 // 0000 0000 0000 0000 0000 0000 1100 0000
28 #define COUNTER_MASK_DDE 0xffffff3f // 1111 1111 1111 1111 1111 1111 0011 1111
28 #define COUNTER_MASK_DDE 0xffffff3f // 1111 1111 1111 1111 1111 1111 0011 1111
29
29
30 // ASR16
30 // ASR16
31 #define POS_FPRF 27
31 #define POS_FPRF 27
32 #define COUNTER_FIELD_FPRF 0x38000000 // 0011 1000 0000 0000 0000 0000 0000 0000
32 #define COUNTER_FIELD_FPRF 0x38000000 // 0011 1000 0000 0000 0000 0000 0000 0000
33 #define COUNTER_MASK_FPRF 0xc7ffffff // 1100 0111 1111 1111 1111 1111 1111 1111
33 #define COUNTER_MASK_FPRF 0xc7ffffff // 1100 0111 1111 1111 1111 1111 1111 1111
34 #define POS_IURF 11
34 #define POS_IURF 11
35 #define COUNTER_FIELD_IURF 0x00003800 // 0000 0000 0000 0000 0011 1000 0000 0000
35 #define COUNTER_FIELD_IURF 0x00003800 // 0000 0000 0000 0000 0011 1000 0000 0000
36 #define COUNTER_MASK_IURF 0xffffc7ff // 1111 1111 1111 1111 1100 0111 1111 1111
36 #define COUNTER_MASK_IURF 0xffffc7ff // 1111 1111 1111 1111 1100 0111 1111 1111
37
37
38 volatile unsigned int *asr16Ptr = (volatile unsigned int *) ASR16_REG_ADDRESS;
38 volatile unsigned int *asr16Ptr = (volatile unsigned int *) ASR16_REG_ADDRESS;
39
39
40 static inline void flushCache()
40 static inline void flushCache()
41 {
41 {
42 /**
42 /**
43 * Flush the data cache and the instruction cache.
43 * Flush the data cache and the instruction cache.
44 *
44 *
45 * @param void
45 * @param void
46 *
46 *
47 * @return void
47 * @return void
48 */
48 */
49
49
50 asm("flush");
50 asm("flush");
51 }
51 }
52
52
53 //***************************
53 //***************************
54 // CCR Cache control register
54 // CCR Cache control register
55
55
56 static unsigned int CCR_getValue()
56 static unsigned int CCR_getValue()
57 {
57 {
58 unsigned int cacheControlRegister = 0;
58 unsigned int cacheControlRegister = 0;
59 __asm__ __volatile__("lda [%%g0] 2, %0" : "=r"(cacheControlRegister) : );
59 __asm__ __volatile__("lda [%%g0] 2, %0" : "=r"(cacheControlRegister) : );
60 return cacheControlRegister;
60 return cacheControlRegister;
61 }
61 }
62
62
63 static void CCR_setValue(unsigned int cacheControlRegister)
63 static void CCR_setValue(unsigned int cacheControlRegister)
64 {
64 {
65 __asm__ __volatile__("sta %0, [%%g0] 2" : : "r"(cacheControlRegister));
65 __asm__ __volatile__("sta %0, [%%g0] 2" : : "r"(cacheControlRegister));
66 }
66 }
67
67
68 static void CCR_resetCacheControlRegister()
68 static void CCR_resetCacheControlRegister()
69 {
69 {
70 unsigned int cacheControlRegister;
70 unsigned int cacheControlRegister;
71 cacheControlRegister = 0x00;
71 cacheControlRegister = 0x00;
72 CCR_setValue(cacheControlRegister);
72 CCR_setValue(cacheControlRegister);
73 }
73 }
74
74
75 static void CCR_enableInstructionCache()
75 static void CCR_enableInstructionCache()
76 {
76 {
77 // [1:0] Instruction Cache state (ICS)
77 // [1:0] Instruction Cache state (ICS)
78 // Indicates the current data cache state according to the following: X0 = disabled, 01 = frozen, 11 = enabled.
78 // Indicates the current data cache state according to the following: X0 = disabled, 01 = frozen, 11 = enabled.
79 unsigned int cacheControlRegister;
79 unsigned int cacheControlRegister;
80 cacheControlRegister = CCR_getValue();
80 cacheControlRegister = CCR_getValue();
81 cacheControlRegister = (cacheControlRegister | 0x3);
81 cacheControlRegister = (cacheControlRegister | 0x3);
82 CCR_setValue(cacheControlRegister);
82 CCR_setValue(cacheControlRegister);
83 }
83 }
84
84
85 static void CCR_enableDataCache()
85 static void CCR_enableDataCache()
86 {
86 {
87 // [3:2] Data Cache state (DCS)
87 // [3:2] Data Cache state (DCS)
88 // Indicates the current data cache state according to the following: X0 = disabled, 01 = frozen, 11 = enabled.
88 // Indicates the current data cache state according to the following: X0 = disabled, 01 = frozen, 11 = enabled.
89 unsigned int cacheControlRegister;
89 unsigned int cacheControlRegister;
90 cacheControlRegister = CCR_getValue();
90 cacheControlRegister = CCR_getValue();
91 cacheControlRegister = (cacheControlRegister | 0xc);
91 cacheControlRegister = (cacheControlRegister | 0xc);
92 CCR_setValue(cacheControlRegister);
92 CCR_setValue(cacheControlRegister);
93 }
93 }
94
94
95 static void CCR_faultTolerantScheme()
95 static void CCR_faultTolerantScheme()
96 {
96 {
97 // [20:19] FT scheme (FT) - β€œ00” = no FT, β€œ01” = 4-bit checking implemented
97 // [20:19] FT scheme (FT) - β€œ00” = no FT, β€œ01” = 4-bit checking implemented
98 unsigned int cacheControlRegister;
98 unsigned int cacheControlRegister;
99 unsigned int *plugAndPlayRegister;
99 unsigned int *plugAndPlayRegister;
100 unsigned int vendorId;
100 unsigned int vendorId;
101 unsigned int deviceId;
101 unsigned int deviceId;
102
102
103 plugAndPlayRegister = (unsigned int*) REGS_ADDR_PLUGANDPLAY;
103 plugAndPlayRegister = (unsigned int*) REGS_ADDR_PLUGANDPLAY;
104 vendorId = ( (*plugAndPlayRegister) & 0xff000000 ) >> 24;
104 vendorId = ( (*plugAndPlayRegister) & 0xff000000 ) >> 24;
105 deviceId = ( (*plugAndPlayRegister) & 0x00fff000 ) >> 12;
105 deviceId = ( (*plugAndPlayRegister) & 0x00fff000 ) >> 12;
106
106
107 if( (vendorId == VENDORID_GAISLER) & (deviceId ==DEVICEID_LEON3FT) )
107 if( (vendorId == VENDORID_GAISLER) & (deviceId ==DEVICEID_LEON3FT) )
108 {
108 {
109 PRINTF("in faultTolerantScheme *** Leon3FT detected, configure the CCR FT bits");
109 PRINTF("in faultTolerantScheme *** Leon3FT detected, configure the CCR FT bits\n");
110 cacheControlRegister = CCR_getValue();
110 cacheControlRegister = CCR_getValue();
111 cacheControlRegister = (cacheControlRegister | 0xc);
111 cacheControlRegister = (cacheControlRegister | 0xc);
112 CCR_setValue(cacheControlRegister);
112 CCR_setValue(cacheControlRegister);
113 }
113 }
114 else
114 else
115 {
115 {
116 PRINTF("in faultTolerantScheme *** not a Leon3FT, no need to configure the CCR FT bits\n");
116 PRINTF("in faultTolerantScheme *** not a Leon3FT, no need to configure the CCR FT bits\n");
117 PRINTF2(" *** vendorID = 0x%x, deviceId = 0x%x\n", vendorId, deviceId);
117 PRINTF2(" *** vendorID = 0x%x, deviceId = 0x%x\n", vendorId, deviceId);
118 }
118 }
119 }
119 }
120
120
121 static void CCR_enableInstructionBurstFetch()
121 static void CCR_enableInstructionBurstFetch()
122 {
122 {
123 // [16] Instruction burst fetch (IB). This bit enables burst fill during instruction fetch.
123 // [16] Instruction burst fetch (IB). This bit enables burst fill during instruction fetch.
124 unsigned int cacheControlRegister;
124 unsigned int cacheControlRegister;
125 cacheControlRegister = CCR_getValue();
125 cacheControlRegister = CCR_getValue();
126 // set the bit IB to 1
126 // set the bit IB to 1
127 cacheControlRegister = (cacheControlRegister | 0x10000);
127 cacheControlRegister = (cacheControlRegister | 0x10000);
128 CCR_setValue(cacheControlRegister);
128 CCR_setValue(cacheControlRegister);
129 }
129 }
130
130
131 static void CCR_getInstructionAndDataErrorCounters( unsigned int* instructionErrorCounter, unsigned int* dataErrorCounter )
131 static void CCR_getInstructionAndDataErrorCounters( unsigned int* instructionErrorCounter, unsigned int* dataErrorCounter )
132 {
132 {
133 // [13:12] Instruction Tag Errors (ITE) - Number of detected parity errors in the instruction tag cache.
133 // [13:12] Instruction Tag Errors (ITE) - Number of detected parity errors in the instruction tag cache.
134 // Only available if fault-tolerance is enabled (FT field in this register is non-zero).
134 // Only available if fault-tolerance is enabled (FT field in this register is non-zero).
135 // [11:10] Instruction Data Errors (IDE) - Number of detected parity errors in the instruction data cache.
135 // [11:10] Instruction Data Errors (IDE) - Number of detected parity errors in the instruction data cache.
136 // Only available if fault-tolerance is enabled (FT field in this register is non-zero).
136 // Only available if fault-tolerance is enabled (FT field in this register is non-zero).
137
137
138 unsigned int cacheControlRegister;
138 unsigned int cacheControlRegister;
139 unsigned int iTE;
139 unsigned int iTE;
140 unsigned int iDE;
140 unsigned int iDE;
141 unsigned int dTE;
141 unsigned int dTE;
142 unsigned int dDE;
142 unsigned int dDE;
143
143
144 cacheControlRegister = CCR_getValue();
144 cacheControlRegister = CCR_getValue();
145 iTE = (cacheControlRegister & COUNTER_FIELD_ITE) >> POS_ITE;
145 iTE = (cacheControlRegister & COUNTER_FIELD_ITE) >> POS_ITE;
146 iDE = (cacheControlRegister & COUNTER_FIELD_IDE) >> POS_IDE;
146 iDE = (cacheControlRegister & COUNTER_FIELD_IDE) >> POS_IDE;
147 dTE = (cacheControlRegister & COUNTER_FIELD_DTE) >> POS_DTE;
147 dTE = (cacheControlRegister & COUNTER_FIELD_DTE) >> POS_DTE;
148 dDE = (cacheControlRegister & COUNTER_FIELD_DDE) >> POS_DDE;
148 dDE = (cacheControlRegister & COUNTER_FIELD_DDE) >> POS_DDE;
149
149
150 *instructionErrorCounter = iTE + iDE;
150 *instructionErrorCounter = iTE + iDE;
151 *dataErrorCounter = dTE + dDE;
151 *dataErrorCounter = dTE + dDE;
152
152
153 // reset counters
153 // reset counters
154 cacheControlRegister = cacheControlRegister
154 cacheControlRegister = cacheControlRegister
155 & COUNTER_FIELD_ITE
155 & COUNTER_FIELD_ITE
156 & COUNTER_FIELD_IDE
156 & COUNTER_FIELD_IDE
157 & COUNTER_FIELD_DTE
157 & COUNTER_FIELD_DTE
158 & COUNTER_FIELD_DDE;
158 & COUNTER_FIELD_DDE;
159
159
160 CCR_setValue(cacheControlRegister);
160 CCR_setValue(cacheControlRegister);
161 }
161 }
162
162
163 //*******************************************
163 //*******************************************
164 // ASR16 Register protection control register
164 // ASR16 Register protection control register
165
165
166 static unsigned int ASR16_get_FPRF_IURF_ErrorCounters( unsigned int* fprfErrorCounter, unsigned int* iurfErrorCounter)
166 static void ASR16_get_FPRF_IURF_ErrorCounters( unsigned int* fprfErrorCounter, unsigned int* iurfErrorCounter)
167 {
167 {
168 /** This function is used to retrieve the integer unit register file error counter and the floating point unit
168 /** This function is used to retrieve the integer unit register file error counter and the floating point unit
169 * register file error counter
169 * register file error counter
170 *
170 *
171 * @return void
171 * @return void
172 *
172 *
173 * [29:27] FP RF error counter - Number of detected parity errors in the FP register file.
173 * [29:27] FP RF error counter - Number of detected parity errors in the FP register file.
174 * [13:11] IU RF error counter - Number of detected parity errors in the IU register file.
174 * [13:11] IU RF error counter - Number of detected parity errors in the IU register file.
175 *
175 *
176 */
176 */
177
177
178 unsigned int asr16;
178 unsigned int asr16;
179
179
180 asr16 = *asr16Ptr;
180 asr16 = *asr16Ptr;
181 *fprfErrorCounter = ( asr16 & COUNTER_FIELD_FPRF ) >> POS_FPRF;
181 *fprfErrorCounter = ( asr16 & COUNTER_FIELD_FPRF ) >> POS_FPRF;
182 *iurfErrorCounter = ( asr16 & COUNTER_FIELD_IURF ) >> POS_IURF;
182 *iurfErrorCounter = ( asr16 & COUNTER_FIELD_IURF ) >> POS_IURF;
183
183
184 // reset the counter to 0
184 // reset the counter to 0
185 asr16 = asr16Ptr
185 asr16 = asr16
186 & COUNTER_MASK_FPRF
186 & COUNTER_MASK_FPRF
187 & COUNTER_FIELD_IURF;
187 & COUNTER_FIELD_IURF;
188
188
189 *asr16Ptr = asr16;
189 *asr16Ptr = asr16;
190 }
190 }
191
191
192 #endif /* GSCMEMORY_HPP_ */
192 #endif /* GSCMEMORY_HPP_ */
@@ -1,56 +1,56
1 #ifndef FSW_SPACEWIRE_H_INCLUDED
1 #ifndef FSW_SPACEWIRE_H_INCLUDED
2 #define FSW_SPACEWIRE_H_INCLUDED
2 #define FSW_SPACEWIRE_H_INCLUDED
3
3
4 #include <rtems.h>
4 #include <rtems.h>
5 #include <grspw.h>
5 #include <grspw.h>
6
6
7 #include <fcntl.h> // for O_RDWR
7 #include <fcntl.h> // for O_RDWR
8 #include <unistd.h> // for the read call
8 #include <unistd.h> // for the read call
9 #include <sys/ioctl.h> // for the ioctl call
9 #include <sys/ioctl.h> // for the ioctl call
10 #include <errno.h>
10 #include <errno.h>
11
11
12 #include "fsw_params.h"
12 #include "fsw_params.h"
13 #include "tc_handler.h"
13 #include "tc_handler.h"
14 #include "fsw_init.h"
14 #include "fsw_init.h"
15
15
16 extern spw_stats spacewire_stats;
16 extern spw_stats spacewire_stats;
17 extern spw_stats spacewire_stats_backup;
17 extern spw_stats spacewire_stats_backup;
18 extern rtems_name timecode_timer_name;
18 extern rtems_name timecode_timer_name;
19 extern rtems_id timecode_timer_id;
19 extern rtems_id timecode_timer_id;
20
20
21 // RTEMS TASK
21 // RTEMS TASK
22 rtems_task spiq_task( rtems_task_argument argument );
22 rtems_task spiq_task( rtems_task_argument argument );
23 rtems_task recv_task( rtems_task_argument unused );
23 rtems_task recv_task( rtems_task_argument unused );
24 rtems_task send_task( rtems_task_argument argument );
24 rtems_task send_task( rtems_task_argument argument );
25 rtems_task wtdg_task( rtems_task_argument argument );
25 rtems_task wtdg_task( rtems_task_argument argument );
26
26
27 int spacewire_open_link( void );
27 int spacewire_open_link( void );
28 int spacewire_start_link( int fd );
28 int spacewire_start_link( int fd );
29 int spacewire_stop_and_start_link( int fd );
29 int spacewire_stop_and_start_link( int fd );
30 int spacewire_configure_link(int fd );
30 int spacewire_configure_link(int fd );
31 int spacewire_reset_link( void );
31 int spacewire_several_connect_attemps( void );
32 void spacewire_set_NP( unsigned char val, unsigned int regAddr ); // No Port force
32 void spacewire_set_NP( unsigned char val, unsigned int regAddr ); // No Port force
33 void spacewire_set_RE( unsigned char val, unsigned int regAddr ); // RMAP Enable
33 void spacewire_set_RE( unsigned char val, unsigned int regAddr ); // RMAP Enable
34 void spacewire_compute_stats_offsets( void );
34 void spacewire_compute_stats_offsets( void );
35 void spacewire_update_statistics( void );
35 void spacewire_update_statistics( void );
36 void increase_unsigned_char_counter( unsigned char *counter );
36 void increase_unsigned_char_counter( unsigned char *counter );
37
37
38 void init_header_cwf( Header_TM_LFR_SCIENCE_CWF_t *header );
38 void init_header_cwf( Header_TM_LFR_SCIENCE_CWF_t *header );
39 void init_header_swf( Header_TM_LFR_SCIENCE_SWF_t *header );
39 void init_header_swf( Header_TM_LFR_SCIENCE_SWF_t *header );
40 void init_header_asm( Header_TM_LFR_SCIENCE_ASM_t *header );
40 void init_header_asm( Header_TM_LFR_SCIENCE_ASM_t *header );
41 int spw_send_waveform_CWF( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_CWF_t *header );
41 int spw_send_waveform_CWF( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_CWF_t *header );
42 int spw_send_waveform_SWF( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_SWF_t *header );
42 int spw_send_waveform_SWF( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_SWF_t *header );
43 int spw_send_waveform_CWF3_light( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_CWF_t *header );
43 int spw_send_waveform_CWF3_light( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_CWF_t *header );
44 void spw_send_asm_f0( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_ASM_t *header );
44 void spw_send_asm_f0( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_ASM_t *header );
45 void spw_send_asm_f1( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_ASM_t *header );
45 void spw_send_asm_f1( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_ASM_t *header );
46 void spw_send_asm_f2( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_ASM_t *header );
46 void spw_send_asm_f2( ring_node *ring_node_to_send, Header_TM_LFR_SCIENCE_ASM_t *header );
47 void spw_send_k_dump( ring_node *ring_node_to_send );
47 void spw_send_k_dump( ring_node *ring_node_to_send );
48
48
49 rtems_timer_service_routine timecode_timer_routine( rtems_id timer_id, void *user_data );
49 rtems_timer_service_routine timecode_timer_routine( rtems_id timer_id, void *user_data );
50 unsigned int check_timecode_and_previous_timecode_coherency(unsigned char currentTimecodeCtr);
50 unsigned int check_timecode_and_previous_timecode_coherency(unsigned char currentTimecodeCtr);
51 unsigned int check_timecode_and_internal_time_coherency(unsigned char timecode, unsigned char internalTime);
51 unsigned int check_timecode_and_internal_time_coherency(unsigned char timecode, unsigned char internalTime);
52 void timecode_irq_handler( void *pDev, void *regs, int minor, unsigned int tc );
52 void timecode_irq_handler( void *pDev, void *regs, int minor, unsigned int tc );
53
53
54 void (*grspw_timecode_callback) ( void *pDev, void *regs, int minor, unsigned int tc );
54 void (*grspw_timecode_callback) ( void *pDev, void *regs, int minor, unsigned int tc );
55
55
56 #endif // FSW_SPACEWIRE_H_INCLUDED
56 #endif // FSW_SPACEWIRE_H_INCLUDED
@@ -1,14 +1,14
1 # LOAD FSW USING LINK 1
1 # LOAD FSW USING LINK 1
2 SpwPlugin0.StarDundeeSelectLinkNumber( 1 )
2 SpwPlugin0.StarDundeeSelectLinkNumber( 1 )
3
3
4 dsu3plugin0.openFile("/opt/DEV_PLE/FSW-qt/bin/fsw")
4 dsu3plugin0.openFile("/opt/DEV_PLE/FSW-qt/bin/fsw")
5 #dsu3plugin0.openFile("/opt/LFR/LFR-FSW/2.0.2.3/fsw")
5 #dsu3plugin0.openFile("/opt/LFR/LFR-FSW/2.0.2.3/fsw")
6 dsu3plugin0.loadFile()
6 dsu3plugin0.loadFile()
7
7
8 dsu3plugin0.run()
8 dsu3plugin0.run()
9
9
10 # START SENDING TIMECODES AT 1 Hz
10 # START SENDING TIMECODES AT 1 Hz
11 SpwPlugin0.StarDundeeStartTimecodes( 1 )
11 #SpwPlugin0.StarDundeeStartTimecodes( 1 )
12
12
13 # it is possible to change the time code frequency
13 # it is possible to change the time code frequency
14 #RMAPPlugin0.changeTimecodeFrequency(2)
14 #RMAPPlugin0.changeTimecodeFrequency(2)
@@ -1,910 +1,909
1 /** This is the RTEMS initialization module.
1 /** This is the RTEMS initialization module.
2 *
2 *
3 * @file
3 * @file
4 * @author P. LEROY
4 * @author P. LEROY
5 *
5 *
6 * This module contains two very different information:
6 * This module contains two very different information:
7 * - specific instructions to configure the compilation of the RTEMS executive
7 * - specific instructions to configure the compilation of the RTEMS executive
8 * - functions related to the fligth softwre initialization, especially the INIT RTEMS task
8 * - functions related to the fligth softwre initialization, especially the INIT RTEMS task
9 *
9 *
10 */
10 */
11
11
12 //*************************
12 //*************************
13 // GPL reminder to be added
13 // GPL reminder to be added
14 //*************************
14 //*************************
15
15
16 #include <rtems.h>
16 #include <rtems.h>
17
17
18 /* configuration information */
18 /* configuration information */
19
19
20 #define CONFIGURE_INIT
20 #define CONFIGURE_INIT
21
21
22 #include <bsp.h> /* for device driver prototypes */
22 #include <bsp.h> /* for device driver prototypes */
23
23
24 /* configuration information */
24 /* configuration information */
25
25
26 #define CONFIGURE_APPLICATION_NEEDS_CONSOLE_DRIVER
26 #define CONFIGURE_APPLICATION_NEEDS_CONSOLE_DRIVER
27 #define CONFIGURE_APPLICATION_NEEDS_CLOCK_DRIVER
27 #define CONFIGURE_APPLICATION_NEEDS_CLOCK_DRIVER
28
28
29 #define CONFIGURE_MAXIMUM_TASKS 20
29 #define CONFIGURE_MAXIMUM_TASKS 20
30 #define CONFIGURE_RTEMS_INIT_TASKS_TABLE
30 #define CONFIGURE_RTEMS_INIT_TASKS_TABLE
31 #define CONFIGURE_EXTRA_TASK_STACKS (3 * RTEMS_MINIMUM_STACK_SIZE)
31 #define CONFIGURE_EXTRA_TASK_STACKS (3 * RTEMS_MINIMUM_STACK_SIZE)
32 #define CONFIGURE_LIBIO_MAXIMUM_FILE_DESCRIPTORS 32
32 #define CONFIGURE_LIBIO_MAXIMUM_FILE_DESCRIPTORS 32
33 #define CONFIGURE_INIT_TASK_PRIORITY 1 // instead of 100
33 #define CONFIGURE_INIT_TASK_PRIORITY 1 // instead of 100
34 #define CONFIGURE_INIT_TASK_MODE (RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT)
34 #define CONFIGURE_INIT_TASK_MODE (RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT)
35 #define CONFIGURE_INIT_TASK_ATTRIBUTES (RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT)
35 #define CONFIGURE_INIT_TASK_ATTRIBUTES (RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT)
36 #define CONFIGURE_MAXIMUM_DRIVERS 16
36 #define CONFIGURE_MAXIMUM_DRIVERS 16
37 #define CONFIGURE_MAXIMUM_PERIODS 5
37 #define CONFIGURE_MAXIMUM_PERIODS 5
38 #define CONFIGURE_MAXIMUM_TIMERS 5 // [spiq] [wtdg] [spacewire_reset_link]
38 #define CONFIGURE_MAXIMUM_TIMERS 5 // [spiq] [wtdg] [spacewire_reset_link]
39 #define CONFIGURE_MAXIMUM_MESSAGE_QUEUES 5
39 #define CONFIGURE_MAXIMUM_MESSAGE_QUEUES 5
40 #ifdef PRINT_STACK_REPORT
40 #ifdef PRINT_STACK_REPORT
41 #define CONFIGURE_STACK_CHECKER_ENABLED
41 #define CONFIGURE_STACK_CHECKER_ENABLED
42 #endif
42 #endif
43
43
44 #include <rtems/confdefs.h>
44 #include <rtems/confdefs.h>
45
45
46 /* If --drvmgr was enabled during the configuration of the RTEMS kernel */
46 /* If --drvmgr was enabled during the configuration of the RTEMS kernel */
47 #ifdef RTEMS_DRVMGR_STARTUP
47 #ifdef RTEMS_DRVMGR_STARTUP
48 #ifdef LEON3
48 #ifdef LEON3
49 /* Add Timer and UART Driver */
49 /* Add Timer and UART Driver */
50 #ifdef CONFIGURE_APPLICATION_NEEDS_CLOCK_DRIVER
50 #ifdef CONFIGURE_APPLICATION_NEEDS_CLOCK_DRIVER
51 #define CONFIGURE_DRIVER_AMBAPP_GAISLER_GPTIMER
51 #define CONFIGURE_DRIVER_AMBAPP_GAISLER_GPTIMER
52 #endif
52 #endif
53 #ifdef CONFIGURE_APPLICATION_NEEDS_CONSOLE_DRIVER
53 #ifdef CONFIGURE_APPLICATION_NEEDS_CONSOLE_DRIVER
54 #define CONFIGURE_DRIVER_AMBAPP_GAISLER_APBUART
54 #define CONFIGURE_DRIVER_AMBAPP_GAISLER_APBUART
55 #endif
55 #endif
56 #endif
56 #endif
57 #define CONFIGURE_DRIVER_AMBAPP_GAISLER_GRSPW /* GRSPW Driver */
57 #define CONFIGURE_DRIVER_AMBAPP_GAISLER_GRSPW /* GRSPW Driver */
58 #include <drvmgr/drvmgr_confdefs.h>
58 #include <drvmgr/drvmgr_confdefs.h>
59 #endif
59 #endif
60
60
61 #include "fsw_init.h"
61 #include "fsw_init.h"
62 #include "fsw_config.c"
62 #include "fsw_config.c"
63 #include "GscMemoryLPP.hpp"
63 #include "GscMemoryLPP.hpp"
64
64
65 void initCache()
65 void initCache()
66 {
66 {
67 // ASI 2 contains a few control registers that have not been assigned as ancillary state registers.
67 // ASI 2 contains a few control registers that have not been assigned as ancillary state registers.
68 // These should only be read and written using 32-bit LDA/STA instructions.
68 // These should only be read and written using 32-bit LDA/STA instructions.
69 // All cache registers are accessed through load/store operations to the alternate address space (LDA/STA), using ASI = 2.
69 // All cache registers are accessed through load/store operations to the alternate address space (LDA/STA), using ASI = 2.
70 // The table below shows the register addresses:
70 // The table below shows the register addresses:
71 // 0x00 Cache control register
71 // 0x00 Cache control register
72 // 0x04 Reserved
72 // 0x04 Reserved
73 // 0x08 Instruction cache configuration register
73 // 0x08 Instruction cache configuration register
74 // 0x0C Data cache configuration register
74 // 0x0C Data cache configuration register
75
75
76 // Cache Control Register Leon3 / Leon3FT
76 // Cache Control Register Leon3 / Leon3FT
77 // 31..30 29 28 27..24 23 22 21 20..19 18 17 16
77 // 31..30 29 28 27..24 23 22 21 20..19 18 17 16
78 // RFT PS TB DS FD FI FT ST IB
78 // RFT PS TB DS FD FI FT ST IB
79 // 15 14 13..12 11..10 9..8 7..6 5 4 3..2 1..0
79 // 15 14 13..12 11..10 9..8 7..6 5 4 3..2 1..0
80 // IP DP ITE IDE DTE DDE DF IF DCS ICS
80 // IP DP ITE IDE DTE DDE DF IF DCS ICS
81
81
82 unsigned int cacheControlRegister;
82 unsigned int cacheControlRegister;
83
83
84 cacheControlRegister = CCR_getValue();
84 cacheControlRegister = CCR_getValue();
85 PRINTF1("(0) cacheControlRegister = %x\n", cacheControlRegister);
85 PRINTF1("(0) cacheControlRegister = %x\n", cacheControlRegister);
86
86
87 CCR_resetCacheControlRegister();
87 CCR_resetCacheControlRegister();
88
88
89 CCR_enableInstructionCache(); // ICS bits
89 CCR_enableInstructionCache(); // ICS bits
90 CCR_enableDataCache(); // DCS bits
90 CCR_enableDataCache(); // DCS bits
91 CCR_enableInstructionBurstFetch(); // IB bit
91 CCR_enableInstructionBurstFetch(); // IB bit
92
92
93 cacheControlRegister = CCR_getValue();
93 cacheControlRegister = CCR_getValue();
94 PRINTF1("(1) cacheControlRegister = %x\n", cacheControlRegister);
94 PRINTF1("(1) cacheControlRegister = %x\n", cacheControlRegister);
95
95
96 CCR_faultTolerantScheme();
96 CCR_faultTolerantScheme();
97
97
98 // FT activation
98 PRINTF("\n");
99 }
99 }
100
100
101 rtems_task Init( rtems_task_argument ignored )
101 rtems_task Init( rtems_task_argument ignored )
102 {
102 {
103 /** This is the RTEMS INIT taks, it is the first task launched by the system.
103 /** This is the RTEMS INIT taks, it is the first task launched by the system.
104 *
104 *
105 * @param unused is the starting argument of the RTEMS task
105 * @param unused is the starting argument of the RTEMS task
106 *
106 *
107 * The INIT task create and run all other RTEMS tasks.
107 * The INIT task create and run all other RTEMS tasks.
108 *
108 *
109 */
109 */
110
110
111 //***********
111 //***********
112 // INIT CACHE
112 // INIT CACHE
113
113
114 unsigned char *vhdlVersion;
114 unsigned char *vhdlVersion;
115
115
116 reset_lfr();
116 reset_lfr();
117
117
118 reset_local_time();
118 reset_local_time();
119
119
120 rtems_cpu_usage_reset();
120 rtems_cpu_usage_reset();
121
121
122 rtems_status_code status;
122 rtems_status_code status;
123 rtems_status_code status_spw;
123 rtems_status_code status_spw;
124 rtems_isr_entry old_isr_handler;
124 rtems_isr_entry old_isr_handler;
125
125
126 // UART settings
126 // UART settings
127 send_console_outputs_on_apbuart_port();
127 enable_apbuart_transmitter();
128 set_apbuart_scaler_reload_register(REGS_ADDR_APBUART, APBUART_SCALER_RELOAD_VALUE);
128 set_apbuart_scaler_reload_register(REGS_ADDR_APBUART, APBUART_SCALER_RELOAD_VALUE);
129 enable_apbuart_transmitter();
130
129
131 DEBUG_PRINTF("\n\n\n\n\nIn INIT *** Now the console is on port COM1\n")
130 DEBUG_PRINTF("\n\n\n\n\nIn INIT *** Now the console is on port COM1\n")
132
131
133
132
134 PRINTF("\n\n\n\n\n")
133 PRINTF("\n\n\n\n\n")
135
134
136 initCache();
135 initCache();
137
136
138 PRINTF("*************************\n")
137 PRINTF("*************************\n")
139 PRINTF("** LFR Flight Software **\n")
138 PRINTF("** LFR Flight Software **\n")
140 PRINTF1("** %d.", SW_VERSION_N1)
139 PRINTF1("** %d.", SW_VERSION_N1)
141 PRINTF1("%d." , SW_VERSION_N2)
140 PRINTF1("%d." , SW_VERSION_N2)
142 PRINTF1("%d." , SW_VERSION_N3)
141 PRINTF1("%d." , SW_VERSION_N3)
143 PRINTF1("%d **\n", SW_VERSION_N4)
142 PRINTF1("%d **\n", SW_VERSION_N4)
144
143
145 vhdlVersion = (unsigned char *) (REGS_ADDR_VHDL_VERSION);
144 vhdlVersion = (unsigned char *) (REGS_ADDR_VHDL_VERSION);
146 PRINTF("** VHDL **\n")
145 PRINTF("** VHDL **\n")
147 PRINTF1("** %d.", vhdlVersion[1])
146 PRINTF1("** %d.", vhdlVersion[1])
148 PRINTF1("%d." , vhdlVersion[2])
147 PRINTF1("%d." , vhdlVersion[2])
149 PRINTF1("%d **\n", vhdlVersion[3])
148 PRINTF1("%d **\n", vhdlVersion[3])
150 PRINTF("*************************\n")
149 PRINTF("*************************\n")
151 PRINTF("\n\n")
150 PRINTF("\n\n")
152
151
153 init_parameter_dump();
152 init_parameter_dump();
154 init_kcoefficients_dump();
153 init_kcoefficients_dump();
155 init_local_mode_parameters();
154 init_local_mode_parameters();
156 init_housekeeping_parameters();
155 init_housekeeping_parameters();
157 init_k_coefficients_prc0();
156 init_k_coefficients_prc0();
158 init_k_coefficients_prc1();
157 init_k_coefficients_prc1();
159 init_k_coefficients_prc2();
158 init_k_coefficients_prc2();
160 pa_bia_status_info = 0x00;
159 pa_bia_status_info = 0x00;
161 update_last_valid_transition_date( DEFAULT_LAST_VALID_TRANSITION_DATE );
160 update_last_valid_transition_date( DEFAULT_LAST_VALID_TRANSITION_DATE );
162
161
163 // waveform picker initialization
162 // waveform picker initialization
164 WFP_init_rings(); LEON_Clear_interrupt( IRQ_SPARC_GPTIMER_WATCHDOG ); // initialize the waveform rings
163 WFP_init_rings(); LEON_Clear_interrupt( IRQ_SPARC_GPTIMER_WATCHDOG ); // initialize the waveform rings
165 WFP_reset_current_ring_nodes();
164 WFP_reset_current_ring_nodes();
166 reset_waveform_picker_regs();
165 reset_waveform_picker_regs();
167
166
168 // spectral matrices initialization
167 // spectral matrices initialization
169 SM_init_rings(); // initialize spectral matrices rings
168 SM_init_rings(); // initialize spectral matrices rings
170 SM_reset_current_ring_nodes();
169 SM_reset_current_ring_nodes();
171 reset_spectral_matrix_regs();
170 reset_spectral_matrix_regs();
172
171
173 // configure calibration
172 // configure calibration
174 configureCalibration( false ); // true means interleaved mode, false is for normal mode
173 configureCalibration( false ); // true means interleaved mode, false is for normal mode
175
174
176 updateLFRCurrentMode();
175 updateLFRCurrentMode();
177
176
178 BOOT_PRINTF1("in INIT *** lfrCurrentMode is %d\n", lfrCurrentMode)
177 BOOT_PRINTF1("in INIT *** lfrCurrentMode is %d\n", lfrCurrentMode)
179
178
180 create_names(); // create all names
179 create_names(); // create all names
181
180
182 status = create_timecode_timer(); // create the timer used by timecode_irq_handler
181 status = create_timecode_timer(); // create the timer used by timecode_irq_handler
183 if (status != RTEMS_SUCCESSFUL)
182 if (status != RTEMS_SUCCESSFUL)
184 {
183 {
185 PRINTF1("in INIT *** ERR in create_timer_timecode, code %d", status)
184 PRINTF1("in INIT *** ERR in create_timer_timecode, code %d", status)
186 }
185 }
187
186
188 status = create_message_queues(); // create message queues
187 status = create_message_queues(); // create message queues
189 if (status != RTEMS_SUCCESSFUL)
188 if (status != RTEMS_SUCCESSFUL)
190 {
189 {
191 PRINTF1("in INIT *** ERR in create_message_queues, code %d", status)
190 PRINTF1("in INIT *** ERR in create_message_queues, code %d", status)
192 }
191 }
193
192
194 status = create_all_tasks(); // create all tasks
193 status = create_all_tasks(); // create all tasks
195 if (status != RTEMS_SUCCESSFUL)
194 if (status != RTEMS_SUCCESSFUL)
196 {
195 {
197 PRINTF1("in INIT *** ERR in create_all_tasks, code %d\n", status)
196 PRINTF1("in INIT *** ERR in create_all_tasks, code %d\n", status)
198 }
197 }
199
198
200 // **************************
199 // **************************
201 // <SPACEWIRE INITIALIZATION>
200 // <SPACEWIRE INITIALIZATION>
202 grspw_timecode_callback = &timecode_irq_handler;
201 grspw_timecode_callback = &timecode_irq_handler;
203
202
204 status_spw = spacewire_open_link(); // (1) open the link
203 status_spw = spacewire_open_link(); // (1) open the link
205 if ( status_spw != RTEMS_SUCCESSFUL )
204 if ( status_spw != RTEMS_SUCCESSFUL )
206 {
205 {
207 PRINTF1("in INIT *** ERR spacewire_open_link code %d\n", status_spw )
206 PRINTF1("in INIT *** ERR spacewire_open_link code %d\n", status_spw )
208 }
207 }
209
208
210 if ( status_spw == RTEMS_SUCCESSFUL ) // (2) configure the link
209 if ( status_spw == RTEMS_SUCCESSFUL ) // (2) configure the link
211 {
210 {
212 status_spw = spacewire_configure_link( fdSPW );
211 status_spw = spacewire_configure_link( fdSPW );
213 if ( status_spw != RTEMS_SUCCESSFUL )
212 if ( status_spw != RTEMS_SUCCESSFUL )
214 {
213 {
215 PRINTF1("in INIT *** ERR spacewire_configure_link code %d\n", status_spw )
214 PRINTF1("in INIT *** ERR spacewire_configure_link code %d\n", status_spw )
216 }
215 }
217 }
216 }
218
217
219 if ( status_spw == RTEMS_SUCCESSFUL) // (3) start the link
218 if ( status_spw == RTEMS_SUCCESSFUL) // (3) start the link
220 {
219 {
221 status_spw = spacewire_start_link( fdSPW );
220 status_spw = spacewire_start_link( fdSPW );
222 if ( status_spw != RTEMS_SUCCESSFUL )
221 if ( status_spw != RTEMS_SUCCESSFUL )
223 {
222 {
224 PRINTF1("in INIT *** ERR spacewire_start_link code %d\n", status_spw )
223 PRINTF1("in INIT *** ERR spacewire_start_link code %d\n", status_spw )
225 }
224 }
226 }
225 }
227 // </SPACEWIRE INITIALIZATION>
226 // </SPACEWIRE INITIALIZATION>
228 // ***************************
227 // ***************************
229
228
230 status = start_all_tasks(); // start all tasks
229 status = start_all_tasks(); // start all tasks
231 if (status != RTEMS_SUCCESSFUL)
230 if (status != RTEMS_SUCCESSFUL)
232 {
231 {
233 PRINTF1("in INIT *** ERR in start_all_tasks, code %d", status)
232 PRINTF1("in INIT *** ERR in start_all_tasks, code %d", status)
234 }
233 }
235
234
236 // start RECV and SEND *AFTER* SpaceWire Initialization, due to the timeout of the start call during the initialization
235 // start RECV and SEND *AFTER* SpaceWire Initialization, due to the timeout of the start call during the initialization
237 status = start_recv_send_tasks();
236 status = start_recv_send_tasks();
238 if ( status != RTEMS_SUCCESSFUL )
237 if ( status != RTEMS_SUCCESSFUL )
239 {
238 {
240 PRINTF1("in INIT *** ERR start_recv_send_tasks code %d\n", status )
239 PRINTF1("in INIT *** ERR start_recv_send_tasks code %d\n", status )
241 }
240 }
242
241
243 // suspend science tasks, they will be restarted later depending on the mode
242 // suspend science tasks, they will be restarted later depending on the mode
244 status = suspend_science_tasks(); // suspend science tasks (not done in stop_current_mode if current mode = STANDBY)
243 status = suspend_science_tasks(); // suspend science tasks (not done in stop_current_mode if current mode = STANDBY)
245 if (status != RTEMS_SUCCESSFUL)
244 if (status != RTEMS_SUCCESSFUL)
246 {
245 {
247 PRINTF1("in INIT *** in suspend_science_tasks *** ERR code: %d\n", status)
246 PRINTF1("in INIT *** in suspend_science_tasks *** ERR code: %d\n", status)
248 }
247 }
249
248
250 // configure IRQ handling for the waveform picker unit
249 // configure IRQ handling for the waveform picker unit
251 status = rtems_interrupt_catch( waveforms_isr,
250 status = rtems_interrupt_catch( waveforms_isr,
252 IRQ_SPARC_WAVEFORM_PICKER,
251 IRQ_SPARC_WAVEFORM_PICKER,
253 &old_isr_handler) ;
252 &old_isr_handler) ;
254 // configure IRQ handling for the spectral matrices unit
253 // configure IRQ handling for the spectral matrices unit
255 status = rtems_interrupt_catch( spectral_matrices_isr,
254 status = rtems_interrupt_catch( spectral_matrices_isr,
256 IRQ_SPARC_SPECTRAL_MATRIX,
255 IRQ_SPARC_SPECTRAL_MATRIX,
257 &old_isr_handler) ;
256 &old_isr_handler) ;
258
257
259 // if the spacewire link is not up then send an event to the SPIQ task for link recovery
258 // if the spacewire link is not up then send an event to the SPIQ task for link recovery
260 if ( status_spw != RTEMS_SUCCESSFUL )
259 if ( status_spw != RTEMS_SUCCESSFUL )
261 {
260 {
262 status = rtems_event_send( Task_id[TASKID_SPIQ], SPW_LINKERR_EVENT );
261 status = rtems_event_send( Task_id[TASKID_SPIQ], SPW_LINKERR_EVENT );
263 if ( status != RTEMS_SUCCESSFUL ) {
262 if ( status != RTEMS_SUCCESSFUL ) {
264 PRINTF1("in INIT *** ERR rtems_event_send to SPIQ code %d\n", status )
263 PRINTF1("in INIT *** ERR rtems_event_send to SPIQ code %d\n", status )
265 }
264 }
266 }
265 }
267
266
268 BOOT_PRINTF("delete INIT\n")
267 BOOT_PRINTF("delete INIT\n")
269
268
270 set_hk_lfr_sc_potential_flag( true );
269 set_hk_lfr_sc_potential_flag( true );
271
270
272 status = rtems_task_delete(RTEMS_SELF);
271 status = rtems_task_delete(RTEMS_SELF);
273
272
274 }
273 }
275
274
276 void init_local_mode_parameters( void )
275 void init_local_mode_parameters( void )
277 {
276 {
278 /** This function initialize the param_local global variable with default values.
277 /** This function initialize the param_local global variable with default values.
279 *
278 *
280 */
279 */
281
280
282 unsigned int i;
281 unsigned int i;
283
282
284 // LOCAL PARAMETERS
283 // LOCAL PARAMETERS
285
284
286 BOOT_PRINTF1("local_sbm1_nb_cwf_max %d \n", param_local.local_sbm1_nb_cwf_max)
285 BOOT_PRINTF1("local_sbm1_nb_cwf_max %d \n", param_local.local_sbm1_nb_cwf_max)
287 BOOT_PRINTF1("local_sbm2_nb_cwf_max %d \n", param_local.local_sbm2_nb_cwf_max)
286 BOOT_PRINTF1("local_sbm2_nb_cwf_max %d \n", param_local.local_sbm2_nb_cwf_max)
288 BOOT_PRINTF1("nb_interrupt_f0_MAX = %d\n", param_local.local_nb_interrupt_f0_MAX)
287 BOOT_PRINTF1("nb_interrupt_f0_MAX = %d\n", param_local.local_nb_interrupt_f0_MAX)
289
288
290 // init sequence counters
289 // init sequence counters
291
290
292 for(i = 0; i<SEQ_CNT_NB_DEST_ID; i++)
291 for(i = 0; i<SEQ_CNT_NB_DEST_ID; i++)
293 {
292 {
294 sequenceCounters_TC_EXE[i] = 0x00;
293 sequenceCounters_TC_EXE[i] = 0x00;
295 sequenceCounters_TM_DUMP[i] = 0x00;
294 sequenceCounters_TM_DUMP[i] = 0x00;
296 }
295 }
297 sequenceCounters_SCIENCE_NORMAL_BURST = 0x00;
296 sequenceCounters_SCIENCE_NORMAL_BURST = 0x00;
298 sequenceCounters_SCIENCE_SBM1_SBM2 = 0x00;
297 sequenceCounters_SCIENCE_SBM1_SBM2 = 0x00;
299 sequenceCounterHK = TM_PACKET_SEQ_CTRL_STANDALONE << 8;
298 sequenceCounterHK = TM_PACKET_SEQ_CTRL_STANDALONE << 8;
300 }
299 }
301
300
302 void reset_local_time( void )
301 void reset_local_time( void )
303 {
302 {
304 time_management_regs->ctrl = time_management_regs->ctrl | 0x02; // [0010] software reset, coarse time = 0x80000000
303 time_management_regs->ctrl = time_management_regs->ctrl | 0x02; // [0010] software reset, coarse time = 0x80000000
305 }
304 }
306
305
307 void create_names( void ) // create all names for tasks and queues
306 void create_names( void ) // create all names for tasks and queues
308 {
307 {
309 /** This function creates all RTEMS names used in the software for tasks and queues.
308 /** This function creates all RTEMS names used in the software for tasks and queues.
310 *
309 *
311 * @return RTEMS directive status codes:
310 * @return RTEMS directive status codes:
312 * - RTEMS_SUCCESSFUL - successful completion
311 * - RTEMS_SUCCESSFUL - successful completion
313 *
312 *
314 */
313 */
315
314
316 // task names
315 // task names
317 Task_name[TASKID_RECV] = rtems_build_name( 'R', 'E', 'C', 'V' );
316 Task_name[TASKID_RECV] = rtems_build_name( 'R', 'E', 'C', 'V' );
318 Task_name[TASKID_ACTN] = rtems_build_name( 'A', 'C', 'T', 'N' );
317 Task_name[TASKID_ACTN] = rtems_build_name( 'A', 'C', 'T', 'N' );
319 Task_name[TASKID_SPIQ] = rtems_build_name( 'S', 'P', 'I', 'Q' );
318 Task_name[TASKID_SPIQ] = rtems_build_name( 'S', 'P', 'I', 'Q' );
320 Task_name[TASKID_LOAD] = rtems_build_name( 'L', 'O', 'A', 'D' );
319 Task_name[TASKID_LOAD] = rtems_build_name( 'L', 'O', 'A', 'D' );
321 Task_name[TASKID_AVF0] = rtems_build_name( 'A', 'V', 'F', '0' );
320 Task_name[TASKID_AVF0] = rtems_build_name( 'A', 'V', 'F', '0' );
322 Task_name[TASKID_SWBD] = rtems_build_name( 'S', 'W', 'B', 'D' );
321 Task_name[TASKID_SWBD] = rtems_build_name( 'S', 'W', 'B', 'D' );
323 Task_name[TASKID_WFRM] = rtems_build_name( 'W', 'F', 'R', 'M' );
322 Task_name[TASKID_WFRM] = rtems_build_name( 'W', 'F', 'R', 'M' );
324 Task_name[TASKID_DUMB] = rtems_build_name( 'D', 'U', 'M', 'B' );
323 Task_name[TASKID_DUMB] = rtems_build_name( 'D', 'U', 'M', 'B' );
325 Task_name[TASKID_HOUS] = rtems_build_name( 'H', 'O', 'U', 'S' );
324 Task_name[TASKID_HOUS] = rtems_build_name( 'H', 'O', 'U', 'S' );
326 Task_name[TASKID_PRC0] = rtems_build_name( 'P', 'R', 'C', '0' );
325 Task_name[TASKID_PRC0] = rtems_build_name( 'P', 'R', 'C', '0' );
327 Task_name[TASKID_CWF3] = rtems_build_name( 'C', 'W', 'F', '3' );
326 Task_name[TASKID_CWF3] = rtems_build_name( 'C', 'W', 'F', '3' );
328 Task_name[TASKID_CWF2] = rtems_build_name( 'C', 'W', 'F', '2' );
327 Task_name[TASKID_CWF2] = rtems_build_name( 'C', 'W', 'F', '2' );
329 Task_name[TASKID_CWF1] = rtems_build_name( 'C', 'W', 'F', '1' );
328 Task_name[TASKID_CWF1] = rtems_build_name( 'C', 'W', 'F', '1' );
330 Task_name[TASKID_SEND] = rtems_build_name( 'S', 'E', 'N', 'D' );
329 Task_name[TASKID_SEND] = rtems_build_name( 'S', 'E', 'N', 'D' );
331 Task_name[TASKID_WTDG] = rtems_build_name( 'W', 'T', 'D', 'G' );
330 Task_name[TASKID_WTDG] = rtems_build_name( 'W', 'T', 'D', 'G' );
332 Task_name[TASKID_AVF1] = rtems_build_name( 'A', 'V', 'F', '1' );
331 Task_name[TASKID_AVF1] = rtems_build_name( 'A', 'V', 'F', '1' );
333 Task_name[TASKID_PRC1] = rtems_build_name( 'P', 'R', 'C', '1' );
332 Task_name[TASKID_PRC1] = rtems_build_name( 'P', 'R', 'C', '1' );
334 Task_name[TASKID_AVF2] = rtems_build_name( 'A', 'V', 'F', '2' );
333 Task_name[TASKID_AVF2] = rtems_build_name( 'A', 'V', 'F', '2' );
335 Task_name[TASKID_PRC2] = rtems_build_name( 'P', 'R', 'C', '2' );
334 Task_name[TASKID_PRC2] = rtems_build_name( 'P', 'R', 'C', '2' );
336
335
337 // rate monotonic period names
336 // rate monotonic period names
338 name_hk_rate_monotonic = rtems_build_name( 'H', 'O', 'U', 'S' );
337 name_hk_rate_monotonic = rtems_build_name( 'H', 'O', 'U', 'S' );
339
338
340 misc_name[QUEUE_RECV] = rtems_build_name( 'Q', '_', 'R', 'V' );
339 misc_name[QUEUE_RECV] = rtems_build_name( 'Q', '_', 'R', 'V' );
341 misc_name[QUEUE_SEND] = rtems_build_name( 'Q', '_', 'S', 'D' );
340 misc_name[QUEUE_SEND] = rtems_build_name( 'Q', '_', 'S', 'D' );
342 misc_name[QUEUE_PRC0] = rtems_build_name( 'Q', '_', 'P', '0' );
341 misc_name[QUEUE_PRC0] = rtems_build_name( 'Q', '_', 'P', '0' );
343 misc_name[QUEUE_PRC1] = rtems_build_name( 'Q', '_', 'P', '1' );
342 misc_name[QUEUE_PRC1] = rtems_build_name( 'Q', '_', 'P', '1' );
344 misc_name[QUEUE_PRC2] = rtems_build_name( 'Q', '_', 'P', '2' );
343 misc_name[QUEUE_PRC2] = rtems_build_name( 'Q', '_', 'P', '2' );
345
344
346 timecode_timer_name = rtems_build_name( 'S', 'P', 'T', 'C' );
345 timecode_timer_name = rtems_build_name( 'S', 'P', 'T', 'C' );
347 }
346 }
348
347
349 int create_all_tasks( void ) // create all tasks which run in the software
348 int create_all_tasks( void ) // create all tasks which run in the software
350 {
349 {
351 /** This function creates all RTEMS tasks used in the software.
350 /** This function creates all RTEMS tasks used in the software.
352 *
351 *
353 * @return RTEMS directive status codes:
352 * @return RTEMS directive status codes:
354 * - RTEMS_SUCCESSFUL - task created successfully
353 * - RTEMS_SUCCESSFUL - task created successfully
355 * - RTEMS_INVALID_ADDRESS - id is NULL
354 * - RTEMS_INVALID_ADDRESS - id is NULL
356 * - RTEMS_INVALID_NAME - invalid task name
355 * - RTEMS_INVALID_NAME - invalid task name
357 * - RTEMS_INVALID_PRIORITY - invalid task priority
356 * - RTEMS_INVALID_PRIORITY - invalid task priority
358 * - RTEMS_MP_NOT_CONFIGURED - multiprocessing not configured
357 * - RTEMS_MP_NOT_CONFIGURED - multiprocessing not configured
359 * - RTEMS_TOO_MANY - too many tasks created
358 * - RTEMS_TOO_MANY - too many tasks created
360 * - RTEMS_UNSATISFIED - not enough memory for stack/FP context
359 * - RTEMS_UNSATISFIED - not enough memory for stack/FP context
361 * - RTEMS_TOO_MANY - too many global objects
360 * - RTEMS_TOO_MANY - too many global objects
362 *
361 *
363 */
362 */
364
363
365 rtems_status_code status;
364 rtems_status_code status;
366
365
367 //**********
366 //**********
368 // SPACEWIRE
367 // SPACEWIRE
369 // RECV
368 // RECV
370 status = rtems_task_create(
369 status = rtems_task_create(
371 Task_name[TASKID_RECV], TASK_PRIORITY_RECV, RTEMS_MINIMUM_STACK_SIZE,
370 Task_name[TASKID_RECV], TASK_PRIORITY_RECV, RTEMS_MINIMUM_STACK_SIZE,
372 RTEMS_DEFAULT_MODES,
371 RTEMS_DEFAULT_MODES,
373 RTEMS_DEFAULT_ATTRIBUTES, &Task_id[TASKID_RECV]
372 RTEMS_DEFAULT_ATTRIBUTES, &Task_id[TASKID_RECV]
374 );
373 );
375 if (status == RTEMS_SUCCESSFUL) // SEND
374 if (status == RTEMS_SUCCESSFUL) // SEND
376 {
375 {
377 status = rtems_task_create(
376 status = rtems_task_create(
378 Task_name[TASKID_SEND], TASK_PRIORITY_SEND, RTEMS_MINIMUM_STACK_SIZE * 2,
377 Task_name[TASKID_SEND], TASK_PRIORITY_SEND, RTEMS_MINIMUM_STACK_SIZE * 2,
379 RTEMS_DEFAULT_MODES,
378 RTEMS_DEFAULT_MODES,
380 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_SEND]
379 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_SEND]
381 );
380 );
382 }
381 }
383 if (status == RTEMS_SUCCESSFUL) // WTDG
382 if (status == RTEMS_SUCCESSFUL) // WTDG
384 {
383 {
385 status = rtems_task_create(
384 status = rtems_task_create(
386 Task_name[TASKID_WTDG], TASK_PRIORITY_WTDG, RTEMS_MINIMUM_STACK_SIZE,
385 Task_name[TASKID_WTDG], TASK_PRIORITY_WTDG, RTEMS_MINIMUM_STACK_SIZE,
387 RTEMS_DEFAULT_MODES,
386 RTEMS_DEFAULT_MODES,
388 RTEMS_DEFAULT_ATTRIBUTES, &Task_id[TASKID_WTDG]
387 RTEMS_DEFAULT_ATTRIBUTES, &Task_id[TASKID_WTDG]
389 );
388 );
390 }
389 }
391 if (status == RTEMS_SUCCESSFUL) // ACTN
390 if (status == RTEMS_SUCCESSFUL) // ACTN
392 {
391 {
393 status = rtems_task_create(
392 status = rtems_task_create(
394 Task_name[TASKID_ACTN], TASK_PRIORITY_ACTN, RTEMS_MINIMUM_STACK_SIZE,
393 Task_name[TASKID_ACTN], TASK_PRIORITY_ACTN, RTEMS_MINIMUM_STACK_SIZE,
395 RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT,
394 RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT,
396 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_ACTN]
395 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_ACTN]
397 );
396 );
398 }
397 }
399 if (status == RTEMS_SUCCESSFUL) // SPIQ
398 if (status == RTEMS_SUCCESSFUL) // SPIQ
400 {
399 {
401 status = rtems_task_create(
400 status = rtems_task_create(
402 Task_name[TASKID_SPIQ], TASK_PRIORITY_SPIQ, RTEMS_MINIMUM_STACK_SIZE,
401 Task_name[TASKID_SPIQ], TASK_PRIORITY_SPIQ, RTEMS_MINIMUM_STACK_SIZE,
403 RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT,
402 RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT,
404 RTEMS_DEFAULT_ATTRIBUTES, &Task_id[TASKID_SPIQ]
403 RTEMS_DEFAULT_ATTRIBUTES, &Task_id[TASKID_SPIQ]
405 );
404 );
406 }
405 }
407
406
408 //******************
407 //******************
409 // SPECTRAL MATRICES
408 // SPECTRAL MATRICES
410 if (status == RTEMS_SUCCESSFUL) // AVF0
409 if (status == RTEMS_SUCCESSFUL) // AVF0
411 {
410 {
412 status = rtems_task_create(
411 status = rtems_task_create(
413 Task_name[TASKID_AVF0], TASK_PRIORITY_AVF0, RTEMS_MINIMUM_STACK_SIZE,
412 Task_name[TASKID_AVF0], TASK_PRIORITY_AVF0, RTEMS_MINIMUM_STACK_SIZE,
414 RTEMS_DEFAULT_MODES,
413 RTEMS_DEFAULT_MODES,
415 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_AVF0]
414 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_AVF0]
416 );
415 );
417 }
416 }
418 if (status == RTEMS_SUCCESSFUL) // PRC0
417 if (status == RTEMS_SUCCESSFUL) // PRC0
419 {
418 {
420 status = rtems_task_create(
419 status = rtems_task_create(
421 Task_name[TASKID_PRC0], TASK_PRIORITY_PRC0, RTEMS_MINIMUM_STACK_SIZE * 2,
420 Task_name[TASKID_PRC0], TASK_PRIORITY_PRC0, RTEMS_MINIMUM_STACK_SIZE * 2,
422 RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT,
421 RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT,
423 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_PRC0]
422 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_PRC0]
424 );
423 );
425 }
424 }
426 if (status == RTEMS_SUCCESSFUL) // AVF1
425 if (status == RTEMS_SUCCESSFUL) // AVF1
427 {
426 {
428 status = rtems_task_create(
427 status = rtems_task_create(
429 Task_name[TASKID_AVF1], TASK_PRIORITY_AVF1, RTEMS_MINIMUM_STACK_SIZE,
428 Task_name[TASKID_AVF1], TASK_PRIORITY_AVF1, RTEMS_MINIMUM_STACK_SIZE,
430 RTEMS_DEFAULT_MODES,
429 RTEMS_DEFAULT_MODES,
431 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_AVF1]
430 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_AVF1]
432 );
431 );
433 }
432 }
434 if (status == RTEMS_SUCCESSFUL) // PRC1
433 if (status == RTEMS_SUCCESSFUL) // PRC1
435 {
434 {
436 status = rtems_task_create(
435 status = rtems_task_create(
437 Task_name[TASKID_PRC1], TASK_PRIORITY_PRC1, RTEMS_MINIMUM_STACK_SIZE * 2,
436 Task_name[TASKID_PRC1], TASK_PRIORITY_PRC1, RTEMS_MINIMUM_STACK_SIZE * 2,
438 RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT,
437 RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT,
439 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_PRC1]
438 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_PRC1]
440 );
439 );
441 }
440 }
442 if (status == RTEMS_SUCCESSFUL) // AVF2
441 if (status == RTEMS_SUCCESSFUL) // AVF2
443 {
442 {
444 status = rtems_task_create(
443 status = rtems_task_create(
445 Task_name[TASKID_AVF2], TASK_PRIORITY_AVF2, RTEMS_MINIMUM_STACK_SIZE,
444 Task_name[TASKID_AVF2], TASK_PRIORITY_AVF2, RTEMS_MINIMUM_STACK_SIZE,
446 RTEMS_DEFAULT_MODES,
445 RTEMS_DEFAULT_MODES,
447 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_AVF2]
446 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_AVF2]
448 );
447 );
449 }
448 }
450 if (status == RTEMS_SUCCESSFUL) // PRC2
449 if (status == RTEMS_SUCCESSFUL) // PRC2
451 {
450 {
452 status = rtems_task_create(
451 status = rtems_task_create(
453 Task_name[TASKID_PRC2], TASK_PRIORITY_PRC2, RTEMS_MINIMUM_STACK_SIZE * 2,
452 Task_name[TASKID_PRC2], TASK_PRIORITY_PRC2, RTEMS_MINIMUM_STACK_SIZE * 2,
454 RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT,
453 RTEMS_DEFAULT_MODES | RTEMS_NO_PREEMPT,
455 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_PRC2]
454 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_PRC2]
456 );
455 );
457 }
456 }
458
457
459 //****************
458 //****************
460 // WAVEFORM PICKER
459 // WAVEFORM PICKER
461 if (status == RTEMS_SUCCESSFUL) // WFRM
460 if (status == RTEMS_SUCCESSFUL) // WFRM
462 {
461 {
463 status = rtems_task_create(
462 status = rtems_task_create(
464 Task_name[TASKID_WFRM], TASK_PRIORITY_WFRM, RTEMS_MINIMUM_STACK_SIZE,
463 Task_name[TASKID_WFRM], TASK_PRIORITY_WFRM, RTEMS_MINIMUM_STACK_SIZE,
465 RTEMS_DEFAULT_MODES,
464 RTEMS_DEFAULT_MODES,
466 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_WFRM]
465 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_WFRM]
467 );
466 );
468 }
467 }
469 if (status == RTEMS_SUCCESSFUL) // CWF3
468 if (status == RTEMS_SUCCESSFUL) // CWF3
470 {
469 {
471 status = rtems_task_create(
470 status = rtems_task_create(
472 Task_name[TASKID_CWF3], TASK_PRIORITY_CWF3, RTEMS_MINIMUM_STACK_SIZE,
471 Task_name[TASKID_CWF3], TASK_PRIORITY_CWF3, RTEMS_MINIMUM_STACK_SIZE,
473 RTEMS_DEFAULT_MODES,
472 RTEMS_DEFAULT_MODES,
474 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_CWF3]
473 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_CWF3]
475 );
474 );
476 }
475 }
477 if (status == RTEMS_SUCCESSFUL) // CWF2
476 if (status == RTEMS_SUCCESSFUL) // CWF2
478 {
477 {
479 status = rtems_task_create(
478 status = rtems_task_create(
480 Task_name[TASKID_CWF2], TASK_PRIORITY_CWF2, RTEMS_MINIMUM_STACK_SIZE,
479 Task_name[TASKID_CWF2], TASK_PRIORITY_CWF2, RTEMS_MINIMUM_STACK_SIZE,
481 RTEMS_DEFAULT_MODES,
480 RTEMS_DEFAULT_MODES,
482 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_CWF2]
481 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_CWF2]
483 );
482 );
484 }
483 }
485 if (status == RTEMS_SUCCESSFUL) // CWF1
484 if (status == RTEMS_SUCCESSFUL) // CWF1
486 {
485 {
487 status = rtems_task_create(
486 status = rtems_task_create(
488 Task_name[TASKID_CWF1], TASK_PRIORITY_CWF1, RTEMS_MINIMUM_STACK_SIZE,
487 Task_name[TASKID_CWF1], TASK_PRIORITY_CWF1, RTEMS_MINIMUM_STACK_SIZE,
489 RTEMS_DEFAULT_MODES,
488 RTEMS_DEFAULT_MODES,
490 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_CWF1]
489 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_CWF1]
491 );
490 );
492 }
491 }
493 if (status == RTEMS_SUCCESSFUL) // SWBD
492 if (status == RTEMS_SUCCESSFUL) // SWBD
494 {
493 {
495 status = rtems_task_create(
494 status = rtems_task_create(
496 Task_name[TASKID_SWBD], TASK_PRIORITY_SWBD, RTEMS_MINIMUM_STACK_SIZE,
495 Task_name[TASKID_SWBD], TASK_PRIORITY_SWBD, RTEMS_MINIMUM_STACK_SIZE,
497 RTEMS_DEFAULT_MODES,
496 RTEMS_DEFAULT_MODES,
498 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_SWBD]
497 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_SWBD]
499 );
498 );
500 }
499 }
501
500
502 //*****
501 //*****
503 // MISC
502 // MISC
504 if (status == RTEMS_SUCCESSFUL) // LOAD
503 if (status == RTEMS_SUCCESSFUL) // LOAD
505 {
504 {
506 status = rtems_task_create(
505 status = rtems_task_create(
507 Task_name[TASKID_LOAD], TASK_PRIORITY_LOAD, RTEMS_MINIMUM_STACK_SIZE,
506 Task_name[TASKID_LOAD], TASK_PRIORITY_LOAD, RTEMS_MINIMUM_STACK_SIZE,
508 RTEMS_DEFAULT_MODES,
507 RTEMS_DEFAULT_MODES,
509 RTEMS_DEFAULT_ATTRIBUTES, &Task_id[TASKID_LOAD]
508 RTEMS_DEFAULT_ATTRIBUTES, &Task_id[TASKID_LOAD]
510 );
509 );
511 }
510 }
512 if (status == RTEMS_SUCCESSFUL) // DUMB
511 if (status == RTEMS_SUCCESSFUL) // DUMB
513 {
512 {
514 status = rtems_task_create(
513 status = rtems_task_create(
515 Task_name[TASKID_DUMB], TASK_PRIORITY_DUMB, RTEMS_MINIMUM_STACK_SIZE,
514 Task_name[TASKID_DUMB], TASK_PRIORITY_DUMB, RTEMS_MINIMUM_STACK_SIZE,
516 RTEMS_DEFAULT_MODES,
515 RTEMS_DEFAULT_MODES,
517 RTEMS_DEFAULT_ATTRIBUTES, &Task_id[TASKID_DUMB]
516 RTEMS_DEFAULT_ATTRIBUTES, &Task_id[TASKID_DUMB]
518 );
517 );
519 }
518 }
520 if (status == RTEMS_SUCCESSFUL) // HOUS
519 if (status == RTEMS_SUCCESSFUL) // HOUS
521 {
520 {
522 status = rtems_task_create(
521 status = rtems_task_create(
523 Task_name[TASKID_HOUS], TASK_PRIORITY_HOUS, RTEMS_MINIMUM_STACK_SIZE,
522 Task_name[TASKID_HOUS], TASK_PRIORITY_HOUS, RTEMS_MINIMUM_STACK_SIZE,
524 RTEMS_DEFAULT_MODES,
523 RTEMS_DEFAULT_MODES,
525 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_HOUS]
524 RTEMS_DEFAULT_ATTRIBUTES | RTEMS_FLOATING_POINT, &Task_id[TASKID_HOUS]
526 );
525 );
527 }
526 }
528
527
529 return status;
528 return status;
530 }
529 }
531
530
532 int start_recv_send_tasks( void )
531 int start_recv_send_tasks( void )
533 {
532 {
534 rtems_status_code status;
533 rtems_status_code status;
535
534
536 status = rtems_task_start( Task_id[TASKID_RECV], recv_task, 1 );
535 status = rtems_task_start( Task_id[TASKID_RECV], recv_task, 1 );
537 if (status!=RTEMS_SUCCESSFUL) {
536 if (status!=RTEMS_SUCCESSFUL) {
538 BOOT_PRINTF("in INIT *** Error starting TASK_RECV\n")
537 BOOT_PRINTF("in INIT *** Error starting TASK_RECV\n")
539 }
538 }
540
539
541 if (status == RTEMS_SUCCESSFUL) // SEND
540 if (status == RTEMS_SUCCESSFUL) // SEND
542 {
541 {
543 status = rtems_task_start( Task_id[TASKID_SEND], send_task, 1 );
542 status = rtems_task_start( Task_id[TASKID_SEND], send_task, 1 );
544 if (status!=RTEMS_SUCCESSFUL) {
543 if (status!=RTEMS_SUCCESSFUL) {
545 BOOT_PRINTF("in INIT *** Error starting TASK_SEND\n")
544 BOOT_PRINTF("in INIT *** Error starting TASK_SEND\n")
546 }
545 }
547 }
546 }
548
547
549 return status;
548 return status;
550 }
549 }
551
550
552 int start_all_tasks( void ) // start all tasks except SEND RECV and HOUS
551 int start_all_tasks( void ) // start all tasks except SEND RECV and HOUS
553 {
552 {
554 /** This function starts all RTEMS tasks used in the software.
553 /** This function starts all RTEMS tasks used in the software.
555 *
554 *
556 * @return RTEMS directive status codes:
555 * @return RTEMS directive status codes:
557 * - RTEMS_SUCCESSFUL - ask started successfully
556 * - RTEMS_SUCCESSFUL - ask started successfully
558 * - RTEMS_INVALID_ADDRESS - invalid task entry point
557 * - RTEMS_INVALID_ADDRESS - invalid task entry point
559 * - RTEMS_INVALID_ID - invalid task id
558 * - RTEMS_INVALID_ID - invalid task id
560 * - RTEMS_INCORRECT_STATE - task not in the dormant state
559 * - RTEMS_INCORRECT_STATE - task not in the dormant state
561 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot start remote task
560 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot start remote task
562 *
561 *
563 */
562 */
564 // starts all the tasks fot eh flight software
563 // starts all the tasks fot eh flight software
565
564
566 rtems_status_code status;
565 rtems_status_code status;
567
566
568 //**********
567 //**********
569 // SPACEWIRE
568 // SPACEWIRE
570 status = rtems_task_start( Task_id[TASKID_SPIQ], spiq_task, 1 );
569 status = rtems_task_start( Task_id[TASKID_SPIQ], spiq_task, 1 );
571 if (status!=RTEMS_SUCCESSFUL) {
570 if (status!=RTEMS_SUCCESSFUL) {
572 BOOT_PRINTF("in INIT *** Error starting TASK_SPIQ\n")
571 BOOT_PRINTF("in INIT *** Error starting TASK_SPIQ\n")
573 }
572 }
574
573
575 if (status == RTEMS_SUCCESSFUL) // WTDG
574 if (status == RTEMS_SUCCESSFUL) // WTDG
576 {
575 {
577 status = rtems_task_start( Task_id[TASKID_WTDG], wtdg_task, 1 );
576 status = rtems_task_start( Task_id[TASKID_WTDG], wtdg_task, 1 );
578 if (status!=RTEMS_SUCCESSFUL) {
577 if (status!=RTEMS_SUCCESSFUL) {
579 BOOT_PRINTF("in INIT *** Error starting TASK_WTDG\n")
578 BOOT_PRINTF("in INIT *** Error starting TASK_WTDG\n")
580 }
579 }
581 }
580 }
582
581
583 if (status == RTEMS_SUCCESSFUL) // ACTN
582 if (status == RTEMS_SUCCESSFUL) // ACTN
584 {
583 {
585 status = rtems_task_start( Task_id[TASKID_ACTN], actn_task, 1 );
584 status = rtems_task_start( Task_id[TASKID_ACTN], actn_task, 1 );
586 if (status!=RTEMS_SUCCESSFUL) {
585 if (status!=RTEMS_SUCCESSFUL) {
587 BOOT_PRINTF("in INIT *** Error starting TASK_ACTN\n")
586 BOOT_PRINTF("in INIT *** Error starting TASK_ACTN\n")
588 }
587 }
589 }
588 }
590
589
591 //******************
590 //******************
592 // SPECTRAL MATRICES
591 // SPECTRAL MATRICES
593 if (status == RTEMS_SUCCESSFUL) // AVF0
592 if (status == RTEMS_SUCCESSFUL) // AVF0
594 {
593 {
595 status = rtems_task_start( Task_id[TASKID_AVF0], avf0_task, LFR_MODE_STANDBY );
594 status = rtems_task_start( Task_id[TASKID_AVF0], avf0_task, LFR_MODE_STANDBY );
596 if (status!=RTEMS_SUCCESSFUL) {
595 if (status!=RTEMS_SUCCESSFUL) {
597 BOOT_PRINTF("in INIT *** Error starting TASK_AVF0\n")
596 BOOT_PRINTF("in INIT *** Error starting TASK_AVF0\n")
598 }
597 }
599 }
598 }
600 if (status == RTEMS_SUCCESSFUL) // PRC0
599 if (status == RTEMS_SUCCESSFUL) // PRC0
601 {
600 {
602 status = rtems_task_start( Task_id[TASKID_PRC0], prc0_task, LFR_MODE_STANDBY );
601 status = rtems_task_start( Task_id[TASKID_PRC0], prc0_task, LFR_MODE_STANDBY );
603 if (status!=RTEMS_SUCCESSFUL) {
602 if (status!=RTEMS_SUCCESSFUL) {
604 BOOT_PRINTF("in INIT *** Error starting TASK_PRC0\n")
603 BOOT_PRINTF("in INIT *** Error starting TASK_PRC0\n")
605 }
604 }
606 }
605 }
607 if (status == RTEMS_SUCCESSFUL) // AVF1
606 if (status == RTEMS_SUCCESSFUL) // AVF1
608 {
607 {
609 status = rtems_task_start( Task_id[TASKID_AVF1], avf1_task, LFR_MODE_STANDBY );
608 status = rtems_task_start( Task_id[TASKID_AVF1], avf1_task, LFR_MODE_STANDBY );
610 if (status!=RTEMS_SUCCESSFUL) {
609 if (status!=RTEMS_SUCCESSFUL) {
611 BOOT_PRINTF("in INIT *** Error starting TASK_AVF1\n")
610 BOOT_PRINTF("in INIT *** Error starting TASK_AVF1\n")
612 }
611 }
613 }
612 }
614 if (status == RTEMS_SUCCESSFUL) // PRC1
613 if (status == RTEMS_SUCCESSFUL) // PRC1
615 {
614 {
616 status = rtems_task_start( Task_id[TASKID_PRC1], prc1_task, LFR_MODE_STANDBY );
615 status = rtems_task_start( Task_id[TASKID_PRC1], prc1_task, LFR_MODE_STANDBY );
617 if (status!=RTEMS_SUCCESSFUL) {
616 if (status!=RTEMS_SUCCESSFUL) {
618 BOOT_PRINTF("in INIT *** Error starting TASK_PRC1\n")
617 BOOT_PRINTF("in INIT *** Error starting TASK_PRC1\n")
619 }
618 }
620 }
619 }
621 if (status == RTEMS_SUCCESSFUL) // AVF2
620 if (status == RTEMS_SUCCESSFUL) // AVF2
622 {
621 {
623 status = rtems_task_start( Task_id[TASKID_AVF2], avf2_task, 1 );
622 status = rtems_task_start( Task_id[TASKID_AVF2], avf2_task, 1 );
624 if (status!=RTEMS_SUCCESSFUL) {
623 if (status!=RTEMS_SUCCESSFUL) {
625 BOOT_PRINTF("in INIT *** Error starting TASK_AVF2\n")
624 BOOT_PRINTF("in INIT *** Error starting TASK_AVF2\n")
626 }
625 }
627 }
626 }
628 if (status == RTEMS_SUCCESSFUL) // PRC2
627 if (status == RTEMS_SUCCESSFUL) // PRC2
629 {
628 {
630 status = rtems_task_start( Task_id[TASKID_PRC2], prc2_task, 1 );
629 status = rtems_task_start( Task_id[TASKID_PRC2], prc2_task, 1 );
631 if (status!=RTEMS_SUCCESSFUL) {
630 if (status!=RTEMS_SUCCESSFUL) {
632 BOOT_PRINTF("in INIT *** Error starting TASK_PRC2\n")
631 BOOT_PRINTF("in INIT *** Error starting TASK_PRC2\n")
633 }
632 }
634 }
633 }
635
634
636 //****************
635 //****************
637 // WAVEFORM PICKER
636 // WAVEFORM PICKER
638 if (status == RTEMS_SUCCESSFUL) // WFRM
637 if (status == RTEMS_SUCCESSFUL) // WFRM
639 {
638 {
640 status = rtems_task_start( Task_id[TASKID_WFRM], wfrm_task, 1 );
639 status = rtems_task_start( Task_id[TASKID_WFRM], wfrm_task, 1 );
641 if (status!=RTEMS_SUCCESSFUL) {
640 if (status!=RTEMS_SUCCESSFUL) {
642 BOOT_PRINTF("in INIT *** Error starting TASK_WFRM\n")
641 BOOT_PRINTF("in INIT *** Error starting TASK_WFRM\n")
643 }
642 }
644 }
643 }
645 if (status == RTEMS_SUCCESSFUL) // CWF3
644 if (status == RTEMS_SUCCESSFUL) // CWF3
646 {
645 {
647 status = rtems_task_start( Task_id[TASKID_CWF3], cwf3_task, 1 );
646 status = rtems_task_start( Task_id[TASKID_CWF3], cwf3_task, 1 );
648 if (status!=RTEMS_SUCCESSFUL) {
647 if (status!=RTEMS_SUCCESSFUL) {
649 BOOT_PRINTF("in INIT *** Error starting TASK_CWF3\n")
648 BOOT_PRINTF("in INIT *** Error starting TASK_CWF3\n")
650 }
649 }
651 }
650 }
652 if (status == RTEMS_SUCCESSFUL) // CWF2
651 if (status == RTEMS_SUCCESSFUL) // CWF2
653 {
652 {
654 status = rtems_task_start( Task_id[TASKID_CWF2], cwf2_task, 1 );
653 status = rtems_task_start( Task_id[TASKID_CWF2], cwf2_task, 1 );
655 if (status!=RTEMS_SUCCESSFUL) {
654 if (status!=RTEMS_SUCCESSFUL) {
656 BOOT_PRINTF("in INIT *** Error starting TASK_CWF2\n")
655 BOOT_PRINTF("in INIT *** Error starting TASK_CWF2\n")
657 }
656 }
658 }
657 }
659 if (status == RTEMS_SUCCESSFUL) // CWF1
658 if (status == RTEMS_SUCCESSFUL) // CWF1
660 {
659 {
661 status = rtems_task_start( Task_id[TASKID_CWF1], cwf1_task, 1 );
660 status = rtems_task_start( Task_id[TASKID_CWF1], cwf1_task, 1 );
662 if (status!=RTEMS_SUCCESSFUL) {
661 if (status!=RTEMS_SUCCESSFUL) {
663 BOOT_PRINTF("in INIT *** Error starting TASK_CWF1\n")
662 BOOT_PRINTF("in INIT *** Error starting TASK_CWF1\n")
664 }
663 }
665 }
664 }
666 if (status == RTEMS_SUCCESSFUL) // SWBD
665 if (status == RTEMS_SUCCESSFUL) // SWBD
667 {
666 {
668 status = rtems_task_start( Task_id[TASKID_SWBD], swbd_task, 1 );
667 status = rtems_task_start( Task_id[TASKID_SWBD], swbd_task, 1 );
669 if (status!=RTEMS_SUCCESSFUL) {
668 if (status!=RTEMS_SUCCESSFUL) {
670 BOOT_PRINTF("in INIT *** Error starting TASK_SWBD\n")
669 BOOT_PRINTF("in INIT *** Error starting TASK_SWBD\n")
671 }
670 }
672 }
671 }
673
672
674 //*****
673 //*****
675 // MISC
674 // MISC
676 if (status == RTEMS_SUCCESSFUL) // HOUS
675 if (status == RTEMS_SUCCESSFUL) // HOUS
677 {
676 {
678 status = rtems_task_start( Task_id[TASKID_HOUS], hous_task, 1 );
677 status = rtems_task_start( Task_id[TASKID_HOUS], hous_task, 1 );
679 if (status!=RTEMS_SUCCESSFUL) {
678 if (status!=RTEMS_SUCCESSFUL) {
680 BOOT_PRINTF("in INIT *** Error starting TASK_HOUS\n")
679 BOOT_PRINTF("in INIT *** Error starting TASK_HOUS\n")
681 }
680 }
682 }
681 }
683 if (status == RTEMS_SUCCESSFUL) // DUMB
682 if (status == RTEMS_SUCCESSFUL) // DUMB
684 {
683 {
685 status = rtems_task_start( Task_id[TASKID_DUMB], dumb_task, 1 );
684 status = rtems_task_start( Task_id[TASKID_DUMB], dumb_task, 1 );
686 if (status!=RTEMS_SUCCESSFUL) {
685 if (status!=RTEMS_SUCCESSFUL) {
687 BOOT_PRINTF("in INIT *** Error starting TASK_DUMB\n")
686 BOOT_PRINTF("in INIT *** Error starting TASK_DUMB\n")
688 }
687 }
689 }
688 }
690 if (status == RTEMS_SUCCESSFUL) // LOAD
689 if (status == RTEMS_SUCCESSFUL) // LOAD
691 {
690 {
692 status = rtems_task_start( Task_id[TASKID_LOAD], load_task, 1 );
691 status = rtems_task_start( Task_id[TASKID_LOAD], load_task, 1 );
693 if (status!=RTEMS_SUCCESSFUL) {
692 if (status!=RTEMS_SUCCESSFUL) {
694 BOOT_PRINTF("in INIT *** Error starting TASK_LOAD\n")
693 BOOT_PRINTF("in INIT *** Error starting TASK_LOAD\n")
695 }
694 }
696 }
695 }
697
696
698 return status;
697 return status;
699 }
698 }
700
699
701 rtems_status_code create_message_queues( void ) // create the two message queues used in the software
700 rtems_status_code create_message_queues( void ) // create the two message queues used in the software
702 {
701 {
703 rtems_status_code status_recv;
702 rtems_status_code status_recv;
704 rtems_status_code status_send;
703 rtems_status_code status_send;
705 rtems_status_code status_q_p0;
704 rtems_status_code status_q_p0;
706 rtems_status_code status_q_p1;
705 rtems_status_code status_q_p1;
707 rtems_status_code status_q_p2;
706 rtems_status_code status_q_p2;
708 rtems_status_code ret;
707 rtems_status_code ret;
709 rtems_id queue_id;
708 rtems_id queue_id;
710
709
711 //****************************************
710 //****************************************
712 // create the queue for handling valid TCs
711 // create the queue for handling valid TCs
713 status_recv = rtems_message_queue_create( misc_name[QUEUE_RECV],
712 status_recv = rtems_message_queue_create( misc_name[QUEUE_RECV],
714 MSG_QUEUE_COUNT_RECV, CCSDS_TC_PKT_MAX_SIZE,
713 MSG_QUEUE_COUNT_RECV, CCSDS_TC_PKT_MAX_SIZE,
715 RTEMS_FIFO | RTEMS_LOCAL, &queue_id );
714 RTEMS_FIFO | RTEMS_LOCAL, &queue_id );
716 if ( status_recv != RTEMS_SUCCESSFUL ) {
715 if ( status_recv != RTEMS_SUCCESSFUL ) {
717 PRINTF1("in create_message_queues *** ERR creating QUEU queue, %d\n", status_recv)
716 PRINTF1("in create_message_queues *** ERR creating QUEU queue, %d\n", status_recv)
718 }
717 }
719
718
720 //************************************************
719 //************************************************
721 // create the queue for handling TM packet sending
720 // create the queue for handling TM packet sending
722 status_send = rtems_message_queue_create( misc_name[QUEUE_SEND],
721 status_send = rtems_message_queue_create( misc_name[QUEUE_SEND],
723 MSG_QUEUE_COUNT_SEND, MSG_QUEUE_SIZE_SEND,
722 MSG_QUEUE_COUNT_SEND, MSG_QUEUE_SIZE_SEND,
724 RTEMS_FIFO | RTEMS_LOCAL, &queue_id );
723 RTEMS_FIFO | RTEMS_LOCAL, &queue_id );
725 if ( status_send != RTEMS_SUCCESSFUL ) {
724 if ( status_send != RTEMS_SUCCESSFUL ) {
726 PRINTF1("in create_message_queues *** ERR creating PKTS queue, %d\n", status_send)
725 PRINTF1("in create_message_queues *** ERR creating PKTS queue, %d\n", status_send)
727 }
726 }
728
727
729 //*****************************************************************************
728 //*****************************************************************************
730 // create the queue for handling averaged spectral matrices for processing @ f0
729 // create the queue for handling averaged spectral matrices for processing @ f0
731 status_q_p0 = rtems_message_queue_create( misc_name[QUEUE_PRC0],
730 status_q_p0 = rtems_message_queue_create( misc_name[QUEUE_PRC0],
732 MSG_QUEUE_COUNT_PRC0, MSG_QUEUE_SIZE_PRC0,
731 MSG_QUEUE_COUNT_PRC0, MSG_QUEUE_SIZE_PRC0,
733 RTEMS_FIFO | RTEMS_LOCAL, &queue_id );
732 RTEMS_FIFO | RTEMS_LOCAL, &queue_id );
734 if ( status_q_p0 != RTEMS_SUCCESSFUL ) {
733 if ( status_q_p0 != RTEMS_SUCCESSFUL ) {
735 PRINTF1("in create_message_queues *** ERR creating Q_P0 queue, %d\n", status_q_p0)
734 PRINTF1("in create_message_queues *** ERR creating Q_P0 queue, %d\n", status_q_p0)
736 }
735 }
737
736
738 //*****************************************************************************
737 //*****************************************************************************
739 // create the queue for handling averaged spectral matrices for processing @ f1
738 // create the queue for handling averaged spectral matrices for processing @ f1
740 status_q_p1 = rtems_message_queue_create( misc_name[QUEUE_PRC1],
739 status_q_p1 = rtems_message_queue_create( misc_name[QUEUE_PRC1],
741 MSG_QUEUE_COUNT_PRC1, MSG_QUEUE_SIZE_PRC1,
740 MSG_QUEUE_COUNT_PRC1, MSG_QUEUE_SIZE_PRC1,
742 RTEMS_FIFO | RTEMS_LOCAL, &queue_id );
741 RTEMS_FIFO | RTEMS_LOCAL, &queue_id );
743 if ( status_q_p1 != RTEMS_SUCCESSFUL ) {
742 if ( status_q_p1 != RTEMS_SUCCESSFUL ) {
744 PRINTF1("in create_message_queues *** ERR creating Q_P1 queue, %d\n", status_q_p1)
743 PRINTF1("in create_message_queues *** ERR creating Q_P1 queue, %d\n", status_q_p1)
745 }
744 }
746
745
747 //*****************************************************************************
746 //*****************************************************************************
748 // create the queue for handling averaged spectral matrices for processing @ f2
747 // create the queue for handling averaged spectral matrices for processing @ f2
749 status_q_p2 = rtems_message_queue_create( misc_name[QUEUE_PRC2],
748 status_q_p2 = rtems_message_queue_create( misc_name[QUEUE_PRC2],
750 MSG_QUEUE_COUNT_PRC2, MSG_QUEUE_SIZE_PRC2,
749 MSG_QUEUE_COUNT_PRC2, MSG_QUEUE_SIZE_PRC2,
751 RTEMS_FIFO | RTEMS_LOCAL, &queue_id );
750 RTEMS_FIFO | RTEMS_LOCAL, &queue_id );
752 if ( status_q_p2 != RTEMS_SUCCESSFUL ) {
751 if ( status_q_p2 != RTEMS_SUCCESSFUL ) {
753 PRINTF1("in create_message_queues *** ERR creating Q_P2 queue, %d\n", status_q_p2)
752 PRINTF1("in create_message_queues *** ERR creating Q_P2 queue, %d\n", status_q_p2)
754 }
753 }
755
754
756 if ( status_recv != RTEMS_SUCCESSFUL )
755 if ( status_recv != RTEMS_SUCCESSFUL )
757 {
756 {
758 ret = status_recv;
757 ret = status_recv;
759 }
758 }
760 else if( status_send != RTEMS_SUCCESSFUL )
759 else if( status_send != RTEMS_SUCCESSFUL )
761 {
760 {
762 ret = status_send;
761 ret = status_send;
763 }
762 }
764 else if( status_q_p0 != RTEMS_SUCCESSFUL )
763 else if( status_q_p0 != RTEMS_SUCCESSFUL )
765 {
764 {
766 ret = status_q_p0;
765 ret = status_q_p0;
767 }
766 }
768 else if( status_q_p1 != RTEMS_SUCCESSFUL )
767 else if( status_q_p1 != RTEMS_SUCCESSFUL )
769 {
768 {
770 ret = status_q_p1;
769 ret = status_q_p1;
771 }
770 }
772 else
771 else
773 {
772 {
774 ret = status_q_p2;
773 ret = status_q_p2;
775 }
774 }
776
775
777 return ret;
776 return ret;
778 }
777 }
779
778
780 rtems_status_code create_timecode_timer( void )
779 rtems_status_code create_timecode_timer( void )
781 {
780 {
782 rtems_status_code status;
781 rtems_status_code status;
783
782
784 status = rtems_timer_create( timecode_timer_name, &timecode_timer_id );
783 status = rtems_timer_create( timecode_timer_name, &timecode_timer_id );
785
784
786 if ( status != RTEMS_SUCCESSFUL )
785 if ( status != RTEMS_SUCCESSFUL )
787 {
786 {
788 PRINTF1("in create_timer_timecode *** ERR creating SPTC timer, %d\n", status)
787 PRINTF1("in create_timer_timecode *** ERR creating SPTC timer, %d\n", status)
789 }
788 }
790 else
789 else
791 {
790 {
792 PRINTF("in create_timer_timecode *** OK creating SPTC timer\n")
791 PRINTF("in create_timer_timecode *** OK creating SPTC timer\n")
793 }
792 }
794
793
795 return status;
794 return status;
796 }
795 }
797
796
798 rtems_status_code get_message_queue_id_send( rtems_id *queue_id )
797 rtems_status_code get_message_queue_id_send( rtems_id *queue_id )
799 {
798 {
800 rtems_status_code status;
799 rtems_status_code status;
801 rtems_name queue_name;
800 rtems_name queue_name;
802
801
803 queue_name = rtems_build_name( 'Q', '_', 'S', 'D' );
802 queue_name = rtems_build_name( 'Q', '_', 'S', 'D' );
804
803
805 status = rtems_message_queue_ident( queue_name, 0, queue_id );
804 status = rtems_message_queue_ident( queue_name, 0, queue_id );
806
805
807 return status;
806 return status;
808 }
807 }
809
808
810 rtems_status_code get_message_queue_id_recv( rtems_id *queue_id )
809 rtems_status_code get_message_queue_id_recv( rtems_id *queue_id )
811 {
810 {
812 rtems_status_code status;
811 rtems_status_code status;
813 rtems_name queue_name;
812 rtems_name queue_name;
814
813
815 queue_name = rtems_build_name( 'Q', '_', 'R', 'V' );
814 queue_name = rtems_build_name( 'Q', '_', 'R', 'V' );
816
815
817 status = rtems_message_queue_ident( queue_name, 0, queue_id );
816 status = rtems_message_queue_ident( queue_name, 0, queue_id );
818
817
819 return status;
818 return status;
820 }
819 }
821
820
822 rtems_status_code get_message_queue_id_prc0( rtems_id *queue_id )
821 rtems_status_code get_message_queue_id_prc0( rtems_id *queue_id )
823 {
822 {
824 rtems_status_code status;
823 rtems_status_code status;
825 rtems_name queue_name;
824 rtems_name queue_name;
826
825
827 queue_name = rtems_build_name( 'Q', '_', 'P', '0' );
826 queue_name = rtems_build_name( 'Q', '_', 'P', '0' );
828
827
829 status = rtems_message_queue_ident( queue_name, 0, queue_id );
828 status = rtems_message_queue_ident( queue_name, 0, queue_id );
830
829
831 return status;
830 return status;
832 }
831 }
833
832
834 rtems_status_code get_message_queue_id_prc1( rtems_id *queue_id )
833 rtems_status_code get_message_queue_id_prc1( rtems_id *queue_id )
835 {
834 {
836 rtems_status_code status;
835 rtems_status_code status;
837 rtems_name queue_name;
836 rtems_name queue_name;
838
837
839 queue_name = rtems_build_name( 'Q', '_', 'P', '1' );
838 queue_name = rtems_build_name( 'Q', '_', 'P', '1' );
840
839
841 status = rtems_message_queue_ident( queue_name, 0, queue_id );
840 status = rtems_message_queue_ident( queue_name, 0, queue_id );
842
841
843 return status;
842 return status;
844 }
843 }
845
844
846 rtems_status_code get_message_queue_id_prc2( rtems_id *queue_id )
845 rtems_status_code get_message_queue_id_prc2( rtems_id *queue_id )
847 {
846 {
848 rtems_status_code status;
847 rtems_status_code status;
849 rtems_name queue_name;
848 rtems_name queue_name;
850
849
851 queue_name = rtems_build_name( 'Q', '_', 'P', '2' );
850 queue_name = rtems_build_name( 'Q', '_', 'P', '2' );
852
851
853 status = rtems_message_queue_ident( queue_name, 0, queue_id );
852 status = rtems_message_queue_ident( queue_name, 0, queue_id );
854
853
855 return status;
854 return status;
856 }
855 }
857
856
858 void update_queue_max_count( rtems_id queue_id, unsigned char*fifo_size_max )
857 void update_queue_max_count( rtems_id queue_id, unsigned char*fifo_size_max )
859 {
858 {
860 u_int32_t count;
859 u_int32_t count;
861 rtems_status_code status;
860 rtems_status_code status;
862
861
863 status = rtems_message_queue_get_number_pending( queue_id, &count );
862 status = rtems_message_queue_get_number_pending( queue_id, &count );
864
863
865 count = count + 1;
864 count = count + 1;
866
865
867 if (status != RTEMS_SUCCESSFUL)
866 if (status != RTEMS_SUCCESSFUL)
868 {
867 {
869 PRINTF1("in update_queue_max_count *** ERR = %d\n", status)
868 PRINTF1("in update_queue_max_count *** ERR = %d\n", status)
870 }
869 }
871 else
870 else
872 {
871 {
873 if (count > *fifo_size_max)
872 if (count > *fifo_size_max)
874 {
873 {
875 *fifo_size_max = count;
874 *fifo_size_max = count;
876 }
875 }
877 }
876 }
878 }
877 }
879
878
880 void init_ring(ring_node ring[], unsigned char nbNodes, volatile int buffer[], unsigned int bufferSize )
879 void init_ring(ring_node ring[], unsigned char nbNodes, volatile int buffer[], unsigned int bufferSize )
881 {
880 {
882 unsigned char i;
881 unsigned char i;
883
882
884 //***************
883 //***************
885 // BUFFER ADDRESS
884 // BUFFER ADDRESS
886 for(i=0; i<nbNodes; i++)
885 for(i=0; i<nbNodes; i++)
887 {
886 {
888 ring[i].coarseTime = 0xffffffff;
887 ring[i].coarseTime = 0xffffffff;
889 ring[i].fineTime = 0xffffffff;
888 ring[i].fineTime = 0xffffffff;
890 ring[i].sid = 0x00;
889 ring[i].sid = 0x00;
891 ring[i].status = 0x00;
890 ring[i].status = 0x00;
892 ring[i].buffer_address = (int) &buffer[ i * bufferSize ];
891 ring[i].buffer_address = (int) &buffer[ i * bufferSize ];
893 }
892 }
894
893
895 //*****
894 //*****
896 // NEXT
895 // NEXT
897 ring[ nbNodes - 1 ].next = (ring_node*) &ring[ 0 ];
896 ring[ nbNodes - 1 ].next = (ring_node*) &ring[ 0 ];
898 for(i=0; i<nbNodes-1; i++)
897 for(i=0; i<nbNodes-1; i++)
899 {
898 {
900 ring[i].next = (ring_node*) &ring[ i + 1 ];
899 ring[i].next = (ring_node*) &ring[ i + 1 ];
901 }
900 }
902
901
903 //*********
902 //*********
904 // PREVIOUS
903 // PREVIOUS
905 ring[ 0 ].previous = (ring_node*) &ring[ nbNodes - 1 ];
904 ring[ 0 ].previous = (ring_node*) &ring[ nbNodes - 1 ];
906 for(i=1; i<nbNodes; i++)
905 for(i=1; i<nbNodes; i++)
907 {
906 {
908 ring[i].previous = (ring_node*) &ring[ i - 1 ];
907 ring[i].previous = (ring_node*) &ring[ i - 1 ];
909 }
908 }
910 }
909 }
@@ -1,745 +1,737
1 /** General usage functions and RTEMS tasks.
1 /** General usage functions and RTEMS tasks.
2 *
2 *
3 * @file
3 * @file
4 * @author P. LEROY
4 * @author P. LEROY
5 *
5 *
6 */
6 */
7
7
8 #include "fsw_misc.h"
8 #include "fsw_misc.h"
9
9
10 void timer_configure(unsigned char timer, unsigned int clock_divider,
10 void timer_configure(unsigned char timer, unsigned int clock_divider,
11 unsigned char interrupt_level, rtems_isr (*timer_isr)() )
11 unsigned char interrupt_level, rtems_isr (*timer_isr)() )
12 {
12 {
13 /** This function configures a GPTIMER timer instantiated in the VHDL design.
13 /** This function configures a GPTIMER timer instantiated in the VHDL design.
14 *
14 *
15 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
15 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
16 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
16 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
17 * @param clock_divider is the divider of the 1 MHz clock that will be configured.
17 * @param clock_divider is the divider of the 1 MHz clock that will be configured.
18 * @param interrupt_level is the interrupt level that the timer drives.
18 * @param interrupt_level is the interrupt level that the timer drives.
19 * @param timer_isr is the interrupt subroutine that will be attached to the IRQ driven by the timer.
19 * @param timer_isr is the interrupt subroutine that will be attached to the IRQ driven by the timer.
20 *
20 *
21 * Interrupt levels are described in the SPARC documentation sparcv8.pdf p.76
21 * Interrupt levels are described in the SPARC documentation sparcv8.pdf p.76
22 *
22 *
23 */
23 */
24
24
25 rtems_status_code status;
25 rtems_status_code status;
26 rtems_isr_entry old_isr_handler;
26 rtems_isr_entry old_isr_handler;
27
27
28 gptimer_regs->timer[timer].ctrl = 0x00; // reset the control register
28 gptimer_regs->timer[timer].ctrl = 0x00; // reset the control register
29
29
30 status = rtems_interrupt_catch( timer_isr, interrupt_level, &old_isr_handler) ; // see sparcv8.pdf p.76 for interrupt levels
30 status = rtems_interrupt_catch( timer_isr, interrupt_level, &old_isr_handler) ; // see sparcv8.pdf p.76 for interrupt levels
31 if (status!=RTEMS_SUCCESSFUL)
31 if (status!=RTEMS_SUCCESSFUL)
32 {
32 {
33 PRINTF("in configure_timer *** ERR rtems_interrupt_catch\n")
33 PRINTF("in configure_timer *** ERR rtems_interrupt_catch\n")
34 }
34 }
35
35
36 timer_set_clock_divider( timer, clock_divider);
36 timer_set_clock_divider( timer, clock_divider);
37 }
37 }
38
38
39 void timer_start(unsigned char timer)
39 void timer_start(unsigned char timer)
40 {
40 {
41 /** This function starts a GPTIMER timer.
41 /** This function starts a GPTIMER timer.
42 *
42 *
43 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
43 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
44 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
44 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
45 *
45 *
46 */
46 */
47
47
48 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000010; // clear pending IRQ if any
48 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000010; // clear pending IRQ if any
49 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000004; // LD load value from the reload register
49 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000004; // LD load value from the reload register
50 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000001; // EN enable the timer
50 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000001; // EN enable the timer
51 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000002; // RS restart
51 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000002; // RS restart
52 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000008; // IE interrupt enable
52 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000008; // IE interrupt enable
53 }
53 }
54
54
55 void timer_stop(unsigned char timer)
55 void timer_stop(unsigned char timer)
56 {
56 {
57 /** This function stops a GPTIMER timer.
57 /** This function stops a GPTIMER timer.
58 *
58 *
59 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
59 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
60 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
60 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
61 *
61 *
62 */
62 */
63
63
64 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl & 0xfffffffe; // EN enable the timer
64 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl & 0xfffffffe; // EN enable the timer
65 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl & 0xffffffef; // IE interrupt enable
65 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl & 0xffffffef; // IE interrupt enable
66 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000010; // clear pending IRQ if any
66 gptimer_regs->timer[timer].ctrl = gptimer_regs->timer[timer].ctrl | 0x00000010; // clear pending IRQ if any
67 }
67 }
68
68
69 void timer_set_clock_divider(unsigned char timer, unsigned int clock_divider)
69 void timer_set_clock_divider(unsigned char timer, unsigned int clock_divider)
70 {
70 {
71 /** This function sets the clock divider of a GPTIMER timer.
71 /** This function sets the clock divider of a GPTIMER timer.
72 *
72 *
73 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
73 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
74 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
74 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
75 * @param clock_divider is the divider of the 1 MHz clock that will be configured.
75 * @param clock_divider is the divider of the 1 MHz clock that will be configured.
76 *
76 *
77 */
77 */
78
78
79 gptimer_regs->timer[timer].reload = clock_divider; // base clock frequency is 1 MHz
79 gptimer_regs->timer[timer].reload = clock_divider; // base clock frequency is 1 MHz
80 }
80 }
81
81
82 // WATCHDOG
82 // WATCHDOG
83
83
84 rtems_isr watchdog_isr( rtems_vector_number vector )
84 rtems_isr watchdog_isr( rtems_vector_number vector )
85 {
85 {
86 rtems_status_code status_code;
86 rtems_status_code status_code;
87
87
88 status_code = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_12 );
88 status_code = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_12 );
89 }
89 }
90
90
91 void watchdog_configure(void)
91 void watchdog_configure(void)
92 {
92 {
93 /** This function configure the watchdog.
93 /** This function configure the watchdog.
94 *
94 *
95 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
95 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
96 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
96 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
97 *
97 *
98 * The watchdog is a timer provided by the GPTIMER IP core of the GRLIB.
98 * The watchdog is a timer provided by the GPTIMER IP core of the GRLIB.
99 *
99 *
100 */
100 */
101
101
102 LEON_Mask_interrupt( IRQ_GPTIMER_WATCHDOG ); // mask gptimer/watchdog interrupt during configuration
102 LEON_Mask_interrupt( IRQ_GPTIMER_WATCHDOG ); // mask gptimer/watchdog interrupt during configuration
103
103
104 timer_configure( TIMER_WATCHDOG, CLKDIV_WATCHDOG, IRQ_SPARC_GPTIMER_WATCHDOG, watchdog_isr );
104 timer_configure( TIMER_WATCHDOG, CLKDIV_WATCHDOG, IRQ_SPARC_GPTIMER_WATCHDOG, watchdog_isr );
105
105
106 LEON_Clear_interrupt( IRQ_GPTIMER_WATCHDOG ); // clear gptimer/watchdog interrupt
106 LEON_Clear_interrupt( IRQ_GPTIMER_WATCHDOG ); // clear gptimer/watchdog interrupt
107 }
107 }
108
108
109 void watchdog_stop(void)
109 void watchdog_stop(void)
110 {
110 {
111 LEON_Mask_interrupt( IRQ_GPTIMER_WATCHDOG ); // mask gptimer/watchdog interrupt line
111 LEON_Mask_interrupt( IRQ_GPTIMER_WATCHDOG ); // mask gptimer/watchdog interrupt line
112 timer_stop( TIMER_WATCHDOG );
112 timer_stop( TIMER_WATCHDOG );
113 LEON_Clear_interrupt( IRQ_GPTIMER_WATCHDOG ); // clear gptimer/watchdog interrupt
113 LEON_Clear_interrupt( IRQ_GPTIMER_WATCHDOG ); // clear gptimer/watchdog interrupt
114 }
114 }
115
115
116 void watchdog_reload(void)
116 void watchdog_reload(void)
117 {
117 {
118 /** This function reloads the watchdog timer counter with the timer reload value.
118 /** This function reloads the watchdog timer counter with the timer reload value.
119 *
119 *
120 * @param void
120 * @param void
121 *
121 *
122 * @return void
122 * @return void
123 *
123 *
124 */
124 */
125
125
126 gptimer_regs->timer[TIMER_WATCHDOG].ctrl = gptimer_regs->timer[TIMER_WATCHDOG].ctrl | 0x00000004; // LD load value from the reload register
126 gptimer_regs->timer[TIMER_WATCHDOG].ctrl = gptimer_regs->timer[TIMER_WATCHDOG].ctrl | 0x00000004; // LD load value from the reload register
127 }
127 }
128
128
129 void watchdog_start(void)
129 void watchdog_start(void)
130 {
130 {
131 /** This function starts the watchdog timer.
131 /** This function starts the watchdog timer.
132 *
132 *
133 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
133 * @param gptimer_regs points to the APB registers of the GPTIMER IP core.
134 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
134 * @param timer is the number of the timer in the IP core (several timers can be instantiated).
135 *
135 *
136 */
136 */
137
137
138 LEON_Clear_interrupt( IRQ_GPTIMER_WATCHDOG );
138 LEON_Clear_interrupt( IRQ_GPTIMER_WATCHDOG );
139
139
140 gptimer_regs->timer[TIMER_WATCHDOG].ctrl = gptimer_regs->timer[TIMER_WATCHDOG].ctrl | 0x00000010; // clear pending IRQ if any
140 gptimer_regs->timer[TIMER_WATCHDOG].ctrl = gptimer_regs->timer[TIMER_WATCHDOG].ctrl | 0x00000010; // clear pending IRQ if any
141 gptimer_regs->timer[TIMER_WATCHDOG].ctrl = gptimer_regs->timer[TIMER_WATCHDOG].ctrl | 0x00000004; // LD load value from the reload register
141 gptimer_regs->timer[TIMER_WATCHDOG].ctrl = gptimer_regs->timer[TIMER_WATCHDOG].ctrl | 0x00000004; // LD load value from the reload register
142 gptimer_regs->timer[TIMER_WATCHDOG].ctrl = gptimer_regs->timer[TIMER_WATCHDOG].ctrl | 0x00000001; // EN enable the timer
142 gptimer_regs->timer[TIMER_WATCHDOG].ctrl = gptimer_regs->timer[TIMER_WATCHDOG].ctrl | 0x00000001; // EN enable the timer
143 gptimer_regs->timer[TIMER_WATCHDOG].ctrl = gptimer_regs->timer[TIMER_WATCHDOG].ctrl | 0x00000008; // IE interrupt enable
143 gptimer_regs->timer[TIMER_WATCHDOG].ctrl = gptimer_regs->timer[TIMER_WATCHDOG].ctrl | 0x00000008; // IE interrupt enable
144
144
145 LEON_Unmask_interrupt( IRQ_GPTIMER_WATCHDOG );
145 LEON_Unmask_interrupt( IRQ_GPTIMER_WATCHDOG );
146
146
147 }
147 }
148
148
149 int send_console_outputs_on_apbuart_port( void ) // Send the console outputs on the apbuart port
149 int enable_apbuart_transmitter( void ) // set the bit 1, TE Transmitter Enable to 1 in the APBUART control register
150 {
150 {
151 struct apbuart_regs_str *apbuart_regs = (struct apbuart_regs_str *) REGS_ADDR_APBUART;
151 struct apbuart_regs_str *apbuart_regs = (struct apbuart_regs_str *) REGS_ADDR_APBUART;
152
152
153 apbuart_regs->ctrl = APBUART_CTRL_REG_MASK_TE;
153 apbuart_regs->ctrl = APBUART_CTRL_REG_MASK_TE;
154
154
155 return 0;
155 return 0;
156 }
156 }
157
157
158 int enable_apbuart_transmitter( void ) // set the bit 1, TE Transmitter Enable to 1 in the APBUART control register
159 {
160 struct apbuart_regs_str *apbuart_regs = (struct apbuart_regs_str *) REGS_ADDR_APBUART;
161
162 apbuart_regs->ctrl = apbuart_regs->ctrl | APBUART_CTRL_REG_MASK_TE;
163
164 return 0;
165 }
166
167 void set_apbuart_scaler_reload_register(unsigned int regs, unsigned int value)
158 void set_apbuart_scaler_reload_register(unsigned int regs, unsigned int value)
168 {
159 {
169 /** This function sets the scaler reload register of the apbuart module
160 /** This function sets the scaler reload register of the apbuart module
170 *
161 *
171 * @param regs is the address of the apbuart registers in memory
162 * @param regs is the address of the apbuart registers in memory
172 * @param value is the value that will be stored in the scaler register
163 * @param value is the value that will be stored in the scaler register
173 *
164 *
174 * The value shall be set by the software to get data on the serial interface.
165 * The value shall be set by the software to get data on the serial interface.
175 *
166 *
176 */
167 */
177
168
178 struct apbuart_regs_str *apbuart_regs = (struct apbuart_regs_str *) regs;
169 struct apbuart_regs_str *apbuart_regs = (struct apbuart_regs_str *) regs;
179
170
180 apbuart_regs->scaler = value;
171 apbuart_regs->scaler = value;
172
181 BOOT_PRINTF1("OK *** apbuart port scaler reload register set to 0x%x\n", value)
173 BOOT_PRINTF1("OK *** apbuart port scaler reload register set to 0x%x\n", value)
182 }
174 }
183
175
184 //************
176 //************
185 // RTEMS TASKS
177 // RTEMS TASKS
186
178
187 rtems_task load_task(rtems_task_argument argument)
179 rtems_task load_task(rtems_task_argument argument)
188 {
180 {
189 BOOT_PRINTF("in LOAD *** \n")
181 BOOT_PRINTF("in LOAD *** \n")
190
182
191 rtems_status_code status;
183 rtems_status_code status;
192 unsigned int i;
184 unsigned int i;
193 unsigned int j;
185 unsigned int j;
194 rtems_name name_watchdog_rate_monotonic; // name of the watchdog rate monotonic
186 rtems_name name_watchdog_rate_monotonic; // name of the watchdog rate monotonic
195 rtems_id watchdog_period_id; // id of the watchdog rate monotonic period
187 rtems_id watchdog_period_id; // id of the watchdog rate monotonic period
196
188
197 name_watchdog_rate_monotonic = rtems_build_name( 'L', 'O', 'A', 'D' );
189 name_watchdog_rate_monotonic = rtems_build_name( 'L', 'O', 'A', 'D' );
198
190
199 status = rtems_rate_monotonic_create( name_watchdog_rate_monotonic, &watchdog_period_id );
191 status = rtems_rate_monotonic_create( name_watchdog_rate_monotonic, &watchdog_period_id );
200 if( status != RTEMS_SUCCESSFUL ) {
192 if( status != RTEMS_SUCCESSFUL ) {
201 PRINTF1( "in LOAD *** rtems_rate_monotonic_create failed with status of %d\n", status )
193 PRINTF1( "in LOAD *** rtems_rate_monotonic_create failed with status of %d\n", status )
202 }
194 }
203
195
204 i = 0;
196 i = 0;
205 j = 0;
197 j = 0;
206
198
207 watchdog_configure();
199 watchdog_configure();
208
200
209 watchdog_start();
201 watchdog_start();
210
202
211 while(1){
203 while(1){
212 status = rtems_rate_monotonic_period( watchdog_period_id, WATCHDOG_PERIOD );
204 status = rtems_rate_monotonic_period( watchdog_period_id, WATCHDOG_PERIOD );
213 watchdog_reload();
205 watchdog_reload();
214 i = i + 1;
206 i = i + 1;
215 if ( i == 10 )
207 if ( i == 10 )
216 {
208 {
217 i = 0;
209 i = 0;
218 j = j + 1;
210 j = j + 1;
219 PRINTF1("%d\n", j)
211 PRINTF1("%d\n", j)
220 }
212 }
221 #ifdef DEBUG_WATCHDOG
213 #ifdef DEBUG_WATCHDOG
222 if (j == 3 )
214 if (j == 3 )
223 {
215 {
224 status = rtems_task_delete(RTEMS_SELF);
216 status = rtems_task_delete(RTEMS_SELF);
225 }
217 }
226 #endif
218 #endif
227 }
219 }
228 }
220 }
229
221
230 rtems_task hous_task(rtems_task_argument argument)
222 rtems_task hous_task(rtems_task_argument argument)
231 {
223 {
232 rtems_status_code status;
224 rtems_status_code status;
233 rtems_status_code spare_status;
225 rtems_status_code spare_status;
234 rtems_id queue_id;
226 rtems_id queue_id;
235 rtems_rate_monotonic_period_status period_status;
227 rtems_rate_monotonic_period_status period_status;
236
228
237 status = get_message_queue_id_send( &queue_id );
229 status = get_message_queue_id_send( &queue_id );
238 if (status != RTEMS_SUCCESSFUL)
230 if (status != RTEMS_SUCCESSFUL)
239 {
231 {
240 PRINTF1("in HOUS *** ERR get_message_queue_id_send %d\n", status)
232 PRINTF1("in HOUS *** ERR get_message_queue_id_send %d\n", status)
241 }
233 }
242
234
243 BOOT_PRINTF("in HOUS ***\n")
235 BOOT_PRINTF("in HOUS ***\n")
244
236
245 if (rtems_rate_monotonic_ident( name_hk_rate_monotonic, &HK_id) != RTEMS_SUCCESSFUL) {
237 if (rtems_rate_monotonic_ident( name_hk_rate_monotonic, &HK_id) != RTEMS_SUCCESSFUL) {
246 status = rtems_rate_monotonic_create( name_hk_rate_monotonic, &HK_id );
238 status = rtems_rate_monotonic_create( name_hk_rate_monotonic, &HK_id );
247 if( status != RTEMS_SUCCESSFUL ) {
239 if( status != RTEMS_SUCCESSFUL ) {
248 PRINTF1( "rtems_rate_monotonic_create failed with status of %d\n", status )
240 PRINTF1( "rtems_rate_monotonic_create failed with status of %d\n", status )
249 }
241 }
250 }
242 }
251
243
252 status = rtems_rate_monotonic_cancel(HK_id);
244 status = rtems_rate_monotonic_cancel(HK_id);
253 if( status != RTEMS_SUCCESSFUL ) {
245 if( status != RTEMS_SUCCESSFUL ) {
254 PRINTF1( "ERR *** in HOUS *** rtems_rate_monotonic_cancel(HK_id) ***code: %d\n", status )
246 PRINTF1( "ERR *** in HOUS *** rtems_rate_monotonic_cancel(HK_id) ***code: %d\n", status )
255 }
247 }
256 else {
248 else {
257 DEBUG_PRINTF("OK *** in HOUS *** rtems_rate_monotonic_cancel(HK_id)\n")
249 DEBUG_PRINTF("OK *** in HOUS *** rtems_rate_monotonic_cancel(HK_id)\n")
258 }
250 }
259
251
260 // startup phase
252 // startup phase
261 status = rtems_rate_monotonic_period( HK_id, SY_LFR_TIME_SYN_TIMEOUT_in_ticks );
253 status = rtems_rate_monotonic_period( HK_id, SY_LFR_TIME_SYN_TIMEOUT_in_ticks );
262 status = rtems_rate_monotonic_get_status( HK_id, &period_status );
254 status = rtems_rate_monotonic_get_status( HK_id, &period_status );
263 DEBUG_PRINTF1("startup HK, HK_id status = %d\n", period_status.state)
255 DEBUG_PRINTF1("startup HK, HK_id status = %d\n", period_status.state)
264 while(period_status.state != RATE_MONOTONIC_EXPIRED ) // after SY_LFR_TIME_SYN_TIMEOUT ms, starts HK anyway
256 while(period_status.state != RATE_MONOTONIC_EXPIRED ) // after SY_LFR_TIME_SYN_TIMEOUT ms, starts HK anyway
265 {
257 {
266 if ((time_management_regs->coarse_time & 0x80000000) == 0x00000000) // check time synchronization
258 if ((time_management_regs->coarse_time & 0x80000000) == 0x00000000) // check time synchronization
267 {
259 {
268 break; // break if LFR is synchronized
260 break; // break if LFR is synchronized
269 }
261 }
270 else
262 else
271 {
263 {
272 status = rtems_rate_monotonic_get_status( HK_id, &period_status );
264 status = rtems_rate_monotonic_get_status( HK_id, &period_status );
273 // sched_yield();
265 // sched_yield();
274 status = rtems_task_wake_after( 10 ); // wait SY_LFR_DPU_CONNECT_TIMEOUT 100 ms = 10 * 10 ms
266 status = rtems_task_wake_after( 10 ); // wait SY_LFR_DPU_CONNECT_TIMEOUT 100 ms = 10 * 10 ms
275 }
267 }
276 }
268 }
277 status = rtems_rate_monotonic_cancel(HK_id);
269 status = rtems_rate_monotonic_cancel(HK_id);
278 DEBUG_PRINTF1("startup HK, HK_id status = %d\n", period_status.state)
270 DEBUG_PRINTF1("startup HK, HK_id status = %d\n", period_status.state)
279
271
280 set_hk_lfr_reset_cause( POWER_ON );
272 set_hk_lfr_reset_cause( POWER_ON );
281
273
282 while(1){ // launch the rate monotonic task
274 while(1){ // launch the rate monotonic task
283 status = rtems_rate_monotonic_period( HK_id, HK_PERIOD );
275 status = rtems_rate_monotonic_period( HK_id, HK_PERIOD );
284 if ( status != RTEMS_SUCCESSFUL ) {
276 if ( status != RTEMS_SUCCESSFUL ) {
285 PRINTF1( "in HOUS *** ERR period: %d\n", status);
277 PRINTF1( "in HOUS *** ERR period: %d\n", status);
286 spare_status = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_6 );
278 spare_status = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_6 );
287 }
279 }
288 else {
280 else {
289 housekeeping_packet.packetSequenceControl[0] = (unsigned char) (sequenceCounterHK >> 8);
281 housekeeping_packet.packetSequenceControl[0] = (unsigned char) (sequenceCounterHK >> 8);
290 housekeeping_packet.packetSequenceControl[1] = (unsigned char) (sequenceCounterHK );
282 housekeeping_packet.packetSequenceControl[1] = (unsigned char) (sequenceCounterHK );
291 increment_seq_counter( &sequenceCounterHK );
283 increment_seq_counter( &sequenceCounterHK );
292
284
293 housekeeping_packet.time[0] = (unsigned char) (time_management_regs->coarse_time>>24);
285 housekeeping_packet.time[0] = (unsigned char) (time_management_regs->coarse_time>>24);
294 housekeeping_packet.time[1] = (unsigned char) (time_management_regs->coarse_time>>16);
286 housekeeping_packet.time[1] = (unsigned char) (time_management_regs->coarse_time>>16);
295 housekeeping_packet.time[2] = (unsigned char) (time_management_regs->coarse_time>>8);
287 housekeeping_packet.time[2] = (unsigned char) (time_management_regs->coarse_time>>8);
296 housekeeping_packet.time[3] = (unsigned char) (time_management_regs->coarse_time);
288 housekeeping_packet.time[3] = (unsigned char) (time_management_regs->coarse_time);
297 housekeeping_packet.time[4] = (unsigned char) (time_management_regs->fine_time>>8);
289 housekeeping_packet.time[4] = (unsigned char) (time_management_regs->fine_time>>8);
298 housekeeping_packet.time[5] = (unsigned char) (time_management_regs->fine_time);
290 housekeeping_packet.time[5] = (unsigned char) (time_management_regs->fine_time);
299
291
300 spacewire_update_statistics();
292 spacewire_update_statistics();
301
293
302 hk_lfr_le_me_he_update();
294 hk_lfr_le_me_he_update();
303
295
304 set_hk_lfr_time_not_synchro();
296 set_hk_lfr_time_not_synchro();
305
297
306 housekeeping_packet.hk_lfr_q_sd_fifo_size_max = hk_lfr_q_sd_fifo_size_max;
298 housekeeping_packet.hk_lfr_q_sd_fifo_size_max = hk_lfr_q_sd_fifo_size_max;
307 housekeeping_packet.hk_lfr_q_rv_fifo_size_max = hk_lfr_q_rv_fifo_size_max;
299 housekeeping_packet.hk_lfr_q_rv_fifo_size_max = hk_lfr_q_rv_fifo_size_max;
308 housekeeping_packet.hk_lfr_q_p0_fifo_size_max = hk_lfr_q_p0_fifo_size_max;
300 housekeeping_packet.hk_lfr_q_p0_fifo_size_max = hk_lfr_q_p0_fifo_size_max;
309 housekeeping_packet.hk_lfr_q_p1_fifo_size_max = hk_lfr_q_p1_fifo_size_max;
301 housekeeping_packet.hk_lfr_q_p1_fifo_size_max = hk_lfr_q_p1_fifo_size_max;
310 housekeeping_packet.hk_lfr_q_p2_fifo_size_max = hk_lfr_q_p2_fifo_size_max;
302 housekeeping_packet.hk_lfr_q_p2_fifo_size_max = hk_lfr_q_p2_fifo_size_max;
311
303
312 housekeeping_packet.sy_lfr_common_parameters_spare = parameter_dump_packet.sy_lfr_common_parameters_spare;
304 housekeeping_packet.sy_lfr_common_parameters_spare = parameter_dump_packet.sy_lfr_common_parameters_spare;
313 housekeeping_packet.sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
305 housekeeping_packet.sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
314 get_temperatures( housekeeping_packet.hk_lfr_temp_scm );
306 get_temperatures( housekeeping_packet.hk_lfr_temp_scm );
315 get_v_e1_e2_f3( housekeeping_packet.hk_lfr_sc_v_f3 );
307 get_v_e1_e2_f3( housekeeping_packet.hk_lfr_sc_v_f3 );
316 get_cpu_load( (unsigned char *) &housekeeping_packet.hk_lfr_cpu_load );
308 get_cpu_load( (unsigned char *) &housekeeping_packet.hk_lfr_cpu_load );
317
309
318 // SEND PACKET
310 // SEND PACKET
319 status = rtems_message_queue_send( queue_id, &housekeeping_packet,
311 status = rtems_message_queue_send( queue_id, &housekeeping_packet,
320 PACKET_LENGTH_HK + CCSDS_TC_TM_PACKET_OFFSET + CCSDS_PROTOCOLE_EXTRA_BYTES);
312 PACKET_LENGTH_HK + CCSDS_TC_TM_PACKET_OFFSET + CCSDS_PROTOCOLE_EXTRA_BYTES);
321 if (status != RTEMS_SUCCESSFUL) {
313 if (status != RTEMS_SUCCESSFUL) {
322 PRINTF1("in HOUS *** ERR send: %d\n", status)
314 PRINTF1("in HOUS *** ERR send: %d\n", status)
323 }
315 }
324 }
316 }
325 }
317 }
326
318
327 PRINTF("in HOUS *** deleting task\n")
319 PRINTF("in HOUS *** deleting task\n")
328
320
329 status = rtems_task_delete( RTEMS_SELF ); // should not return
321 status = rtems_task_delete( RTEMS_SELF ); // should not return
330
322
331 return;
323 return;
332 }
324 }
333
325
334 rtems_task dumb_task( rtems_task_argument unused )
326 rtems_task dumb_task( rtems_task_argument unused )
335 {
327 {
336 /** This RTEMS taks is used to print messages without affecting the general behaviour of the software.
328 /** This RTEMS taks is used to print messages without affecting the general behaviour of the software.
337 *
329 *
338 * @param unused is the starting argument of the RTEMS task
330 * @param unused is the starting argument of the RTEMS task
339 *
331 *
340 * The DUMB taks waits for RTEMS events and print messages depending on the incoming events.
332 * The DUMB taks waits for RTEMS events and print messages depending on the incoming events.
341 *
333 *
342 */
334 */
343
335
344 unsigned int i;
336 unsigned int i;
345 unsigned int intEventOut;
337 unsigned int intEventOut;
346 unsigned int coarse_time = 0;
338 unsigned int coarse_time = 0;
347 unsigned int fine_time = 0;
339 unsigned int fine_time = 0;
348 rtems_event_set event_out;
340 rtems_event_set event_out;
349
341
350 char *DumbMessages[14] = {"in DUMB *** default", // RTEMS_EVENT_0
342 char *DumbMessages[14] = {"in DUMB *** default", // RTEMS_EVENT_0
351 "in DUMB *** timecode_irq_handler", // RTEMS_EVENT_1
343 "in DUMB *** timecode_irq_handler", // RTEMS_EVENT_1
352 "in DUMB *** f3 buffer changed", // RTEMS_EVENT_2
344 "in DUMB *** f3 buffer changed", // RTEMS_EVENT_2
353 "in DUMB *** in SMIQ *** Error sending event to AVF0", // RTEMS_EVENT_3
345 "in DUMB *** in SMIQ *** Error sending event to AVF0", // RTEMS_EVENT_3
354 "in DUMB *** spectral_matrices_isr *** Error sending event to SMIQ", // RTEMS_EVENT_4
346 "in DUMB *** spectral_matrices_isr *** Error sending event to SMIQ", // RTEMS_EVENT_4
355 "in DUMB *** waveforms_simulator_isr", // RTEMS_EVENT_5
347 "in DUMB *** waveforms_simulator_isr", // RTEMS_EVENT_5
356 "VHDL SM *** two buffers f0 ready", // RTEMS_EVENT_6
348 "VHDL SM *** two buffers f0 ready", // RTEMS_EVENT_6
357 "ready for dump", // RTEMS_EVENT_7
349 "ready for dump", // RTEMS_EVENT_7
358 "VHDL ERR *** spectral matrix", // RTEMS_EVENT_8
350 "VHDL ERR *** spectral matrix", // RTEMS_EVENT_8
359 "tick", // RTEMS_EVENT_9
351 "tick", // RTEMS_EVENT_9
360 "VHDL ERR *** waveform picker", // RTEMS_EVENT_10
352 "VHDL ERR *** waveform picker", // RTEMS_EVENT_10
361 "VHDL ERR *** unexpected ready matrix values", // RTEMS_EVENT_11
353 "VHDL ERR *** unexpected ready matrix values", // RTEMS_EVENT_11
362 "WATCHDOG timer", // RTEMS_EVENT_12
354 "WATCHDOG timer", // RTEMS_EVENT_12
363 "TIMECODE timer" // RTEMS_EVENT_13
355 "TIMECODE timer" // RTEMS_EVENT_13
364 };
356 };
365
357
366 BOOT_PRINTF("in DUMB *** \n")
358 BOOT_PRINTF("in DUMB *** \n")
367
359
368 while(1){
360 while(1){
369 rtems_event_receive(RTEMS_EVENT_0 | RTEMS_EVENT_1 | RTEMS_EVENT_2 | RTEMS_EVENT_3
361 rtems_event_receive(RTEMS_EVENT_0 | RTEMS_EVENT_1 | RTEMS_EVENT_2 | RTEMS_EVENT_3
370 | RTEMS_EVENT_4 | RTEMS_EVENT_5 | RTEMS_EVENT_6 | RTEMS_EVENT_7
362 | RTEMS_EVENT_4 | RTEMS_EVENT_5 | RTEMS_EVENT_6 | RTEMS_EVENT_7
371 | RTEMS_EVENT_8 | RTEMS_EVENT_9 | RTEMS_EVENT_12 | RTEMS_EVENT_13,
363 | RTEMS_EVENT_8 | RTEMS_EVENT_9 | RTEMS_EVENT_12 | RTEMS_EVENT_13,
372 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out); // wait for an RTEMS_EVENT
364 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out); // wait for an RTEMS_EVENT
373 intEventOut = (unsigned int) event_out;
365 intEventOut = (unsigned int) event_out;
374 for ( i=0; i<32; i++)
366 for ( i=0; i<32; i++)
375 {
367 {
376 if ( ((intEventOut >> i) & 0x0001) != 0)
368 if ( ((intEventOut >> i) & 0x0001) != 0)
377 {
369 {
378 coarse_time = time_management_regs->coarse_time;
370 coarse_time = time_management_regs->coarse_time;
379 fine_time = time_management_regs->fine_time;
371 fine_time = time_management_regs->fine_time;
380 if (i==12)
372 if (i==12)
381 {
373 {
382 PRINTF1("%s\n", DumbMessages[12])
374 PRINTF1("%s\n", DumbMessages[12])
383 }
375 }
384 if (i==13)
376 if (i==13)
385 {
377 {
386 PRINTF1("%s\n", DumbMessages[13])
378 PRINTF1("%s\n", DumbMessages[13])
387 }
379 }
388 }
380 }
389 }
381 }
390 }
382 }
391 }
383 }
392
384
393 //*****************************
385 //*****************************
394 // init housekeeping parameters
386 // init housekeeping parameters
395
387
396 void init_housekeeping_parameters( void )
388 void init_housekeeping_parameters( void )
397 {
389 {
398 /** This function initialize the housekeeping_packet global variable with default values.
390 /** This function initialize the housekeeping_packet global variable with default values.
399 *
391 *
400 */
392 */
401
393
402 unsigned int i = 0;
394 unsigned int i = 0;
403 unsigned char *parameters;
395 unsigned char *parameters;
404 unsigned char sizeOfHK;
396 unsigned char sizeOfHK;
405
397
406 sizeOfHK = sizeof( Packet_TM_LFR_HK_t );
398 sizeOfHK = sizeof( Packet_TM_LFR_HK_t );
407
399
408 parameters = (unsigned char*) &housekeeping_packet;
400 parameters = (unsigned char*) &housekeeping_packet;
409
401
410 for(i = 0; i< sizeOfHK; i++)
402 for(i = 0; i< sizeOfHK; i++)
411 {
403 {
412 parameters[i] = 0x00;
404 parameters[i] = 0x00;
413 }
405 }
414
406
415 housekeeping_packet.targetLogicalAddress = CCSDS_DESTINATION_ID;
407 housekeeping_packet.targetLogicalAddress = CCSDS_DESTINATION_ID;
416 housekeeping_packet.protocolIdentifier = CCSDS_PROTOCOLE_ID;
408 housekeeping_packet.protocolIdentifier = CCSDS_PROTOCOLE_ID;
417 housekeeping_packet.reserved = DEFAULT_RESERVED;
409 housekeeping_packet.reserved = DEFAULT_RESERVED;
418 housekeeping_packet.userApplication = CCSDS_USER_APP;
410 housekeeping_packet.userApplication = CCSDS_USER_APP;
419 housekeeping_packet.packetID[0] = (unsigned char) (APID_TM_HK >> 8);
411 housekeeping_packet.packetID[0] = (unsigned char) (APID_TM_HK >> 8);
420 housekeeping_packet.packetID[1] = (unsigned char) (APID_TM_HK);
412 housekeeping_packet.packetID[1] = (unsigned char) (APID_TM_HK);
421 housekeeping_packet.packetSequenceControl[0] = TM_PACKET_SEQ_CTRL_STANDALONE;
413 housekeeping_packet.packetSequenceControl[0] = TM_PACKET_SEQ_CTRL_STANDALONE;
422 housekeeping_packet.packetSequenceControl[1] = TM_PACKET_SEQ_CNT_DEFAULT;
414 housekeeping_packet.packetSequenceControl[1] = TM_PACKET_SEQ_CNT_DEFAULT;
423 housekeeping_packet.packetLength[0] = (unsigned char) (PACKET_LENGTH_HK >> 8);
415 housekeeping_packet.packetLength[0] = (unsigned char) (PACKET_LENGTH_HK >> 8);
424 housekeeping_packet.packetLength[1] = (unsigned char) (PACKET_LENGTH_HK );
416 housekeeping_packet.packetLength[1] = (unsigned char) (PACKET_LENGTH_HK );
425 housekeeping_packet.spare1_pusVersion_spare2 = DEFAULT_SPARE1_PUSVERSION_SPARE2;
417 housekeeping_packet.spare1_pusVersion_spare2 = DEFAULT_SPARE1_PUSVERSION_SPARE2;
426 housekeeping_packet.serviceType = TM_TYPE_HK;
418 housekeeping_packet.serviceType = TM_TYPE_HK;
427 housekeeping_packet.serviceSubType = TM_SUBTYPE_HK;
419 housekeeping_packet.serviceSubType = TM_SUBTYPE_HK;
428 housekeeping_packet.destinationID = TM_DESTINATION_ID_GROUND;
420 housekeeping_packet.destinationID = TM_DESTINATION_ID_GROUND;
429 housekeeping_packet.sid = SID_HK;
421 housekeeping_packet.sid = SID_HK;
430
422
431 // init status word
423 // init status word
432 housekeeping_packet.lfr_status_word[0] = DEFAULT_STATUS_WORD_BYTE0;
424 housekeeping_packet.lfr_status_word[0] = DEFAULT_STATUS_WORD_BYTE0;
433 housekeeping_packet.lfr_status_word[1] = DEFAULT_STATUS_WORD_BYTE1;
425 housekeeping_packet.lfr_status_word[1] = DEFAULT_STATUS_WORD_BYTE1;
434 // init software version
426 // init software version
435 housekeeping_packet.lfr_sw_version[0] = SW_VERSION_N1;
427 housekeeping_packet.lfr_sw_version[0] = SW_VERSION_N1;
436 housekeeping_packet.lfr_sw_version[1] = SW_VERSION_N2;
428 housekeeping_packet.lfr_sw_version[1] = SW_VERSION_N2;
437 housekeeping_packet.lfr_sw_version[2] = SW_VERSION_N3;
429 housekeeping_packet.lfr_sw_version[2] = SW_VERSION_N3;
438 housekeeping_packet.lfr_sw_version[3] = SW_VERSION_N4;
430 housekeeping_packet.lfr_sw_version[3] = SW_VERSION_N4;
439 // init fpga version
431 // init fpga version
440 parameters = (unsigned char *) (REGS_ADDR_VHDL_VERSION);
432 parameters = (unsigned char *) (REGS_ADDR_VHDL_VERSION);
441 housekeeping_packet.lfr_fpga_version[0] = parameters[1]; // n1
433 housekeeping_packet.lfr_fpga_version[0] = parameters[1]; // n1
442 housekeeping_packet.lfr_fpga_version[1] = parameters[2]; // n2
434 housekeeping_packet.lfr_fpga_version[1] = parameters[2]; // n2
443 housekeeping_packet.lfr_fpga_version[2] = parameters[3]; // n3
435 housekeeping_packet.lfr_fpga_version[2] = parameters[3]; // n3
444
436
445 housekeeping_packet.hk_lfr_q_sd_fifo_size = MSG_QUEUE_COUNT_SEND;
437 housekeeping_packet.hk_lfr_q_sd_fifo_size = MSG_QUEUE_COUNT_SEND;
446 housekeeping_packet.hk_lfr_q_rv_fifo_size = MSG_QUEUE_COUNT_RECV;
438 housekeeping_packet.hk_lfr_q_rv_fifo_size = MSG_QUEUE_COUNT_RECV;
447 housekeeping_packet.hk_lfr_q_p0_fifo_size = MSG_QUEUE_COUNT_PRC0;
439 housekeeping_packet.hk_lfr_q_p0_fifo_size = MSG_QUEUE_COUNT_PRC0;
448 housekeeping_packet.hk_lfr_q_p1_fifo_size = MSG_QUEUE_COUNT_PRC1;
440 housekeeping_packet.hk_lfr_q_p1_fifo_size = MSG_QUEUE_COUNT_PRC1;
449 housekeeping_packet.hk_lfr_q_p2_fifo_size = MSG_QUEUE_COUNT_PRC2;
441 housekeeping_packet.hk_lfr_q_p2_fifo_size = MSG_QUEUE_COUNT_PRC2;
450 }
442 }
451
443
452 void increment_seq_counter( unsigned short *packetSequenceControl )
444 void increment_seq_counter( unsigned short *packetSequenceControl )
453 {
445 {
454 /** This function increment the sequence counter passes in argument.
446 /** This function increment the sequence counter passes in argument.
455 *
447 *
456 * The increment does not affect the grouping flag. In case of an overflow, the counter is reset to 0.
448 * The increment does not affect the grouping flag. In case of an overflow, the counter is reset to 0.
457 *
449 *
458 */
450 */
459
451
460 unsigned short segmentation_grouping_flag;
452 unsigned short segmentation_grouping_flag;
461 unsigned short sequence_cnt;
453 unsigned short sequence_cnt;
462
454
463 segmentation_grouping_flag = TM_PACKET_SEQ_CTRL_STANDALONE << 8; // keep bits 7 downto 6
455 segmentation_grouping_flag = TM_PACKET_SEQ_CTRL_STANDALONE << 8; // keep bits 7 downto 6
464 sequence_cnt = (*packetSequenceControl) & 0x3fff; // [0011 1111 1111 1111]
456 sequence_cnt = (*packetSequenceControl) & 0x3fff; // [0011 1111 1111 1111]
465
457
466 if ( sequence_cnt < SEQ_CNT_MAX)
458 if ( sequence_cnt < SEQ_CNT_MAX)
467 {
459 {
468 sequence_cnt = sequence_cnt + 1;
460 sequence_cnt = sequence_cnt + 1;
469 }
461 }
470 else
462 else
471 {
463 {
472 sequence_cnt = 0;
464 sequence_cnt = 0;
473 }
465 }
474
466
475 *packetSequenceControl = segmentation_grouping_flag | sequence_cnt ;
467 *packetSequenceControl = segmentation_grouping_flag | sequence_cnt ;
476 }
468 }
477
469
478 void getTime( unsigned char *time)
470 void getTime( unsigned char *time)
479 {
471 {
480 /** This function write the current local time in the time buffer passed in argument.
472 /** This function write the current local time in the time buffer passed in argument.
481 *
473 *
482 */
474 */
483
475
484 time[0] = (unsigned char) (time_management_regs->coarse_time>>24);
476 time[0] = (unsigned char) (time_management_regs->coarse_time>>24);
485 time[1] = (unsigned char) (time_management_regs->coarse_time>>16);
477 time[1] = (unsigned char) (time_management_regs->coarse_time>>16);
486 time[2] = (unsigned char) (time_management_regs->coarse_time>>8);
478 time[2] = (unsigned char) (time_management_regs->coarse_time>>8);
487 time[3] = (unsigned char) (time_management_regs->coarse_time);
479 time[3] = (unsigned char) (time_management_regs->coarse_time);
488 time[4] = (unsigned char) (time_management_regs->fine_time>>8);
480 time[4] = (unsigned char) (time_management_regs->fine_time>>8);
489 time[5] = (unsigned char) (time_management_regs->fine_time);
481 time[5] = (unsigned char) (time_management_regs->fine_time);
490 }
482 }
491
483
492 unsigned long long int getTimeAsUnsignedLongLongInt( )
484 unsigned long long int getTimeAsUnsignedLongLongInt( )
493 {
485 {
494 /** This function write the current local time in the time buffer passed in argument.
486 /** This function write the current local time in the time buffer passed in argument.
495 *
487 *
496 */
488 */
497 unsigned long long int time;
489 unsigned long long int time;
498
490
499 time = ( (unsigned long long int) (time_management_regs->coarse_time & 0x7fffffff) << 16 )
491 time = ( (unsigned long long int) (time_management_regs->coarse_time & 0x7fffffff) << 16 )
500 + time_management_regs->fine_time;
492 + time_management_regs->fine_time;
501
493
502 return time;
494 return time;
503 }
495 }
504
496
505 void send_dumb_hk( void )
497 void send_dumb_hk( void )
506 {
498 {
507 Packet_TM_LFR_HK_t dummy_hk_packet;
499 Packet_TM_LFR_HK_t dummy_hk_packet;
508 unsigned char *parameters;
500 unsigned char *parameters;
509 unsigned int i;
501 unsigned int i;
510 rtems_id queue_id;
502 rtems_id queue_id;
511
503
512 dummy_hk_packet.targetLogicalAddress = CCSDS_DESTINATION_ID;
504 dummy_hk_packet.targetLogicalAddress = CCSDS_DESTINATION_ID;
513 dummy_hk_packet.protocolIdentifier = CCSDS_PROTOCOLE_ID;
505 dummy_hk_packet.protocolIdentifier = CCSDS_PROTOCOLE_ID;
514 dummy_hk_packet.reserved = DEFAULT_RESERVED;
506 dummy_hk_packet.reserved = DEFAULT_RESERVED;
515 dummy_hk_packet.userApplication = CCSDS_USER_APP;
507 dummy_hk_packet.userApplication = CCSDS_USER_APP;
516 dummy_hk_packet.packetID[0] = (unsigned char) (APID_TM_HK >> 8);
508 dummy_hk_packet.packetID[0] = (unsigned char) (APID_TM_HK >> 8);
517 dummy_hk_packet.packetID[1] = (unsigned char) (APID_TM_HK);
509 dummy_hk_packet.packetID[1] = (unsigned char) (APID_TM_HK);
518 dummy_hk_packet.packetSequenceControl[0] = TM_PACKET_SEQ_CTRL_STANDALONE;
510 dummy_hk_packet.packetSequenceControl[0] = TM_PACKET_SEQ_CTRL_STANDALONE;
519 dummy_hk_packet.packetSequenceControl[1] = TM_PACKET_SEQ_CNT_DEFAULT;
511 dummy_hk_packet.packetSequenceControl[1] = TM_PACKET_SEQ_CNT_DEFAULT;
520 dummy_hk_packet.packetLength[0] = (unsigned char) (PACKET_LENGTH_HK >> 8);
512 dummy_hk_packet.packetLength[0] = (unsigned char) (PACKET_LENGTH_HK >> 8);
521 dummy_hk_packet.packetLength[1] = (unsigned char) (PACKET_LENGTH_HK );
513 dummy_hk_packet.packetLength[1] = (unsigned char) (PACKET_LENGTH_HK );
522 dummy_hk_packet.spare1_pusVersion_spare2 = DEFAULT_SPARE1_PUSVERSION_SPARE2;
514 dummy_hk_packet.spare1_pusVersion_spare2 = DEFAULT_SPARE1_PUSVERSION_SPARE2;
523 dummy_hk_packet.serviceType = TM_TYPE_HK;
515 dummy_hk_packet.serviceType = TM_TYPE_HK;
524 dummy_hk_packet.serviceSubType = TM_SUBTYPE_HK;
516 dummy_hk_packet.serviceSubType = TM_SUBTYPE_HK;
525 dummy_hk_packet.destinationID = TM_DESTINATION_ID_GROUND;
517 dummy_hk_packet.destinationID = TM_DESTINATION_ID_GROUND;
526 dummy_hk_packet.time[0] = (unsigned char) (time_management_regs->coarse_time>>24);
518 dummy_hk_packet.time[0] = (unsigned char) (time_management_regs->coarse_time>>24);
527 dummy_hk_packet.time[1] = (unsigned char) (time_management_regs->coarse_time>>16);
519 dummy_hk_packet.time[1] = (unsigned char) (time_management_regs->coarse_time>>16);
528 dummy_hk_packet.time[2] = (unsigned char) (time_management_regs->coarse_time>>8);
520 dummy_hk_packet.time[2] = (unsigned char) (time_management_regs->coarse_time>>8);
529 dummy_hk_packet.time[3] = (unsigned char) (time_management_regs->coarse_time);
521 dummy_hk_packet.time[3] = (unsigned char) (time_management_regs->coarse_time);
530 dummy_hk_packet.time[4] = (unsigned char) (time_management_regs->fine_time>>8);
522 dummy_hk_packet.time[4] = (unsigned char) (time_management_regs->fine_time>>8);
531 dummy_hk_packet.time[5] = (unsigned char) (time_management_regs->fine_time);
523 dummy_hk_packet.time[5] = (unsigned char) (time_management_regs->fine_time);
532 dummy_hk_packet.sid = SID_HK;
524 dummy_hk_packet.sid = SID_HK;
533
525
534 // init status word
526 // init status word
535 dummy_hk_packet.lfr_status_word[0] = 0xff;
527 dummy_hk_packet.lfr_status_word[0] = 0xff;
536 dummy_hk_packet.lfr_status_word[1] = 0xff;
528 dummy_hk_packet.lfr_status_word[1] = 0xff;
537 // init software version
529 // init software version
538 dummy_hk_packet.lfr_sw_version[0] = SW_VERSION_N1;
530 dummy_hk_packet.lfr_sw_version[0] = SW_VERSION_N1;
539 dummy_hk_packet.lfr_sw_version[1] = SW_VERSION_N2;
531 dummy_hk_packet.lfr_sw_version[1] = SW_VERSION_N2;
540 dummy_hk_packet.lfr_sw_version[2] = SW_VERSION_N3;
532 dummy_hk_packet.lfr_sw_version[2] = SW_VERSION_N3;
541 dummy_hk_packet.lfr_sw_version[3] = SW_VERSION_N4;
533 dummy_hk_packet.lfr_sw_version[3] = SW_VERSION_N4;
542 // init fpga version
534 // init fpga version
543 parameters = (unsigned char *) (REGS_ADDR_WAVEFORM_PICKER + 0xb0);
535 parameters = (unsigned char *) (REGS_ADDR_WAVEFORM_PICKER + 0xb0);
544 dummy_hk_packet.lfr_fpga_version[0] = parameters[1]; // n1
536 dummy_hk_packet.lfr_fpga_version[0] = parameters[1]; // n1
545 dummy_hk_packet.lfr_fpga_version[1] = parameters[2]; // n2
537 dummy_hk_packet.lfr_fpga_version[1] = parameters[2]; // n2
546 dummy_hk_packet.lfr_fpga_version[2] = parameters[3]; // n3
538 dummy_hk_packet.lfr_fpga_version[2] = parameters[3]; // n3
547
539
548 parameters = (unsigned char *) &dummy_hk_packet.hk_lfr_cpu_load;
540 parameters = (unsigned char *) &dummy_hk_packet.hk_lfr_cpu_load;
549
541
550 for (i=0; i<100; i++)
542 for (i=0; i<100; i++)
551 {
543 {
552 parameters[i] = 0xff;
544 parameters[i] = 0xff;
553 }
545 }
554
546
555 get_message_queue_id_send( &queue_id );
547 get_message_queue_id_send( &queue_id );
556
548
557 rtems_message_queue_send( queue_id, &dummy_hk_packet,
549 rtems_message_queue_send( queue_id, &dummy_hk_packet,
558 PACKET_LENGTH_HK + CCSDS_TC_TM_PACKET_OFFSET + CCSDS_PROTOCOLE_EXTRA_BYTES);
550 PACKET_LENGTH_HK + CCSDS_TC_TM_PACKET_OFFSET + CCSDS_PROTOCOLE_EXTRA_BYTES);
559 }
551 }
560
552
561 void get_temperatures( unsigned char *temperatures )
553 void get_temperatures( unsigned char *temperatures )
562 {
554 {
563 unsigned char* temp_scm_ptr;
555 unsigned char* temp_scm_ptr;
564 unsigned char* temp_pcb_ptr;
556 unsigned char* temp_pcb_ptr;
565 unsigned char* temp_fpga_ptr;
557 unsigned char* temp_fpga_ptr;
566
558
567 // SEL1 SEL0
559 // SEL1 SEL0
568 // 0 0 => PCB
560 // 0 0 => PCB
569 // 0 1 => FPGA
561 // 0 1 => FPGA
570 // 1 0 => SCM
562 // 1 0 => SCM
571
563
572 temp_scm_ptr = (unsigned char *) &time_management_regs->temp_scm;
564 temp_scm_ptr = (unsigned char *) &time_management_regs->temp_scm;
573 temp_pcb_ptr = (unsigned char *) &time_management_regs->temp_pcb;
565 temp_pcb_ptr = (unsigned char *) &time_management_regs->temp_pcb;
574 temp_fpga_ptr = (unsigned char *) &time_management_regs->temp_fpga;
566 temp_fpga_ptr = (unsigned char *) &time_management_regs->temp_fpga;
575
567
576 temperatures[0] = temp_scm_ptr[2];
568 temperatures[0] = temp_scm_ptr[2];
577 temperatures[1] = temp_scm_ptr[3];
569 temperatures[1] = temp_scm_ptr[3];
578 temperatures[2] = temp_pcb_ptr[2];
570 temperatures[2] = temp_pcb_ptr[2];
579 temperatures[3] = temp_pcb_ptr[3];
571 temperatures[3] = temp_pcb_ptr[3];
580 temperatures[4] = temp_fpga_ptr[2];
572 temperatures[4] = temp_fpga_ptr[2];
581 temperatures[5] = temp_fpga_ptr[3];
573 temperatures[5] = temp_fpga_ptr[3];
582 }
574 }
583
575
584 void get_v_e1_e2_f3( unsigned char *spacecraft_potential )
576 void get_v_e1_e2_f3( unsigned char *spacecraft_potential )
585 {
577 {
586 unsigned char* v_ptr;
578 unsigned char* v_ptr;
587 unsigned char* e1_ptr;
579 unsigned char* e1_ptr;
588 unsigned char* e2_ptr;
580 unsigned char* e2_ptr;
589
581
590 v_ptr = (unsigned char *) &waveform_picker_regs->v;
582 v_ptr = (unsigned char *) &waveform_picker_regs->v;
591 e1_ptr = (unsigned char *) &waveform_picker_regs->e1;
583 e1_ptr = (unsigned char *) &waveform_picker_regs->e1;
592 e2_ptr = (unsigned char *) &waveform_picker_regs->e2;
584 e2_ptr = (unsigned char *) &waveform_picker_regs->e2;
593
585
594 spacecraft_potential[0] = v_ptr[2];
586 spacecraft_potential[0] = v_ptr[2];
595 spacecraft_potential[1] = v_ptr[3];
587 spacecraft_potential[1] = v_ptr[3];
596 spacecraft_potential[2] = e1_ptr[2];
588 spacecraft_potential[2] = e1_ptr[2];
597 spacecraft_potential[3] = e1_ptr[3];
589 spacecraft_potential[3] = e1_ptr[3];
598 spacecraft_potential[4] = e2_ptr[2];
590 spacecraft_potential[4] = e2_ptr[2];
599 spacecraft_potential[5] = e2_ptr[3];
591 spacecraft_potential[5] = e2_ptr[3];
600 }
592 }
601
593
602 void get_cpu_load( unsigned char *resource_statistics )
594 void get_cpu_load( unsigned char *resource_statistics )
603 {
595 {
604 unsigned char cpu_load;
596 unsigned char cpu_load;
605
597
606 cpu_load = lfr_rtems_cpu_usage_report();
598 cpu_load = lfr_rtems_cpu_usage_report();
607
599
608 // HK_LFR_CPU_LOAD
600 // HK_LFR_CPU_LOAD
609 resource_statistics[0] = cpu_load;
601 resource_statistics[0] = cpu_load;
610
602
611 // HK_LFR_CPU_LOAD_MAX
603 // HK_LFR_CPU_LOAD_MAX
612 if (cpu_load > resource_statistics[1])
604 if (cpu_load > resource_statistics[1])
613 {
605 {
614 resource_statistics[1] = cpu_load;
606 resource_statistics[1] = cpu_load;
615 }
607 }
616
608
617 // CPU_LOAD_AVE
609 // CPU_LOAD_AVE
618 resource_statistics[2] = 0;
610 resource_statistics[2] = 0;
619
611
620 #ifndef PRINT_TASK_STATISTICS
612 #ifndef PRINT_TASK_STATISTICS
621 rtems_cpu_usage_reset();
613 rtems_cpu_usage_reset();
622 #endif
614 #endif
623
615
624 }
616 }
625
617
626 void set_hk_lfr_sc_potential_flag( bool state )
618 void set_hk_lfr_sc_potential_flag( bool state )
627 {
619 {
628 if (state == true)
620 if (state == true)
629 {
621 {
630 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] | 0x40; // [0100 0000]
622 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] | 0x40; // [0100 0000]
631 }
623 }
632 else
624 else
633 {
625 {
634 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] & 0xbf; // [1011 1111]
626 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] & 0xbf; // [1011 1111]
635 }
627 }
636 }
628 }
637
629
638 void set_hk_lfr_mag_fields_flag( bool state )
630 void set_hk_lfr_mag_fields_flag( bool state )
639 {
631 {
640 if (state == true)
632 if (state == true)
641 {
633 {
642 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] | 0x20; // [0010 0000]
634 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] | 0x20; // [0010 0000]
643 }
635 }
644 else
636 else
645 {
637 {
646 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] & 0xd7; // [1101 1111]
638 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] & 0xd7; // [1101 1111]
647 }
639 }
648 }
640 }
649
641
650 void set_hk_lfr_calib_enable( bool state )
642 void set_hk_lfr_calib_enable( bool state )
651 {
643 {
652 if (state == true)
644 if (state == true)
653 {
645 {
654 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] | 0x08; // [0000 1000]
646 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] | 0x08; // [0000 1000]
655 }
647 }
656 else
648 else
657 {
649 {
658 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] & 0xf7; // [1111 0111]
650 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1] & 0xf7; // [1111 0111]
659 }
651 }
660 }
652 }
661
653
662 void set_hk_lfr_reset_cause( enum lfr_reset_cause_t lfr_reset_cause )
654 void set_hk_lfr_reset_cause( enum lfr_reset_cause_t lfr_reset_cause )
663 {
655 {
664 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1]
656 housekeeping_packet.lfr_status_word[1] = housekeeping_packet.lfr_status_word[1]
665 | (lfr_reset_cause & 0x07 ); // [0000 0111]
657 | (lfr_reset_cause & 0x07 ); // [0000 0111]
666 }
658 }
667
659
668 void hk_lfr_le_me_he_update()
660 void hk_lfr_le_me_he_update()
669 {
661 {
670 unsigned int hk_lfr_le_cnt;
662 unsigned int hk_lfr_le_cnt;
671 unsigned int hk_lfr_me_cnt;
663 unsigned int hk_lfr_me_cnt;
672 unsigned int hk_lfr_he_cnt;
664 unsigned int hk_lfr_he_cnt;
673
665
674 hk_lfr_le_cnt = 0;
666 hk_lfr_le_cnt = 0;
675 hk_lfr_me_cnt = 0;
667 hk_lfr_me_cnt = 0;
676 hk_lfr_he_cnt = 0;
668 hk_lfr_he_cnt = 0;
677
669
678 //update the low severity error counter
670 //update the low severity error counter
679 hk_lfr_le_cnt =
671 hk_lfr_le_cnt =
680 housekeeping_packet.hk_lfr_dpu_spw_parity
672 housekeeping_packet.hk_lfr_dpu_spw_parity
681 + housekeeping_packet.hk_lfr_dpu_spw_disconnect
673 + housekeeping_packet.hk_lfr_dpu_spw_disconnect
682 + housekeeping_packet.hk_lfr_dpu_spw_escape
674 + housekeeping_packet.hk_lfr_dpu_spw_escape
683 + housekeeping_packet.hk_lfr_dpu_spw_credit
675 + housekeeping_packet.hk_lfr_dpu_spw_credit
684 + housekeeping_packet.hk_lfr_dpu_spw_write_sync
676 + housekeeping_packet.hk_lfr_dpu_spw_write_sync
685 + housekeeping_packet.hk_lfr_dpu_spw_rx_ahb
677 + housekeeping_packet.hk_lfr_dpu_spw_rx_ahb
686 + housekeeping_packet.hk_lfr_dpu_spw_tx_ahb
678 + housekeeping_packet.hk_lfr_dpu_spw_tx_ahb
687 + housekeeping_packet.hk_lfr_timecode_erroneous
679 + housekeeping_packet.hk_lfr_timecode_erroneous
688 + housekeeping_packet.hk_lfr_timecode_missing
680 + housekeeping_packet.hk_lfr_timecode_missing
689 + housekeeping_packet.hk_lfr_timecode_invalid
681 + housekeeping_packet.hk_lfr_timecode_invalid
690 + housekeeping_packet.hk_lfr_time_timecode_it
682 + housekeeping_packet.hk_lfr_time_timecode_it
691 + housekeeping_packet.hk_lfr_time_not_synchro
683 + housekeeping_packet.hk_lfr_time_not_synchro
692 + housekeeping_packet.hk_lfr_time_timecode_ctr;
684 + housekeeping_packet.hk_lfr_time_timecode_ctr;
693
685
694 //update the medium severity error counter
686 //update the medium severity error counter
695 hk_lfr_me_cnt =
687 hk_lfr_me_cnt =
696 housekeeping_packet.hk_lfr_dpu_spw_early_eop
688 housekeeping_packet.hk_lfr_dpu_spw_early_eop
697 + housekeeping_packet.hk_lfr_dpu_spw_invalid_addr
689 + housekeeping_packet.hk_lfr_dpu_spw_invalid_addr
698 + housekeeping_packet.hk_lfr_dpu_spw_eep
690 + housekeeping_packet.hk_lfr_dpu_spw_eep
699 + housekeeping_packet.hk_lfr_dpu_spw_rx_too_big;
691 + housekeeping_packet.hk_lfr_dpu_spw_rx_too_big;
700
692
701 //update the high severity error counter
693 //update the high severity error counter
702 hk_lfr_he_cnt = 0;
694 hk_lfr_he_cnt = 0;
703
695
704 // update housekeeping packet counters, convert unsigned int numbers in 2 bytes numbers
696 // update housekeeping packet counters, convert unsigned int numbers in 2 bytes numbers
705 // LE
697 // LE
706 housekeeping_packet.hk_lfr_le_cnt[0] = (unsigned char) ((hk_lfr_le_cnt & 0xff00) >> 8);
698 housekeeping_packet.hk_lfr_le_cnt[0] = (unsigned char) ((hk_lfr_le_cnt & 0xff00) >> 8);
707 housekeeping_packet.hk_lfr_le_cnt[1] = (unsigned char) (hk_lfr_le_cnt & 0x00ff);
699 housekeeping_packet.hk_lfr_le_cnt[1] = (unsigned char) (hk_lfr_le_cnt & 0x00ff);
708 // ME
700 // ME
709 housekeeping_packet.hk_lfr_me_cnt[0] = (unsigned char) ((hk_lfr_me_cnt & 0xff00) >> 8);
701 housekeeping_packet.hk_lfr_me_cnt[0] = (unsigned char) ((hk_lfr_me_cnt & 0xff00) >> 8);
710 housekeeping_packet.hk_lfr_me_cnt[1] = (unsigned char) (hk_lfr_me_cnt & 0x00ff);
702 housekeeping_packet.hk_lfr_me_cnt[1] = (unsigned char) (hk_lfr_me_cnt & 0x00ff);
711 // HE
703 // HE
712 housekeeping_packet.hk_lfr_he_cnt[0] = (unsigned char) ((hk_lfr_he_cnt & 0xff00) >> 8);
704 housekeeping_packet.hk_lfr_he_cnt[0] = (unsigned char) ((hk_lfr_he_cnt & 0xff00) >> 8);
713 housekeeping_packet.hk_lfr_he_cnt[1] = (unsigned char) (hk_lfr_he_cnt & 0x00ff);
705 housekeeping_packet.hk_lfr_he_cnt[1] = (unsigned char) (hk_lfr_he_cnt & 0x00ff);
714
706
715 }
707 }
716
708
717 void set_hk_lfr_time_not_synchro()
709 void set_hk_lfr_time_not_synchro()
718 {
710 {
719 static unsigned char synchroLost = 1;
711 static unsigned char synchroLost = 1;
720 int synchronizationBit;
712 int synchronizationBit;
721
713
722 // get the synchronization bit
714 // get the synchronization bit
723 synchronizationBit = (time_management_regs->coarse_time & 0x80000000) >> 31; // 1000 0000 0000 0000
715 synchronizationBit = (time_management_regs->coarse_time & 0x80000000) >> 31; // 1000 0000 0000 0000
724
716
725 switch (synchronizationBit)
717 switch (synchronizationBit)
726 {
718 {
727 case 0:
719 case 0:
728 if (synchroLost == 1)
720 if (synchroLost == 1)
729 {
721 {
730 synchroLost = 0;
722 synchroLost = 0;
731 }
723 }
732 break;
724 break;
733 case 1:
725 case 1:
734 if (synchroLost == 0 )
726 if (synchroLost == 0 )
735 {
727 {
736 synchroLost = 1;
728 synchroLost = 1;
737 increase_unsigned_char_counter(&housekeeping_packet.hk_lfr_time_not_synchro);
729 increase_unsigned_char_counter(&housekeeping_packet.hk_lfr_time_not_synchro);
738 }
730 }
739 break;
731 break;
740 default:
732 default:
741 PRINTF1("in hk_lfr_time_not_synchro *** unexpected value for synchronizationBit = %d\n", synchronizationBit);
733 PRINTF1("in hk_lfr_time_not_synchro *** unexpected value for synchronizationBit = %d\n", synchronizationBit);
742 break;
734 break;
743 }
735 }
744
736
745 }
737 }
@@ -1,1422 +1,1423
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;
16 rtems_name semq_name;
17 rtems_id semq_id;
17 rtems_id semq_id;
18
18
19 //*****************
19 //*****************
20 // waveform headers
20 // waveform headers
21 Header_TM_LFR_SCIENCE_CWF_t headerCWF;
21 Header_TM_LFR_SCIENCE_CWF_t headerCWF;
22 Header_TM_LFR_SCIENCE_SWF_t headerSWF;
22 Header_TM_LFR_SCIENCE_SWF_t headerSWF;
23 Header_TM_LFR_SCIENCE_ASM_t headerASM;
23 Header_TM_LFR_SCIENCE_ASM_t headerASM;
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 BOOT_PRINTF("in SPIQ *** \n")
42 BOOT_PRINTF("in SPIQ *** \n")
43
43
44 while(true){
44 while(true){
45 rtems_event_receive(SPW_LINKERR_EVENT, RTEMS_WAIT, RTEMS_NO_TIMEOUT, &event_out); // wait for an SPW_LINKERR_EVENT
45 rtems_event_receive(SPW_LINKERR_EVENT, RTEMS_WAIT, RTEMS_NO_TIMEOUT, &event_out); // wait for an SPW_LINKERR_EVENT
46 PRINTF("in SPIQ *** got SPW_LINKERR_EVENT\n")
46 PRINTF("in SPIQ *** got SPW_LINKERR_EVENT\n")
47
47
48 // [0] SUSPEND RECV AND SEND TASKS
48 // [0] SUSPEND RECV AND SEND TASKS
49 status = rtems_task_suspend( Task_id[ TASKID_RECV ] );
49 status = rtems_task_suspend( Task_id[ TASKID_RECV ] );
50 if ( status != RTEMS_SUCCESSFUL ) {
50 if ( status != RTEMS_SUCCESSFUL ) {
51 PRINTF("in SPIQ *** ERR suspending RECV Task\n")
51 PRINTF("in SPIQ *** ERR suspending RECV Task\n")
52 }
52 }
53 status = rtems_task_suspend( Task_id[ TASKID_SEND ] );
53 status = rtems_task_suspend( Task_id[ TASKID_SEND ] );
54 if ( status != RTEMS_SUCCESSFUL ) {
54 if ( status != RTEMS_SUCCESSFUL ) {
55 PRINTF("in SPIQ *** ERR suspending SEND Task\n")
55 PRINTF("in SPIQ *** ERR suspending SEND Task\n")
56 }
56 }
57
57
58 // [1] CHECK THE LINK
58 // [1] CHECK THE LINK
59 status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status (1)
59 status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status (1)
60 if ( linkStatus != 5) {
60 if ( linkStatus != 5) {
61 PRINTF1("in SPIQ *** linkStatus %d, wait...\n", linkStatus)
61 PRINTF1("in SPIQ *** linkStatus %d, wait...\n", linkStatus)
62 status = rtems_task_wake_after( SY_LFR_DPU_CONNECT_TIMEOUT ); // wait SY_LFR_DPU_CONNECT_TIMEOUT 1000 ms
62 status = rtems_task_wake_after( SY_LFR_DPU_CONNECT_TIMEOUT ); // wait SY_LFR_DPU_CONNECT_TIMEOUT 1000 ms
63 }
63 }
64
64
65 // [2] RECHECK THE LINK AFTER SY_LFR_DPU_CONNECT_TIMEOUT
65 // [2] RECHECK THE LINK AFTER SY_LFR_DPU_CONNECT_TIMEOUT
66 status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status (2)
66 status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status (2)
67 if ( linkStatus != 5 ) // [2.a] not in run state, reset the link
67 if ( linkStatus != 5 ) // [2.a] not in run state, reset the link
68 {
68 {
69 spacewire_compute_stats_offsets();
69 spacewire_compute_stats_offsets();
70 status = spacewire_reset_link( );
70 status = spacewire_several_connect_attemps( );
71 }
71 }
72 else // [2.b] in run state, start the link
72 else // [2.b] in run state, start the link
73 {
73 {
74 status = spacewire_stop_and_start_link( fdSPW ); // start the link
74 status = spacewire_stop_and_start_link( fdSPW ); // start the link
75 if ( status != RTEMS_SUCCESSFUL)
75 if ( status != RTEMS_SUCCESSFUL)
76 {
76 {
77 PRINTF1("in SPIQ *** ERR spacewire_stop_and_start_link %d\n", status)
77 PRINTF1("in SPIQ *** ERR spacewire_stop_and_start_link %d\n", status)
78 }
78 }
79 }
79 }
80
80
81 // [3] COMPLETE RECOVERY ACTION AFTER SY_LFR_DPU_CONNECT_ATTEMPTS
81 // [3] COMPLETE RECOVERY ACTION AFTER SY_LFR_DPU_CONNECT_ATTEMPTS
82 if ( status == RTEMS_SUCCESSFUL ) // [3.a] the link is in run state and has been started successfully
82 if ( status == RTEMS_SUCCESSFUL ) // [3.a] the link is in run state and has been started successfully
83 {
83 {
84 status = rtems_task_restart( Task_id[ TASKID_SEND ], 1 );
84 status = rtems_task_restart( Task_id[ TASKID_SEND ], 1 );
85 if ( status != RTEMS_SUCCESSFUL ) {
85 if ( status != RTEMS_SUCCESSFUL ) {
86 PRINTF("in SPIQ *** ERR resuming SEND Task\n")
86 PRINTF("in SPIQ *** ERR resuming SEND Task\n")
87 }
87 }
88 status = rtems_task_restart( Task_id[ TASKID_RECV ], 1 );
88 status = rtems_task_restart( Task_id[ TASKID_RECV ], 1 );
89 if ( status != RTEMS_SUCCESSFUL ) {
89 if ( status != RTEMS_SUCCESSFUL ) {
90 PRINTF("in SPIQ *** ERR resuming RECV Task\n")
90 PRINTF("in SPIQ *** ERR resuming RECV Task\n")
91 }
91 }
92 }
92 }
93 else // [3.b] the link is not in run state, go in STANDBY mode
93 else // [3.b] the link is not in run state, go in STANDBY mode
94 {
94 {
95 status = enter_mode_standby();
95 status = enter_mode_standby();
96 if ( status != RTEMS_SUCCESSFUL ) {
96 if ( status != RTEMS_SUCCESSFUL )
97 {
97 PRINTF1("in SPIQ *** ERR enter_standby_mode *** code %d\n", status)
98 PRINTF1("in SPIQ *** ERR enter_standby_mode *** code %d\n", status)
98 }
99 }
99 // wake the WTDG task up to wait for the link recovery
100 // wake the WTDG task up to wait for the link recovery
100 status = rtems_event_send ( Task_id[TASKID_WTDG], RTEMS_EVENT_0 );
101 status = rtems_event_send ( Task_id[TASKID_WTDG], RTEMS_EVENT_0 );
101 status = rtems_task_suspend( RTEMS_SELF );
102 status = rtems_task_suspend( RTEMS_SELF );
102 }
103 }
103 }
104 }
104 }
105 }
105
106
106 rtems_task recv_task( rtems_task_argument unused )
107 rtems_task recv_task( rtems_task_argument unused )
107 {
108 {
108 /** This RTEMS task is dedicated to the reception of incoming TeleCommands.
109 /** This RTEMS task is dedicated to the reception of incoming TeleCommands.
109 *
110 *
110 * @param unused is the starting argument of the RTEMS task
111 * @param unused is the starting argument of the RTEMS task
111 *
112 *
112 * The RECV task blocks on a call to the read system call, waiting for incoming SpaceWire data. When unblocked:
113 * The RECV task blocks on a call to the read system call, waiting for incoming SpaceWire data. When unblocked:
113 * 1. It reads the incoming data.
114 * 1. It reads the incoming data.
114 * 2. Launches the acceptance procedure.
115 * 2. Launches the acceptance procedure.
115 * 3. If the Telecommand is valid, sends it to a dedicated RTEMS message queue.
116 * 3. If the Telecommand is valid, sends it to a dedicated RTEMS message queue.
116 *
117 *
117 */
118 */
118
119
119 int len;
120 int len;
120 ccsdsTelecommandPacket_t currentTC;
121 ccsdsTelecommandPacket_t currentTC;
121 unsigned char computed_CRC[ 2 ];
122 unsigned char computed_CRC[ 2 ];
122 unsigned char currentTC_LEN_RCV[ 2 ];
123 unsigned char currentTC_LEN_RCV[ 2 ];
123 unsigned char destinationID;
124 unsigned char destinationID;
124 unsigned int estimatedPacketLength;
125 unsigned int estimatedPacketLength;
125 unsigned int parserCode;
126 unsigned int parserCode;
126 rtems_status_code status;
127 rtems_status_code status;
127 rtems_id queue_recv_id;
128 rtems_id queue_recv_id;
128 rtems_id queue_send_id;
129 rtems_id queue_send_id;
129
130
130 initLookUpTableForCRC(); // the table is used to compute Cyclic Redundancy Codes
131 initLookUpTableForCRC(); // the table is used to compute Cyclic Redundancy Codes
131
132
132 status = get_message_queue_id_recv( &queue_recv_id );
133 status = get_message_queue_id_recv( &queue_recv_id );
133 if (status != RTEMS_SUCCESSFUL)
134 if (status != RTEMS_SUCCESSFUL)
134 {
135 {
135 PRINTF1("in RECV *** ERR get_message_queue_id_recv %d\n", status)
136 PRINTF1("in RECV *** ERR get_message_queue_id_recv %d\n", status)
136 }
137 }
137
138
138 status = get_message_queue_id_send( &queue_send_id );
139 status = get_message_queue_id_send( &queue_send_id );
139 if (status != RTEMS_SUCCESSFUL)
140 if (status != RTEMS_SUCCESSFUL)
140 {
141 {
141 PRINTF1("in RECV *** ERR get_message_queue_id_send %d\n", status)
142 PRINTF1("in RECV *** ERR get_message_queue_id_send %d\n", status)
142 }
143 }
143
144
144 BOOT_PRINTF("in RECV *** \n")
145 BOOT_PRINTF("in RECV *** \n")
145
146
146 while(1)
147 while(1)
147 {
148 {
148 len = read( fdSPW, (char*) &currentTC, CCSDS_TC_PKT_MAX_SIZE ); // the call to read is blocking
149 len = read( fdSPW, (char*) &currentTC, CCSDS_TC_PKT_MAX_SIZE ); // the call to read is blocking
149 if (len == -1){ // error during the read call
150 if (len == -1){ // error during the read call
150 PRINTF1("in RECV *** last read call returned -1, ERRNO %d\n", errno)
151 PRINTF1("in RECV *** last read call returned -1, ERRNO %d\n", errno)
151 }
152 }
152 else {
153 else {
153 if ( (len+1) < CCSDS_TC_PKT_MIN_SIZE ) {
154 if ( (len+1) < CCSDS_TC_PKT_MIN_SIZE ) {
154 PRINTF("in RECV *** packet lenght too short\n")
155 PRINTF("in RECV *** packet lenght too short\n")
155 }
156 }
156 else {
157 else {
157 estimatedPacketLength = (unsigned int) (len - CCSDS_TC_TM_PACKET_OFFSET - 3); // => -3 is for Prot ID, Reserved and User App bytes
158 estimatedPacketLength = (unsigned int) (len - CCSDS_TC_TM_PACKET_OFFSET - 3); // => -3 is for Prot ID, Reserved and User App bytes
158 currentTC_LEN_RCV[ 0 ] = (unsigned char) (estimatedPacketLength >> 8);
159 currentTC_LEN_RCV[ 0 ] = (unsigned char) (estimatedPacketLength >> 8);
159 currentTC_LEN_RCV[ 1 ] = (unsigned char) (estimatedPacketLength );
160 currentTC_LEN_RCV[ 1 ] = (unsigned char) (estimatedPacketLength );
160 // CHECK THE TC
161 // CHECK THE TC
161 parserCode = tc_parser( &currentTC, estimatedPacketLength, computed_CRC ) ;
162 parserCode = tc_parser( &currentTC, estimatedPacketLength, computed_CRC ) ;
162 if ( (parserCode == ILLEGAL_APID) || (parserCode == WRONG_LEN_PKT)
163 if ( (parserCode == ILLEGAL_APID) || (parserCode == WRONG_LEN_PKT)
163 || (parserCode == INCOR_CHECKSUM) || (parserCode == ILL_TYPE)
164 || (parserCode == INCOR_CHECKSUM) || (parserCode == ILL_TYPE)
164 || (parserCode == ILL_SUBTYPE) || (parserCode == WRONG_APP_DATA)
165 || (parserCode == ILL_SUBTYPE) || (parserCode == WRONG_APP_DATA)
165 || (parserCode == WRONG_SRC_ID) )
166 || (parserCode == WRONG_SRC_ID) )
166 { // send TM_LFR_TC_EXE_CORRUPTED
167 { // send TM_LFR_TC_EXE_CORRUPTED
167 PRINTF1("TC corrupted received, with code: %d\n", parserCode)
168 PRINTF1("TC corrupted received, with code: %d\n", parserCode)
168 if ( !( (currentTC.serviceType==TC_TYPE_TIME) && (currentTC.serviceSubType==TC_SUBTYPE_UPDT_TIME) )
169 if ( !( (currentTC.serviceType==TC_TYPE_TIME) && (currentTC.serviceSubType==TC_SUBTYPE_UPDT_TIME) )
169 &&
170 &&
170 !( (currentTC.serviceType==TC_TYPE_GEN) && (currentTC.serviceSubType==TC_SUBTYPE_UPDT_INFO))
171 !( (currentTC.serviceType==TC_TYPE_GEN) && (currentTC.serviceSubType==TC_SUBTYPE_UPDT_INFO))
171 )
172 )
172 {
173 {
173 if ( parserCode == WRONG_SRC_ID )
174 if ( parserCode == WRONG_SRC_ID )
174 {
175 {
175 destinationID = SID_TC_GROUND;
176 destinationID = SID_TC_GROUND;
176 }
177 }
177 else
178 else
178 {
179 {
179 destinationID = currentTC.sourceID;
180 destinationID = currentTC.sourceID;
180 }
181 }
181 send_tm_lfr_tc_exe_corrupted( &currentTC, queue_send_id,
182 send_tm_lfr_tc_exe_corrupted( &currentTC, queue_send_id,
182 computed_CRC, currentTC_LEN_RCV,
183 computed_CRC, currentTC_LEN_RCV,
183 destinationID );
184 destinationID );
184 }
185 }
185 }
186 }
186 else
187 else
187 { // send valid TC to the action launcher
188 { // send valid TC to the action launcher
188 status = rtems_message_queue_send( queue_recv_id, &currentTC,
189 status = rtems_message_queue_send( queue_recv_id, &currentTC,
189 estimatedPacketLength + CCSDS_TC_TM_PACKET_OFFSET + 3);
190 estimatedPacketLength + CCSDS_TC_TM_PACKET_OFFSET + 3);
190 }
191 }
191 }
192 }
192 }
193 }
193
194
194 update_queue_max_count( queue_recv_id, &hk_lfr_q_rv_fifo_size_max );
195 update_queue_max_count( queue_recv_id, &hk_lfr_q_rv_fifo_size_max );
195
196
196 }
197 }
197 }
198 }
198
199
199 rtems_task send_task( rtems_task_argument argument)
200 rtems_task send_task( rtems_task_argument argument)
200 {
201 {
201 /** This RTEMS task is dedicated to the transmission of TeleMetry packets.
202 /** This RTEMS task is dedicated to the transmission of TeleMetry packets.
202 *
203 *
203 * @param unused is the starting argument of the RTEMS task
204 * @param unused is the starting argument of the RTEMS task
204 *
205 *
205 * The SEND task waits for a message to become available in the dedicated RTEMS queue. When a message arrives:
206 * The SEND task waits for a message to become available in the dedicated RTEMS queue. When a message arrives:
206 * - if the first byte is equal to CCSDS_DESTINATION_ID, the message is sent as is using the write system call.
207 * - if the first byte is equal to CCSDS_DESTINATION_ID, the message is sent as is using the write system call.
207 * - if the first byte is not equal to CCSDS_DESTINATION_ID, the message is handled as a spw_ioctl_pkt_send. After
208 * - if the first byte is not equal to CCSDS_DESTINATION_ID, the message is handled as a spw_ioctl_pkt_send. After
208 * analyzis, the packet is sent either using the write system call or using the ioctl call SPACEWIRE_IOCTRL_SEND, depending on the
209 * analyzis, the packet is sent either using the write system call or using the ioctl call SPACEWIRE_IOCTRL_SEND, depending on the
209 * data it contains.
210 * data it contains.
210 *
211 *
211 */
212 */
212
213
213 rtems_status_code status; // RTEMS status code
214 rtems_status_code status; // RTEMS status code
214 char incomingData[MSG_QUEUE_SIZE_SEND]; // incoming data buffer
215 char incomingData[MSG_QUEUE_SIZE_SEND]; // incoming data buffer
215 ring_node *incomingRingNodePtr;
216 ring_node *incomingRingNodePtr;
216 int ring_node_address;
217 int ring_node_address;
217 char *charPtr;
218 char *charPtr;
218 spw_ioctl_pkt_send *spw_ioctl_send;
219 spw_ioctl_pkt_send *spw_ioctl_send;
219 size_t size; // size of the incoming TC packet
220 size_t size; // size of the incoming TC packet
220 rtems_id queue_send_id;
221 rtems_id queue_send_id;
221 unsigned int sid;
222 unsigned int sid;
222 unsigned char sidAsUnsignedChar;
223 unsigned char sidAsUnsignedChar;
223 unsigned char type;
224 unsigned char type;
224
225
225 incomingRingNodePtr = NULL;
226 incomingRingNodePtr = NULL;
226 ring_node_address = 0;
227 ring_node_address = 0;
227 charPtr = (char *) &ring_node_address;
228 charPtr = (char *) &ring_node_address;
228 sid = 0;
229 sid = 0;
229 sidAsUnsignedChar = 0;
230 sidAsUnsignedChar = 0;
230
231
231 init_header_cwf( &headerCWF );
232 init_header_cwf( &headerCWF );
232 init_header_swf( &headerSWF );
233 init_header_swf( &headerSWF );
233 init_header_asm( &headerASM );
234 init_header_asm( &headerASM );
234
235
235 status = get_message_queue_id_send( &queue_send_id );
236 status = get_message_queue_id_send( &queue_send_id );
236 if (status != RTEMS_SUCCESSFUL)
237 if (status != RTEMS_SUCCESSFUL)
237 {
238 {
238 PRINTF1("in HOUS *** ERR get_message_queue_id_send %d\n", status)
239 PRINTF1("in HOUS *** ERR get_message_queue_id_send %d\n", status)
239 }
240 }
240
241
241 BOOT_PRINTF("in SEND *** \n")
242 BOOT_PRINTF("in SEND *** \n")
242
243
243 while(1)
244 while(1)
244 {
245 {
245 status = rtems_message_queue_receive( queue_send_id, incomingData, &size,
246 status = rtems_message_queue_receive( queue_send_id, incomingData, &size,
246 RTEMS_WAIT, RTEMS_NO_TIMEOUT );
247 RTEMS_WAIT, RTEMS_NO_TIMEOUT );
247
248
248 if (status!=RTEMS_SUCCESSFUL)
249 if (status!=RTEMS_SUCCESSFUL)
249 {
250 {
250 PRINTF1("in SEND *** (1) ERR = %d\n", status)
251 PRINTF1("in SEND *** (1) ERR = %d\n", status)
251 }
252 }
252 else
253 else
253 {
254 {
254 if ( size == sizeof(ring_node*) )
255 if ( size == sizeof(ring_node*) )
255 {
256 {
256 charPtr[0] = incomingData[0];
257 charPtr[0] = incomingData[0];
257 charPtr[1] = incomingData[1];
258 charPtr[1] = incomingData[1];
258 charPtr[2] = incomingData[2];
259 charPtr[2] = incomingData[2];
259 charPtr[3] = incomingData[3];
260 charPtr[3] = incomingData[3];
260 incomingRingNodePtr = (ring_node*) ring_node_address;
261 incomingRingNodePtr = (ring_node*) ring_node_address;
261 sid = incomingRingNodePtr->sid;
262 sid = incomingRingNodePtr->sid;
262 if ( (sid==SID_NORM_CWF_LONG_F3)
263 if ( (sid==SID_NORM_CWF_LONG_F3)
263 || (sid==SID_BURST_CWF_F2 )
264 || (sid==SID_BURST_CWF_F2 )
264 || (sid==SID_SBM1_CWF_F1 )
265 || (sid==SID_SBM1_CWF_F1 )
265 || (sid==SID_SBM2_CWF_F2 ))
266 || (sid==SID_SBM2_CWF_F2 ))
266 {
267 {
267 spw_send_waveform_CWF( incomingRingNodePtr, &headerCWF );
268 spw_send_waveform_CWF( incomingRingNodePtr, &headerCWF );
268 }
269 }
269 else if ( (sid==SID_NORM_SWF_F0) || (sid== SID_NORM_SWF_F1) || (sid==SID_NORM_SWF_F2) )
270 else if ( (sid==SID_NORM_SWF_F0) || (sid== SID_NORM_SWF_F1) || (sid==SID_NORM_SWF_F2) )
270 {
271 {
271 spw_send_waveform_SWF( incomingRingNodePtr, &headerSWF );
272 spw_send_waveform_SWF( incomingRingNodePtr, &headerSWF );
272 }
273 }
273 else if ( (sid==SID_NORM_CWF_F3) )
274 else if ( (sid==SID_NORM_CWF_F3) )
274 {
275 {
275 spw_send_waveform_CWF3_light( incomingRingNodePtr, &headerCWF );
276 spw_send_waveform_CWF3_light( incomingRingNodePtr, &headerCWF );
276 }
277 }
277 else if (sid==SID_NORM_ASM_F0)
278 else if (sid==SID_NORM_ASM_F0)
278 {
279 {
279 spw_send_asm_f0( incomingRingNodePtr, &headerASM );
280 spw_send_asm_f0( incomingRingNodePtr, &headerASM );
280 }
281 }
281 else if (sid==SID_NORM_ASM_F1)
282 else if (sid==SID_NORM_ASM_F1)
282 {
283 {
283 spw_send_asm_f1( incomingRingNodePtr, &headerASM );
284 spw_send_asm_f1( incomingRingNodePtr, &headerASM );
284 }
285 }
285 else if (sid==SID_NORM_ASM_F2)
286 else if (sid==SID_NORM_ASM_F2)
286 {
287 {
287 spw_send_asm_f2( incomingRingNodePtr, &headerASM );
288 spw_send_asm_f2( incomingRingNodePtr, &headerASM );
288 }
289 }
289 else if ( sid==TM_CODE_K_DUMP )
290 else if ( sid==TM_CODE_K_DUMP )
290 {
291 {
291 spw_send_k_dump( incomingRingNodePtr );
292 spw_send_k_dump( incomingRingNodePtr );
292 }
293 }
293 else
294 else
294 {
295 {
295 PRINTF1("unexpected sid = %d\n", sid);
296 PRINTF1("unexpected sid = %d\n", sid);
296 }
297 }
297 }
298 }
298 else if ( incomingData[0] == CCSDS_DESTINATION_ID ) // the incoming message is a ccsds packet
299 else if ( incomingData[0] == CCSDS_DESTINATION_ID ) // the incoming message is a ccsds packet
299 {
300 {
300 sidAsUnsignedChar = (unsigned char) incomingData[ PACKET_POS_PA_LFR_SID_PKT ];
301 sidAsUnsignedChar = (unsigned char) incomingData[ PACKET_POS_PA_LFR_SID_PKT ];
301 sid = sidAsUnsignedChar;
302 sid = sidAsUnsignedChar;
302 type = (unsigned char) incomingData[ PACKET_POS_SERVICE_TYPE ];
303 type = (unsigned char) incomingData[ PACKET_POS_SERVICE_TYPE ];
303 if (type == TM_TYPE_LFR_SCIENCE) // this is a BP packet, all other types are handled differently
304 if (type == TM_TYPE_LFR_SCIENCE) // this is a BP packet, all other types are handled differently
304 // SET THE SEQUENCE_CNT PARAMETER IN CASE OF BP0 OR BP1 PACKETS
305 // SET THE SEQUENCE_CNT PARAMETER IN CASE OF BP0 OR BP1 PACKETS
305 {
306 {
306 increment_seq_counter_source_id( (unsigned char*) &incomingData[ PACKET_POS_SEQUENCE_CNT ], sid );
307 increment_seq_counter_source_id( (unsigned char*) &incomingData[ PACKET_POS_SEQUENCE_CNT ], sid );
307 }
308 }
308
309
309 status = write( fdSPW, incomingData, size );
310 status = write( fdSPW, incomingData, size );
310 if (status == -1){
311 if (status == -1){
311 PRINTF2("in SEND *** (2.a) ERRNO = %d, size = %d\n", errno, size)
312 PRINTF2("in SEND *** (2.a) ERRNO = %d, size = %d\n", errno, size)
312 }
313 }
313 }
314 }
314 else // the incoming message is a spw_ioctl_pkt_send structure
315 else // the incoming message is a spw_ioctl_pkt_send structure
315 {
316 {
316 spw_ioctl_send = (spw_ioctl_pkt_send*) incomingData;
317 spw_ioctl_send = (spw_ioctl_pkt_send*) incomingData;
317 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, spw_ioctl_send );
318 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, spw_ioctl_send );
318 if (status == -1){
319 if (status == -1){
319 PRINTF2("in SEND *** (2.b) ERRNO = %d, RTEMS = %d\n", errno, status)
320 PRINTF2("in SEND *** (2.b) ERRNO = %d, RTEMS = %d\n", errno, status)
320 }
321 }
321 }
322 }
322 }
323 }
323
324
324 update_queue_max_count( queue_send_id, &hk_lfr_q_sd_fifo_size_max );
325 update_queue_max_count( queue_send_id, &hk_lfr_q_sd_fifo_size_max );
325
326
326 }
327 }
327 }
328 }
328
329
329 rtems_task wtdg_task( rtems_task_argument argument )
330 rtems_task wtdg_task( rtems_task_argument argument )
330 {
331 {
331 rtems_event_set event_out;
332 rtems_event_set event_out;
332 rtems_status_code status;
333 rtems_status_code status;
333 int linkStatus;
334 int linkStatus;
334
335
335 BOOT_PRINTF("in WTDG ***\n")
336 BOOT_PRINTF("in WTDG ***\n")
336
337
337 while(1)
338 while(1)
338 {
339 {
339 // wait for an RTEMS_EVENT
340 // wait for an RTEMS_EVENT
340 rtems_event_receive( RTEMS_EVENT_0,
341 rtems_event_receive( RTEMS_EVENT_0,
341 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
342 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
342 PRINTF("in WTDG *** wait for the link\n")
343 PRINTF("in WTDG *** wait for the link\n")
343 status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status
344 status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status
344 while( linkStatus != 5) // wait for the link
345 while( linkStatus != 5) // wait for the link
345 {
346 {
346 status = rtems_task_wake_after( 10 ); // monitor the link each 100ms
347 status = rtems_task_wake_after( 10 ); // monitor the link each 100ms
347 status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status
348 status = ioctl(fdSPW, SPACEWIRE_IOCTRL_GET_LINK_STATUS, &linkStatus); // get the link status
348 }
349 }
349
350
350 status = spacewire_stop_and_start_link( fdSPW );
351 status = spacewire_stop_and_start_link( fdSPW );
351
352
352 if (status != RTEMS_SUCCESSFUL)
353 if (status != RTEMS_SUCCESSFUL)
353 {
354 {
354 PRINTF1("in WTDG *** ERR link not started %d\n", status)
355 PRINTF1("in WTDG *** ERR link not started %d\n", status)
355 }
356 }
356 else
357 else
357 {
358 {
358 PRINTF("in WTDG *** OK link started\n")
359 PRINTF("in WTDG *** OK link started\n")
359 }
360 }
360
361
361 // restart the SPIQ task
362 // restart the SPIQ task
362 status = rtems_task_restart( Task_id[TASKID_SPIQ], 1 );
363 status = rtems_task_restart( Task_id[TASKID_SPIQ], 1 );
363 if ( status != RTEMS_SUCCESSFUL ) {
364 if ( status != RTEMS_SUCCESSFUL ) {
364 PRINTF("in SPIQ *** ERR restarting SPIQ Task\n")
365 PRINTF("in SPIQ *** ERR restarting SPIQ Task\n")
365 }
366 }
366
367
367 // restart RECV and SEND
368 // restart RECV and SEND
368 status = rtems_task_restart( Task_id[ TASKID_SEND ], 1 );
369 status = rtems_task_restart( Task_id[ TASKID_SEND ], 1 );
369 if ( status != RTEMS_SUCCESSFUL ) {
370 if ( status != RTEMS_SUCCESSFUL ) {
370 PRINTF("in SPIQ *** ERR restarting SEND Task\n")
371 PRINTF("in SPIQ *** ERR restarting SEND Task\n")
371 }
372 }
372 status = rtems_task_restart( Task_id[ TASKID_RECV ], 1 );
373 status = rtems_task_restart( Task_id[ TASKID_RECV ], 1 );
373 if ( status != RTEMS_SUCCESSFUL ) {
374 if ( status != RTEMS_SUCCESSFUL ) {
374 PRINTF("in SPIQ *** ERR restarting RECV Task\n")
375 PRINTF("in SPIQ *** ERR restarting RECV Task\n")
375 }
376 }
376 }
377 }
377 }
378 }
378
379
379 //****************
380 //****************
380 // OTHER FUNCTIONS
381 // OTHER FUNCTIONS
381 int spacewire_open_link( void ) // by default, the driver resets the core: [SPW_CTRL_WRITE(pDev, SPW_CTRL_RESET);]
382 int spacewire_open_link( void ) // by default, the driver resets the core: [SPW_CTRL_WRITE(pDev, SPW_CTRL_RESET);]
382 {
383 {
383 /** This function opens the SpaceWire link.
384 /** This function opens the SpaceWire link.
384 *
385 *
385 * @return a valid file descriptor in case of success, -1 in case of a failure
386 * @return a valid file descriptor in case of success, -1 in case of a failure
386 *
387 *
387 */
388 */
388 rtems_status_code status;
389 rtems_status_code status;
389
390
390 fdSPW = open(GRSPW_DEVICE_NAME, O_RDWR); // open the device. the open call resets the hardware
391 fdSPW = open(GRSPW_DEVICE_NAME, O_RDWR); // open the device. the open call resets the hardware
391 if ( fdSPW < 0 ) {
392 if ( fdSPW < 0 ) {
392 PRINTF1("ERR *** in configure_spw_link *** error opening "GRSPW_DEVICE_NAME" with ERR %d\n", errno)
393 PRINTF1("ERR *** in configure_spw_link *** error opening "GRSPW_DEVICE_NAME" with ERR %d\n", errno)
393 }
394 }
394 else
395 else
395 {
396 {
396 status = RTEMS_SUCCESSFUL;
397 status = RTEMS_SUCCESSFUL;
397 }
398 }
398
399
399 return status;
400 return status;
400 }
401 }
401
402
402 int spacewire_start_link( int fd )
403 int spacewire_start_link( int fd )
403 {
404 {
404 rtems_status_code status;
405 rtems_status_code status;
405
406
406 status = ioctl( fd, SPACEWIRE_IOCTRL_START, -1); // returns successfuly if the link is started
407 status = ioctl( fd, SPACEWIRE_IOCTRL_START, -1); // returns successfuly if the link is started
407 // -1 default hardcoded driver timeout
408 // -1 default hardcoded driver timeout
408
409
409 return status;
410 return status;
410 }
411 }
411
412
412 int spacewire_stop_and_start_link( int fd )
413 int spacewire_stop_and_start_link( int fd )
413 {
414 {
414 rtems_status_code status;
415 rtems_status_code status;
415
416
416 status = ioctl( fd, SPACEWIRE_IOCTRL_STOP); // start fails if link pDev->running != 0
417 status = ioctl( fd, SPACEWIRE_IOCTRL_STOP); // start fails if link pDev->running != 0
417 status = ioctl( fd, SPACEWIRE_IOCTRL_START, -1); // returns successfuly if the link is started
418 status = ioctl( fd, SPACEWIRE_IOCTRL_START, -1); // returns successfuly if the link is started
418 // -1 default hardcoded driver timeout
419 // -1 default hardcoded driver timeout
419
420
420 return status;
421 return status;
421 }
422 }
422
423
423 int spacewire_configure_link( int fd )
424 int spacewire_configure_link( int fd )
424 {
425 {
425 /** This function configures the SpaceWire link.
426 /** This function configures the SpaceWire link.
426 *
427 *
427 * @return GR-RTEMS-DRIVER directive status codes:
428 * @return GR-RTEMS-DRIVER directive status codes:
428 * - 22 EINVAL - Null pointer or an out of range value was given as the argument.
429 * - 22 EINVAL - Null pointer or an out of range value was given as the argument.
429 * - 16 EBUSY - Only used for SEND. Returned when no descriptors are avialble in non-blocking mode.
430 * - 16 EBUSY - Only used for SEND. Returned when no descriptors are avialble in non-blocking mode.
430 * - 88 ENOSYS - Returned for SET_DESTKEY if RMAP command handler is not available or if a non-implemented call is used.
431 * - 88 ENOSYS - Returned for SET_DESTKEY if RMAP command handler is not available or if a non-implemented call is used.
431 * - 116 ETIMEDOUT - REturned for SET_PACKET_SIZE and START if the link could not be brought up.
432 * - 116 ETIMEDOUT - REturned for SET_PACKET_SIZE and START if the link could not be brought up.
432 * - 12 ENOMEM - Returned for SET_PACKETSIZE if it was unable to allocate the new buffers.
433 * - 12 ENOMEM - Returned for SET_PACKETSIZE if it was unable to allocate the new buffers.
433 * - 5 EIO - Error when writing to grswp hardware registers.
434 * - 5 EIO - Error when writing to grswp hardware registers.
434 * - 2 ENOENT - No such file or directory
435 * - 2 ENOENT - No such file or directory
435 */
436 */
436
437
437 rtems_status_code status;
438 rtems_status_code status;
438
439
439 spacewire_set_NP(1, REGS_ADDR_GRSPW); // [N]o [P]ort force
440 spacewire_set_NP(1, REGS_ADDR_GRSPW); // [N]o [P]ort force
440 spacewire_set_RE(1, REGS_ADDR_GRSPW); // [R]MAP [E]nable, the dedicated call seems to break the no port force configuration
441 spacewire_set_RE(1, REGS_ADDR_GRSPW); // [R]MAP [E]nable, the dedicated call seems to break the no port force configuration
441
442
442 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_RXBLOCK, 1); // sets the blocking mode for reception
443 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_RXBLOCK, 1); // sets the blocking mode for reception
443 if (status!=RTEMS_SUCCESSFUL) {
444 if (status!=RTEMS_SUCCESSFUL) {
444 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_RXBLOCK\n")
445 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_RXBLOCK\n")
445 }
446 }
446 //
447 //
447 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_EVENT_ID, Task_id[TASKID_SPIQ]); // sets the task ID to which an event is sent when a
448 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_EVENT_ID, Task_id[TASKID_SPIQ]); // sets the task ID to which an event is sent when a
448 if (status!=RTEMS_SUCCESSFUL) {
449 if (status!=RTEMS_SUCCESSFUL) {
449 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_EVENT_ID\n") // link-error interrupt occurs
450 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_EVENT_ID\n") // link-error interrupt occurs
450 }
451 }
451 //
452 //
452 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_DISABLE_ERR, 0); // automatic link-disabling due to link-error interrupts
453 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_DISABLE_ERR, 0); // automatic link-disabling due to link-error interrupts
453 if (status!=RTEMS_SUCCESSFUL) {
454 if (status!=RTEMS_SUCCESSFUL) {
454 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_DISABLE_ERR\n")
455 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_DISABLE_ERR\n")
455 }
456 }
456 //
457 //
457 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_LINK_ERR_IRQ, 1); // sets the link-error interrupt bit
458 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_LINK_ERR_IRQ, 1); // sets the link-error interrupt bit
458 if (status!=RTEMS_SUCCESSFUL) {
459 if (status!=RTEMS_SUCCESSFUL) {
459 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_LINK_ERR_IRQ\n")
460 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_LINK_ERR_IRQ\n")
460 }
461 }
461 //
462 //
462 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_TXBLOCK, 1); // transmission blocks
463 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_TXBLOCK, 1); // transmission blocks
463 if (status!=RTEMS_SUCCESSFUL) {
464 if (status!=RTEMS_SUCCESSFUL) {
464 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_TXBLOCK\n")
465 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_TXBLOCK\n")
465 }
466 }
466 //
467 //
467 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_TXBLOCK_ON_FULL, 1); // transmission blocks when no transmission descriptor is available
468 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_TXBLOCK_ON_FULL, 1); // transmission blocks when no transmission descriptor is available
468 if (status!=RTEMS_SUCCESSFUL) {
469 if (status!=RTEMS_SUCCESSFUL) {
469 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_TXBLOCK_ON_FULL\n")
470 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_TXBLOCK_ON_FULL\n")
470 }
471 }
471 //
472 //
472 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_TCODE_CTRL, 0x0909); // [Time Rx : Time Tx : Link error : Tick-out IRQ]
473 status = ioctl(fd, SPACEWIRE_IOCTRL_SET_TCODE_CTRL, 0x0909); // [Time Rx : Time Tx : Link error : Tick-out IRQ]
473 if (status!=RTEMS_SUCCESSFUL) {
474 if (status!=RTEMS_SUCCESSFUL) {
474 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_TCODE_CTRL,\n")
475 PRINTF("in SPIQ *** Error SPACEWIRE_IOCTRL_SET_TCODE_CTRL,\n")
475 }
476 }
476
477
477 return status;
478 return status;
478 }
479 }
479
480
480 int spacewire_reset_link( void )
481 int spacewire_several_connect_attemps( void )
481 {
482 {
482 /** This function is executed by the SPIQ rtems_task wehn it has been awaken by an interruption raised by the SpaceWire driver.
483 /** This function is executed by the SPIQ rtems_task wehn it has been awaken by an interruption raised by the SpaceWire driver.
483 *
484 *
484 * @return RTEMS directive status code:
485 * @return RTEMS directive status code:
485 * - RTEMS_UNSATISFIED is returned is the link is not in the running state after 10 s.
486 * - RTEMS_UNSATISFIED is returned is the link is not in the running state after 10 s.
486 * - RTEMS_SUCCESSFUL is returned if the link is up before the timeout.
487 * - RTEMS_SUCCESSFUL is returned if the link is up before the timeout.
487 *
488 *
488 */
489 */
489
490
490 rtems_status_code status_spw;
491 rtems_status_code status_spw;
491 rtems_status_code status;
492 rtems_status_code status;
492 int i;
493 int i;
493
494
494 for ( i=0; i<SY_LFR_DPU_CONNECT_ATTEMPT; i++ )
495 for ( i=0; i<SY_LFR_DPU_CONNECT_ATTEMPT; i++ )
495 {
496 {
496 PRINTF1("in spacewire_reset_link *** link recovery, try %d\n", i);
497 PRINTF1("in spacewire_reset_link *** link recovery, try %d\n", i);
497
498
498 // CLOSING THE DRIVER AT THIS POINT WILL MAKE THE SEND TASK BLOCK THE SYSTEM
499 // CLOSING THE DRIVER AT THIS POINT WILL MAKE THE SEND TASK BLOCK THE SYSTEM
499
500
500 status = rtems_task_wake_after( SY_LFR_DPU_CONNECT_TIMEOUT ); // wait SY_LFR_DPU_CONNECT_TIMEOUT 1000 ms
501 status = rtems_task_wake_after( SY_LFR_DPU_CONNECT_TIMEOUT ); // wait SY_LFR_DPU_CONNECT_TIMEOUT 1000 ms
501
502
502 status_spw = spacewire_stop_and_start_link( fdSPW );
503 status_spw = spacewire_stop_and_start_link( fdSPW );
503 if ( status_spw != RTEMS_SUCCESSFUL )
504 if ( status_spw != RTEMS_SUCCESSFUL )
504 {
505 {
505 PRINTF1("in spacewire_reset_link *** ERR spacewire_start_link code %d\n", status_spw)
506 PRINTF1("in spacewire_reset_link *** ERR spacewire_start_link code %d\n", status_spw)
506 }
507 }
507
508
508 if ( status_spw == RTEMS_SUCCESSFUL)
509 if ( status_spw == RTEMS_SUCCESSFUL)
509 {
510 {
510 break;
511 break;
511 }
512 }
512 }
513 }
513
514
514 return status_spw;
515 return status_spw;
515 }
516 }
516
517
517 void spacewire_set_NP( unsigned char val, unsigned int regAddr ) // [N]o [P]ort force
518 void spacewire_set_NP( unsigned char val, unsigned int regAddr ) // [N]o [P]ort force
518 {
519 {
519 /** This function sets the [N]o [P]ort force bit of the GRSPW control register.
520 /** This function sets the [N]o [P]ort force bit of the GRSPW control register.
520 *
521 *
521 * @param val is the value, 0 or 1, used to set the value of the NP bit.
522 * @param val is the value, 0 or 1, used to set the value of the NP bit.
522 * @param regAddr is the address of the GRSPW control register.
523 * @param regAddr is the address of the GRSPW control register.
523 *
524 *
524 * NP is the bit 20 of the GRSPW control register.
525 * NP is the bit 20 of the GRSPW control register.
525 *
526 *
526 */
527 */
527
528
528 unsigned int *spwptr = (unsigned int*) regAddr;
529 unsigned int *spwptr = (unsigned int*) regAddr;
529
530
530 if (val == 1) {
531 if (val == 1) {
531 *spwptr = *spwptr | 0x00100000; // [NP] set the No port force bit
532 *spwptr = *spwptr | 0x00100000; // [NP] set the No port force bit
532 }
533 }
533 if (val== 0) {
534 if (val== 0) {
534 *spwptr = *spwptr & 0xffdfffff;
535 *spwptr = *spwptr & 0xffdfffff;
535 }
536 }
536 }
537 }
537
538
538 void spacewire_set_RE( unsigned char val, unsigned int regAddr ) // [R]MAP [E]nable
539 void spacewire_set_RE( unsigned char val, unsigned int regAddr ) // [R]MAP [E]nable
539 {
540 {
540 /** This function sets the [R]MAP [E]nable bit of the GRSPW control register.
541 /** This function sets the [R]MAP [E]nable bit of the GRSPW control register.
541 *
542 *
542 * @param val is the value, 0 or 1, used to set the value of the RE bit.
543 * @param val is the value, 0 or 1, used to set the value of the RE bit.
543 * @param regAddr is the address of the GRSPW control register.
544 * @param regAddr is the address of the GRSPW control register.
544 *
545 *
545 * RE is the bit 16 of the GRSPW control register.
546 * RE is the bit 16 of the GRSPW control register.
546 *
547 *
547 */
548 */
548
549
549 unsigned int *spwptr = (unsigned int*) regAddr;
550 unsigned int *spwptr = (unsigned int*) regAddr;
550
551
551 if (val == 1)
552 if (val == 1)
552 {
553 {
553 *spwptr = *spwptr | 0x00010000; // [RE] set the RMAP Enable bit
554 *spwptr = *spwptr | 0x00010000; // [RE] set the RMAP Enable bit
554 }
555 }
555 if (val== 0)
556 if (val== 0)
556 {
557 {
557 *spwptr = *spwptr & 0xfffdffff;
558 *spwptr = *spwptr & 0xfffdffff;
558 }
559 }
559 }
560 }
560
561
561 void spacewire_compute_stats_offsets( void )
562 void spacewire_compute_stats_offsets( void )
562 {
563 {
563 /** This function computes the SpaceWire statistics offsets in case of a SpaceWire related interruption raising.
564 /** This function computes the SpaceWire statistics offsets in case of a SpaceWire related interruption raising.
564 *
565 *
565 * The offsets keep a record of the statistics in case of a reset of the statistics. They are added to the current statistics
566 * The offsets keep a record of the statistics in case of a reset of the statistics. They are added to the current statistics
566 * to keep the counters consistent even after a reset of the SpaceWire driver (the counter are set to zero by the driver when it
567 * to keep the counters consistent even after a reset of the SpaceWire driver (the counter are set to zero by the driver when it
567 * during the open systel call).
568 * during the open systel call).
568 *
569 *
569 */
570 */
570
571
571 spw_stats spacewire_stats_grspw;
572 spw_stats spacewire_stats_grspw;
572 rtems_status_code status;
573 rtems_status_code status;
573
574
574 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_GET_STATISTICS, &spacewire_stats_grspw );
575 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_GET_STATISTICS, &spacewire_stats_grspw );
575
576
576 spacewire_stats_backup.packets_received = spacewire_stats_grspw.packets_received
577 spacewire_stats_backup.packets_received = spacewire_stats_grspw.packets_received
577 + spacewire_stats.packets_received;
578 + spacewire_stats.packets_received;
578 spacewire_stats_backup.packets_sent = spacewire_stats_grspw.packets_sent
579 spacewire_stats_backup.packets_sent = spacewire_stats_grspw.packets_sent
579 + spacewire_stats.packets_sent;
580 + spacewire_stats.packets_sent;
580 spacewire_stats_backup.parity_err = spacewire_stats_grspw.parity_err
581 spacewire_stats_backup.parity_err = spacewire_stats_grspw.parity_err
581 + spacewire_stats.parity_err;
582 + spacewire_stats.parity_err;
582 spacewire_stats_backup.disconnect_err = spacewire_stats_grspw.disconnect_err
583 spacewire_stats_backup.disconnect_err = spacewire_stats_grspw.disconnect_err
583 + spacewire_stats.disconnect_err;
584 + spacewire_stats.disconnect_err;
584 spacewire_stats_backup.escape_err = spacewire_stats_grspw.escape_err
585 spacewire_stats_backup.escape_err = spacewire_stats_grspw.escape_err
585 + spacewire_stats.escape_err;
586 + spacewire_stats.escape_err;
586 spacewire_stats_backup.credit_err = spacewire_stats_grspw.credit_err
587 spacewire_stats_backup.credit_err = spacewire_stats_grspw.credit_err
587 + spacewire_stats.credit_err;
588 + spacewire_stats.credit_err;
588 spacewire_stats_backup.write_sync_err = spacewire_stats_grspw.write_sync_err
589 spacewire_stats_backup.write_sync_err = spacewire_stats_grspw.write_sync_err
589 + spacewire_stats.write_sync_err;
590 + spacewire_stats.write_sync_err;
590 spacewire_stats_backup.rx_rmap_header_crc_err = spacewire_stats_grspw.rx_rmap_header_crc_err
591 spacewire_stats_backup.rx_rmap_header_crc_err = spacewire_stats_grspw.rx_rmap_header_crc_err
591 + spacewire_stats.rx_rmap_header_crc_err;
592 + spacewire_stats.rx_rmap_header_crc_err;
592 spacewire_stats_backup.rx_rmap_data_crc_err = spacewire_stats_grspw.rx_rmap_data_crc_err
593 spacewire_stats_backup.rx_rmap_data_crc_err = spacewire_stats_grspw.rx_rmap_data_crc_err
593 + spacewire_stats.rx_rmap_data_crc_err;
594 + spacewire_stats.rx_rmap_data_crc_err;
594 spacewire_stats_backup.early_ep = spacewire_stats_grspw.early_ep
595 spacewire_stats_backup.early_ep = spacewire_stats_grspw.early_ep
595 + spacewire_stats.early_ep;
596 + spacewire_stats.early_ep;
596 spacewire_stats_backup.invalid_address = spacewire_stats_grspw.invalid_address
597 spacewire_stats_backup.invalid_address = spacewire_stats_grspw.invalid_address
597 + spacewire_stats.invalid_address;
598 + spacewire_stats.invalid_address;
598 spacewire_stats_backup.rx_eep_err = spacewire_stats_grspw.rx_eep_err
599 spacewire_stats_backup.rx_eep_err = spacewire_stats_grspw.rx_eep_err
599 + spacewire_stats.rx_eep_err;
600 + spacewire_stats.rx_eep_err;
600 spacewire_stats_backup.rx_truncated = spacewire_stats_grspw.rx_truncated
601 spacewire_stats_backup.rx_truncated = spacewire_stats_grspw.rx_truncated
601 + spacewire_stats.rx_truncated;
602 + spacewire_stats.rx_truncated;
602 }
603 }
603
604
604 void spacewire_update_statistics( void )
605 void spacewire_update_statistics( void )
605 {
606 {
606 rtems_status_code status;
607 rtems_status_code status;
607 spw_stats spacewire_stats_grspw;
608 spw_stats spacewire_stats_grspw;
608
609
609 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_GET_STATISTICS, &spacewire_stats_grspw );
610 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_GET_STATISTICS, &spacewire_stats_grspw );
610
611
611 spacewire_stats.packets_received = spacewire_stats_backup.packets_received
612 spacewire_stats.packets_received = spacewire_stats_backup.packets_received
612 + spacewire_stats_grspw.packets_received;
613 + spacewire_stats_grspw.packets_received;
613 spacewire_stats.packets_sent = spacewire_stats_backup.packets_sent
614 spacewire_stats.packets_sent = spacewire_stats_backup.packets_sent
614 + spacewire_stats_grspw.packets_sent;
615 + spacewire_stats_grspw.packets_sent;
615 spacewire_stats.parity_err = spacewire_stats_backup.parity_err
616 spacewire_stats.parity_err = spacewire_stats_backup.parity_err
616 + spacewire_stats_grspw.parity_err;
617 + spacewire_stats_grspw.parity_err;
617 spacewire_stats.disconnect_err = spacewire_stats_backup.disconnect_err
618 spacewire_stats.disconnect_err = spacewire_stats_backup.disconnect_err
618 + spacewire_stats_grspw.disconnect_err;
619 + spacewire_stats_grspw.disconnect_err;
619 spacewire_stats.escape_err = spacewire_stats_backup.escape_err
620 spacewire_stats.escape_err = spacewire_stats_backup.escape_err
620 + spacewire_stats_grspw.escape_err;
621 + spacewire_stats_grspw.escape_err;
621 spacewire_stats.credit_err = spacewire_stats_backup.credit_err
622 spacewire_stats.credit_err = spacewire_stats_backup.credit_err
622 + spacewire_stats_grspw.credit_err;
623 + spacewire_stats_grspw.credit_err;
623 spacewire_stats.write_sync_err = spacewire_stats_backup.write_sync_err
624 spacewire_stats.write_sync_err = spacewire_stats_backup.write_sync_err
624 + spacewire_stats_grspw.write_sync_err;
625 + spacewire_stats_grspw.write_sync_err;
625 spacewire_stats.rx_rmap_header_crc_err = spacewire_stats_backup.rx_rmap_header_crc_err
626 spacewire_stats.rx_rmap_header_crc_err = spacewire_stats_backup.rx_rmap_header_crc_err
626 + spacewire_stats_grspw.rx_rmap_header_crc_err;
627 + spacewire_stats_grspw.rx_rmap_header_crc_err;
627 spacewire_stats.rx_rmap_data_crc_err = spacewire_stats_backup.rx_rmap_data_crc_err
628 spacewire_stats.rx_rmap_data_crc_err = spacewire_stats_backup.rx_rmap_data_crc_err
628 + spacewire_stats_grspw.rx_rmap_data_crc_err;
629 + spacewire_stats_grspw.rx_rmap_data_crc_err;
629 spacewire_stats.early_ep = spacewire_stats_backup.early_ep
630 spacewire_stats.early_ep = spacewire_stats_backup.early_ep
630 + spacewire_stats_grspw.early_ep;
631 + spacewire_stats_grspw.early_ep;
631 spacewire_stats.invalid_address = spacewire_stats_backup.invalid_address
632 spacewire_stats.invalid_address = spacewire_stats_backup.invalid_address
632 + spacewire_stats_grspw.invalid_address;
633 + spacewire_stats_grspw.invalid_address;
633 spacewire_stats.rx_eep_err = spacewire_stats_backup.rx_eep_err
634 spacewire_stats.rx_eep_err = spacewire_stats_backup.rx_eep_err
634 + spacewire_stats_grspw.rx_eep_err;
635 + spacewire_stats_grspw.rx_eep_err;
635 spacewire_stats.rx_truncated = spacewire_stats_backup.rx_truncated
636 spacewire_stats.rx_truncated = spacewire_stats_backup.rx_truncated
636 + spacewire_stats_grspw.rx_truncated;
637 + spacewire_stats_grspw.rx_truncated;
637 //spacewire_stats.tx_link_err;
638 //spacewire_stats.tx_link_err;
638
639
639 //****************************
640 //****************************
640 // DPU_SPACEWIRE_IF_STATISTICS
641 // DPU_SPACEWIRE_IF_STATISTICS
641 housekeeping_packet.hk_lfr_dpu_spw_pkt_rcv_cnt[0] = (unsigned char) (spacewire_stats.packets_received >> 8);
642 housekeeping_packet.hk_lfr_dpu_spw_pkt_rcv_cnt[0] = (unsigned char) (spacewire_stats.packets_received >> 8);
642 housekeeping_packet.hk_lfr_dpu_spw_pkt_rcv_cnt[1] = (unsigned char) (spacewire_stats.packets_received);
643 housekeeping_packet.hk_lfr_dpu_spw_pkt_rcv_cnt[1] = (unsigned char) (spacewire_stats.packets_received);
643 housekeeping_packet.hk_lfr_dpu_spw_pkt_sent_cnt[0] = (unsigned char) (spacewire_stats.packets_sent >> 8);
644 housekeeping_packet.hk_lfr_dpu_spw_pkt_sent_cnt[0] = (unsigned char) (spacewire_stats.packets_sent >> 8);
644 housekeeping_packet.hk_lfr_dpu_spw_pkt_sent_cnt[1] = (unsigned char) (spacewire_stats.packets_sent);
645 housekeeping_packet.hk_lfr_dpu_spw_pkt_sent_cnt[1] = (unsigned char) (spacewire_stats.packets_sent);
645 //housekeeping_packet.hk_lfr_dpu_spw_tick_out_cnt;
646 //housekeeping_packet.hk_lfr_dpu_spw_tick_out_cnt;
646 //housekeeping_packet.hk_lfr_dpu_spw_last_timc;
647 //housekeeping_packet.hk_lfr_dpu_spw_last_timc;
647
648
648 //******************************************
649 //******************************************
649 // ERROR COUNTERS / SPACEWIRE / LOW SEVERITY
650 // ERROR COUNTERS / SPACEWIRE / LOW SEVERITY
650 housekeeping_packet.hk_lfr_dpu_spw_parity = (unsigned char) spacewire_stats.parity_err;
651 housekeeping_packet.hk_lfr_dpu_spw_parity = (unsigned char) spacewire_stats.parity_err;
651 housekeeping_packet.hk_lfr_dpu_spw_disconnect = (unsigned char) spacewire_stats.disconnect_err;
652 housekeeping_packet.hk_lfr_dpu_spw_disconnect = (unsigned char) spacewire_stats.disconnect_err;
652 housekeeping_packet.hk_lfr_dpu_spw_escape = (unsigned char) spacewire_stats.escape_err;
653 housekeeping_packet.hk_lfr_dpu_spw_escape = (unsigned char) spacewire_stats.escape_err;
653 housekeeping_packet.hk_lfr_dpu_spw_credit = (unsigned char) spacewire_stats.credit_err;
654 housekeeping_packet.hk_lfr_dpu_spw_credit = (unsigned char) spacewire_stats.credit_err;
654 housekeeping_packet.hk_lfr_dpu_spw_write_sync = (unsigned char) spacewire_stats.write_sync_err;
655 housekeeping_packet.hk_lfr_dpu_spw_write_sync = (unsigned char) spacewire_stats.write_sync_err;
655
656
656 //*********************************************
657 //*********************************************
657 // ERROR COUNTERS / SPACEWIRE / MEDIUM SEVERITY
658 // ERROR COUNTERS / SPACEWIRE / MEDIUM SEVERITY
658 housekeeping_packet.hk_lfr_dpu_spw_early_eop = (unsigned char) spacewire_stats.early_ep;
659 housekeeping_packet.hk_lfr_dpu_spw_early_eop = (unsigned char) spacewire_stats.early_ep;
659 housekeeping_packet.hk_lfr_dpu_spw_invalid_addr = (unsigned char) spacewire_stats.invalid_address;
660 housekeeping_packet.hk_lfr_dpu_spw_invalid_addr = (unsigned char) spacewire_stats.invalid_address;
660 housekeeping_packet.hk_lfr_dpu_spw_eep = (unsigned char) spacewire_stats.rx_eep_err;
661 housekeeping_packet.hk_lfr_dpu_spw_eep = (unsigned char) spacewire_stats.rx_eep_err;
661 housekeeping_packet.hk_lfr_dpu_spw_rx_too_big = (unsigned char) spacewire_stats.rx_truncated;
662 housekeeping_packet.hk_lfr_dpu_spw_rx_too_big = (unsigned char) spacewire_stats.rx_truncated;
662 }
663 }
663
664
664 void increase_unsigned_char_counter( unsigned char *counter )
665 void increase_unsigned_char_counter( unsigned char *counter )
665 {
666 {
666 // update the number of valid timecodes that have been received
667 // update the number of valid timecodes that have been received
667 if (*counter == 255)
668 if (*counter == 255)
668 {
669 {
669 *counter = 0;
670 *counter = 0;
670 }
671 }
671 else
672 else
672 {
673 {
673 *counter = *counter + 1;
674 *counter = *counter + 1;
674 }
675 }
675 }
676 }
676
677
677 rtems_timer_service_routine timecode_timer_routine( rtems_id timer_id, void *user_data )
678 rtems_timer_service_routine timecode_timer_routine( rtems_id timer_id, void *user_data )
678 {
679 {
679
680
680 unsigned char currentTimecodeCtr;
681 unsigned char currentTimecodeCtr;
681
682
682 currentTimecodeCtr = (unsigned char) (grspwPtr[0] & TIMECODE_MASK);
683 currentTimecodeCtr = (unsigned char) (grspwPtr[0] & TIMECODE_MASK);
683
684
684 if (currentTimecodeCtr == previousTimecodeCtr)
685 if (currentTimecodeCtr == previousTimecodeCtr)
685 {
686 {
686 //************************
687 //************************
687 // HK_LFR_TIMECODE_MISSING
688 // HK_LFR_TIMECODE_MISSING
688 // the timecode value has not changed, no valid timecode has been received, the timecode is MISSING
689 // the timecode value has not changed, no valid timecode has been received, the timecode is MISSING
689 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_timecode_missing );
690 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_timecode_missing );
690 }
691 }
691 else if (currentTimecodeCtr == (previousTimecodeCtr+1))
692 else if (currentTimecodeCtr == (previousTimecodeCtr+1))
692 {
693 {
693 // the timecode value has changed and the value is valid, this is unexpected because
694 // the timecode value has changed and the value is valid, this is unexpected because
694 // the timer should not have fired, the timecode_irq_handler should have been raised
695 // the timer should not have fired, the timecode_irq_handler should have been raised
695 }
696 }
696 else
697 else
697 {
698 {
698 //************************
699 //************************
699 // HK_LFR_TIMECODE_INVALID
700 // HK_LFR_TIMECODE_INVALID
700 // the timecode value has changed and the value is not valid, no tickout has been generated
701 // the timecode value has changed and the value is not valid, no tickout has been generated
701 // this is why the timer has fired
702 // this is why the timer has fired
702 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_timecode_invalid );
703 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_timecode_invalid );
703 }
704 }
704
705
705 rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_13 );
706 rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_13 );
706 }
707 }
707
708
708 unsigned int check_timecode_and_previous_timecode_coherency(unsigned char currentTimecodeCtr)
709 unsigned int check_timecode_and_previous_timecode_coherency(unsigned char currentTimecodeCtr)
709 {
710 {
710 /** This function checks the coherency between the incoming timecode and the last valid timecode.
711 /** This function checks the coherency between the incoming timecode and the last valid timecode.
711 *
712 *
712 * @param currentTimecodeCtr is the incoming timecode
713 * @param currentTimecodeCtr is the incoming timecode
713 *
714 *
714 * @return returned codes::
715 * @return returned codes::
715 * - LFR_DEFAULT
716 * - LFR_DEFAULT
716 * - LFR_SUCCESSFUL
717 * - LFR_SUCCESSFUL
717 *
718 *
718 */
719 */
719
720
720 static unsigned char firstTickout = 1;
721 static unsigned char firstTickout = 1;
721 unsigned char ret;
722 unsigned char ret;
722
723
723 ret = LFR_DEFAULT;
724 ret = LFR_DEFAULT;
724
725
725 if (firstTickout == 0)
726 if (firstTickout == 0)
726 {
727 {
727 if (currentTimecodeCtr == 0)
728 if (currentTimecodeCtr == 0)
728 {
729 {
729 if (previousTimecodeCtr == 63)
730 if (previousTimecodeCtr == 63)
730 {
731 {
731 ret = LFR_SUCCESSFUL;
732 ret = LFR_SUCCESSFUL;
732 }
733 }
733 else
734 else
734 {
735 {
735 ret = LFR_DEFAULT;
736 ret = LFR_DEFAULT;
736 }
737 }
737 }
738 }
738 else
739 else
739 {
740 {
740 if (currentTimecodeCtr == (previousTimecodeCtr +1))
741 if (currentTimecodeCtr == (previousTimecodeCtr +1))
741 {
742 {
742 ret = LFR_SUCCESSFUL;
743 ret = LFR_SUCCESSFUL;
743 }
744 }
744 else
745 else
745 {
746 {
746 ret = LFR_DEFAULT;
747 ret = LFR_DEFAULT;
747 }
748 }
748 }
749 }
749 }
750 }
750 else
751 else
751 {
752 {
752 firstTickout = 0;
753 firstTickout = 0;
753 ret = LFR_SUCCESSFUL;
754 ret = LFR_SUCCESSFUL;
754 }
755 }
755
756
756 return ret;
757 return ret;
757 }
758 }
758
759
759 unsigned int check_timecode_and_internal_time_coherency(unsigned char timecode, unsigned char internalTime)
760 unsigned int check_timecode_and_internal_time_coherency(unsigned char timecode, unsigned char internalTime)
760 {
761 {
761 unsigned int ret;
762 unsigned int ret;
762
763
763 ret = LFR_DEFAULT;
764 ret = LFR_DEFAULT;
764
765
765 if (timecode == internalTime)
766 if (timecode == internalTime)
766 {
767 {
767 ret = LFR_SUCCESSFUL;
768 ret = LFR_SUCCESSFUL;
768 }
769 }
769 else
770 else
770 {
771 {
771 ret = LFR_DEFAULT;
772 ret = LFR_DEFAULT;
772 }
773 }
773
774
774 return ret;
775 return ret;
775 }
776 }
776
777
777 void timecode_irq_handler( void *pDev, void *regs, int minor, unsigned int tc )
778 void timecode_irq_handler( void *pDev, void *regs, int minor, unsigned int tc )
778 {
779 {
779 // a tickout has been emitted, perform actions on the incoming timecode
780 // a tickout has been emitted, perform actions on the incoming timecode
780
781
781 unsigned char incomingTimecode;
782 unsigned char incomingTimecode;
782 unsigned char updateTime;
783 unsigned char updateTime;
783 unsigned char internalTime;
784 unsigned char internalTime;
784 rtems_status_code status;
785 rtems_status_code status;
785
786
786 incomingTimecode = (unsigned char) (grspwPtr[0] & TIMECODE_MASK);
787 incomingTimecode = (unsigned char) (grspwPtr[0] & TIMECODE_MASK);
787 updateTime = time_management_regs->coarse_time_load & TIMECODE_MASK;
788 updateTime = time_management_regs->coarse_time_load & TIMECODE_MASK;
788 internalTime = time_management_regs->coarse_time & TIMECODE_MASK;
789 internalTime = time_management_regs->coarse_time & TIMECODE_MASK;
789
790
790 housekeeping_packet.hk_lfr_dpu_spw_last_timc = incomingTimecode;
791 housekeeping_packet.hk_lfr_dpu_spw_last_timc = incomingTimecode;
791
792
792 // update the number of tickout that have been generated
793 // update the number of tickout that have been generated
793 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_dpu_spw_tick_out_cnt );
794 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_dpu_spw_tick_out_cnt );
794
795
795 //**************************
796 //**************************
796 // HK_LFR_TIMECODE_ERRONEOUS
797 // HK_LFR_TIMECODE_ERRONEOUS
797 // MISSING and INVALID are handled by the timecode_timer_routine service routine
798 // MISSING and INVALID are handled by the timecode_timer_routine service routine
798 if (check_timecode_and_previous_timecode_coherency( incomingTimecode ) == LFR_DEFAULT)
799 if (check_timecode_and_previous_timecode_coherency( incomingTimecode ) == LFR_DEFAULT)
799 {
800 {
800 // this is unexpected but a tickout could have been raised despite of the timecode being erroneous
801 // this is unexpected but a tickout could have been raised despite of the timecode being erroneous
801 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_timecode_erroneous );
802 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_timecode_erroneous );
802 }
803 }
803
804
804 //************************
805 //************************
805 // HK_LFR_TIME_TIMECODE_IT
806 // HK_LFR_TIME_TIMECODE_IT
806 // check the coherency between the SpaceWire timecode and the Internal Time
807 // check the coherency between the SpaceWire timecode and the Internal Time
807 if (check_timecode_and_internal_time_coherency( incomingTimecode, internalTime ) == LFR_DEFAULT)
808 if (check_timecode_and_internal_time_coherency( incomingTimecode, internalTime ) == LFR_DEFAULT)
808 {
809 {
809 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_time_timecode_it );
810 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_time_timecode_it );
810 }
811 }
811
812
812 //********************
813 //********************
813 // HK_LFR_TIMECODE_CTR
814 // HK_LFR_TIMECODE_CTR
814 // check the value of the timecode with respect to the last TC_LFR_UPDATE_TIME => SSS-CP-FS-370
815 // check the value of the timecode with respect to the last TC_LFR_UPDATE_TIME => SSS-CP-FS-370
815 if (incomingTimecode != updateTime)
816 if (incomingTimecode != updateTime)
816 {
817 {
817 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_time_timecode_ctr );
818 increase_unsigned_char_counter( &housekeeping_packet.hk_lfr_time_timecode_ctr );
818 }
819 }
819
820
820 // launch the timecode timer to detect missing or invalid timecodes
821 // launch the timecode timer to detect missing or invalid timecodes
821 previousTimecodeCtr = incomingTimecode; // update the previousTimecodeCtr value
822 previousTimecodeCtr = incomingTimecode; // update the previousTimecodeCtr value
822 status = rtems_timer_fire_after( timecode_timer_id, TIMECODE_TIMER_TIMEOUT, timecode_timer_routine, NULL );
823 status = rtems_timer_fire_after( timecode_timer_id, TIMECODE_TIMER_TIMEOUT, timecode_timer_routine, NULL );
823 }
824 }
824
825
825 void init_header_cwf( Header_TM_LFR_SCIENCE_CWF_t *header )
826 void init_header_cwf( Header_TM_LFR_SCIENCE_CWF_t *header )
826 {
827 {
827 header->targetLogicalAddress = CCSDS_DESTINATION_ID;
828 header->targetLogicalAddress = CCSDS_DESTINATION_ID;
828 header->protocolIdentifier = CCSDS_PROTOCOLE_ID;
829 header->protocolIdentifier = CCSDS_PROTOCOLE_ID;
829 header->reserved = DEFAULT_RESERVED;
830 header->reserved = DEFAULT_RESERVED;
830 header->userApplication = CCSDS_USER_APP;
831 header->userApplication = CCSDS_USER_APP;
831 header->packetSequenceControl[0]= TM_PACKET_SEQ_CTRL_STANDALONE;
832 header->packetSequenceControl[0]= TM_PACKET_SEQ_CTRL_STANDALONE;
832 header->packetSequenceControl[1]= TM_PACKET_SEQ_CNT_DEFAULT;
833 header->packetSequenceControl[1]= TM_PACKET_SEQ_CNT_DEFAULT;
833 header->packetLength[0] = 0x00;
834 header->packetLength[0] = 0x00;
834 header->packetLength[1] = 0x00;
835 header->packetLength[1] = 0x00;
835 // DATA FIELD HEADER
836 // DATA FIELD HEADER
836 header->spare1_pusVersion_spare2 = DEFAULT_SPARE1_PUSVERSION_SPARE2;
837 header->spare1_pusVersion_spare2 = DEFAULT_SPARE1_PUSVERSION_SPARE2;
837 header->serviceType = TM_TYPE_LFR_SCIENCE; // service type
838 header->serviceType = TM_TYPE_LFR_SCIENCE; // service type
838 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6; // service subtype
839 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6; // service subtype
839 header->destinationID = TM_DESTINATION_ID_GROUND;
840 header->destinationID = TM_DESTINATION_ID_GROUND;
840 header->time[0] = 0x00;
841 header->time[0] = 0x00;
841 header->time[0] = 0x00;
842 header->time[0] = 0x00;
842 header->time[0] = 0x00;
843 header->time[0] = 0x00;
843 header->time[0] = 0x00;
844 header->time[0] = 0x00;
844 header->time[0] = 0x00;
845 header->time[0] = 0x00;
845 header->time[0] = 0x00;
846 header->time[0] = 0x00;
846 // AUXILIARY DATA HEADER
847 // AUXILIARY DATA HEADER
847 header->sid = 0x00;
848 header->sid = 0x00;
848 header->hkBIA = DEFAULT_HKBIA;
849 header->hkBIA = DEFAULT_HKBIA;
849 header->blkNr[0] = 0x00;
850 header->blkNr[0] = 0x00;
850 header->blkNr[1] = 0x00;
851 header->blkNr[1] = 0x00;
851 }
852 }
852
853
853 void init_header_swf( Header_TM_LFR_SCIENCE_SWF_t *header )
854 void init_header_swf( Header_TM_LFR_SCIENCE_SWF_t *header )
854 {
855 {
855 header->targetLogicalAddress = CCSDS_DESTINATION_ID;
856 header->targetLogicalAddress = CCSDS_DESTINATION_ID;
856 header->protocolIdentifier = CCSDS_PROTOCOLE_ID;
857 header->protocolIdentifier = CCSDS_PROTOCOLE_ID;
857 header->reserved = DEFAULT_RESERVED;
858 header->reserved = DEFAULT_RESERVED;
858 header->userApplication = CCSDS_USER_APP;
859 header->userApplication = CCSDS_USER_APP;
859 header->packetID[0] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST >> 8);
860 header->packetID[0] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST >> 8);
860 header->packetID[1] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST);
861 header->packetID[1] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST);
861 header->packetSequenceControl[0] = TM_PACKET_SEQ_CTRL_STANDALONE;
862 header->packetSequenceControl[0] = TM_PACKET_SEQ_CTRL_STANDALONE;
862 header->packetSequenceControl[1] = TM_PACKET_SEQ_CNT_DEFAULT;
863 header->packetSequenceControl[1] = TM_PACKET_SEQ_CNT_DEFAULT;
863 header->packetLength[0] = (unsigned char) (TM_LEN_SCI_CWF_336 >> 8);
864 header->packetLength[0] = (unsigned char) (TM_LEN_SCI_CWF_336 >> 8);
864 header->packetLength[1] = (unsigned char) (TM_LEN_SCI_CWF_336 );
865 header->packetLength[1] = (unsigned char) (TM_LEN_SCI_CWF_336 );
865 // DATA FIELD HEADER
866 // DATA FIELD HEADER
866 header->spare1_pusVersion_spare2 = DEFAULT_SPARE1_PUSVERSION_SPARE2;
867 header->spare1_pusVersion_spare2 = DEFAULT_SPARE1_PUSVERSION_SPARE2;
867 header->serviceType = TM_TYPE_LFR_SCIENCE; // service type
868 header->serviceType = TM_TYPE_LFR_SCIENCE; // service type
868 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6; // service subtype
869 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6; // service subtype
869 header->destinationID = TM_DESTINATION_ID_GROUND;
870 header->destinationID = TM_DESTINATION_ID_GROUND;
870 header->time[0] = 0x00;
871 header->time[0] = 0x00;
871 header->time[0] = 0x00;
872 header->time[0] = 0x00;
872 header->time[0] = 0x00;
873 header->time[0] = 0x00;
873 header->time[0] = 0x00;
874 header->time[0] = 0x00;
874 header->time[0] = 0x00;
875 header->time[0] = 0x00;
875 header->time[0] = 0x00;
876 header->time[0] = 0x00;
876 // AUXILIARY DATA HEADER
877 // AUXILIARY DATA HEADER
877 header->sid = 0x00;
878 header->sid = 0x00;
878 header->hkBIA = DEFAULT_HKBIA;
879 header->hkBIA = DEFAULT_HKBIA;
879 header->pktCnt = DEFAULT_PKTCNT; // PKT_CNT
880 header->pktCnt = DEFAULT_PKTCNT; // PKT_CNT
880 header->pktNr = 0x00;
881 header->pktNr = 0x00;
881 header->blkNr[0] = (unsigned char) (BLK_NR_CWF >> 8);
882 header->blkNr[0] = (unsigned char) (BLK_NR_CWF >> 8);
882 header->blkNr[1] = (unsigned char) (BLK_NR_CWF );
883 header->blkNr[1] = (unsigned char) (BLK_NR_CWF );
883 }
884 }
884
885
885 void init_header_asm( Header_TM_LFR_SCIENCE_ASM_t *header )
886 void init_header_asm( Header_TM_LFR_SCIENCE_ASM_t *header )
886 {
887 {
887 header->targetLogicalAddress = CCSDS_DESTINATION_ID;
888 header->targetLogicalAddress = CCSDS_DESTINATION_ID;
888 header->protocolIdentifier = CCSDS_PROTOCOLE_ID;
889 header->protocolIdentifier = CCSDS_PROTOCOLE_ID;
889 header->reserved = DEFAULT_RESERVED;
890 header->reserved = DEFAULT_RESERVED;
890 header->userApplication = CCSDS_USER_APP;
891 header->userApplication = CCSDS_USER_APP;
891 header->packetID[0] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST >> 8);
892 header->packetID[0] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST >> 8);
892 header->packetID[1] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST);
893 header->packetID[1] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST);
893 header->packetSequenceControl[0] = TM_PACKET_SEQ_CTRL_STANDALONE;
894 header->packetSequenceControl[0] = TM_PACKET_SEQ_CTRL_STANDALONE;
894 header->packetSequenceControl[1] = TM_PACKET_SEQ_CNT_DEFAULT;
895 header->packetSequenceControl[1] = TM_PACKET_SEQ_CNT_DEFAULT;
895 header->packetLength[0] = 0x00;
896 header->packetLength[0] = 0x00;
896 header->packetLength[1] = 0x00;
897 header->packetLength[1] = 0x00;
897 // DATA FIELD HEADER
898 // DATA FIELD HEADER
898 header->spare1_pusVersion_spare2 = DEFAULT_SPARE1_PUSVERSION_SPARE2;
899 header->spare1_pusVersion_spare2 = DEFAULT_SPARE1_PUSVERSION_SPARE2;
899 header->serviceType = TM_TYPE_LFR_SCIENCE; // service type
900 header->serviceType = TM_TYPE_LFR_SCIENCE; // service type
900 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_3; // service subtype
901 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_3; // service subtype
901 header->destinationID = TM_DESTINATION_ID_GROUND;
902 header->destinationID = TM_DESTINATION_ID_GROUND;
902 header->time[0] = 0x00;
903 header->time[0] = 0x00;
903 header->time[0] = 0x00;
904 header->time[0] = 0x00;
904 header->time[0] = 0x00;
905 header->time[0] = 0x00;
905 header->time[0] = 0x00;
906 header->time[0] = 0x00;
906 header->time[0] = 0x00;
907 header->time[0] = 0x00;
907 header->time[0] = 0x00;
908 header->time[0] = 0x00;
908 // AUXILIARY DATA HEADER
909 // AUXILIARY DATA HEADER
909 header->sid = 0x00;
910 header->sid = 0x00;
910 header->biaStatusInfo = 0x00;
911 header->biaStatusInfo = 0x00;
911 header->pa_lfr_pkt_cnt_asm = 0x00;
912 header->pa_lfr_pkt_cnt_asm = 0x00;
912 header->pa_lfr_pkt_nr_asm = 0x00;
913 header->pa_lfr_pkt_nr_asm = 0x00;
913 header->pa_lfr_asm_blk_nr[0] = 0x00;
914 header->pa_lfr_asm_blk_nr[0] = 0x00;
914 header->pa_lfr_asm_blk_nr[1] = 0x00;
915 header->pa_lfr_asm_blk_nr[1] = 0x00;
915 }
916 }
916
917
917 int spw_send_waveform_CWF( ring_node *ring_node_to_send,
918 int spw_send_waveform_CWF( ring_node *ring_node_to_send,
918 Header_TM_LFR_SCIENCE_CWF_t *header )
919 Header_TM_LFR_SCIENCE_CWF_t *header )
919 {
920 {
920 /** This function sends CWF CCSDS packets (F2, F1 or F0).
921 /** This function sends CWF CCSDS packets (F2, F1 or F0).
921 *
922 *
922 * @param waveform points to the buffer containing the data that will be send.
923 * @param waveform points to the buffer containing the data that will be send.
923 * @param sid is the source identifier of the data that will be sent.
924 * @param sid is the source identifier of the data that will be sent.
924 * @param headerCWF points to a table of headers that have been prepared for the data transmission.
925 * @param headerCWF points to a table of headers that have been prepared for the data transmission.
925 * @param queue_id is the id of the rtems queue to which spw_ioctl_pkt_send structures will be send. The structures
926 * @param queue_id is the id of the rtems queue to which spw_ioctl_pkt_send structures will be send. The structures
926 * contain information to setup the transmission of the data packets.
927 * contain information to setup the transmission of the data packets.
927 *
928 *
928 * One group of 2048 samples is sent as 7 consecutive packets, 6 packets containing 340 blocks and 8 packets containing 8 blocks.
929 * One group of 2048 samples is sent as 7 consecutive packets, 6 packets containing 340 blocks and 8 packets containing 8 blocks.
929 *
930 *
930 */
931 */
931
932
932 unsigned int i;
933 unsigned int i;
933 int ret;
934 int ret;
934 unsigned int coarseTime;
935 unsigned int coarseTime;
935 unsigned int fineTime;
936 unsigned int fineTime;
936 rtems_status_code status;
937 rtems_status_code status;
937 spw_ioctl_pkt_send spw_ioctl_send_CWF;
938 spw_ioctl_pkt_send spw_ioctl_send_CWF;
938 int *dataPtr;
939 int *dataPtr;
939 unsigned char sid;
940 unsigned char sid;
940
941
941 spw_ioctl_send_CWF.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_CWF;
942 spw_ioctl_send_CWF.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_CWF;
942 spw_ioctl_send_CWF.options = 0;
943 spw_ioctl_send_CWF.options = 0;
943
944
944 ret = LFR_DEFAULT;
945 ret = LFR_DEFAULT;
945 sid = (unsigned char) ring_node_to_send->sid;
946 sid = (unsigned char) ring_node_to_send->sid;
946
947
947 coarseTime = ring_node_to_send->coarseTime;
948 coarseTime = ring_node_to_send->coarseTime;
948 fineTime = ring_node_to_send->fineTime;
949 fineTime = ring_node_to_send->fineTime;
949 dataPtr = (int*) ring_node_to_send->buffer_address;
950 dataPtr = (int*) ring_node_to_send->buffer_address;
950
951
951 header->packetLength[0] = (unsigned char) (TM_LEN_SCI_CWF_336 >> 8);
952 header->packetLength[0] = (unsigned char) (TM_LEN_SCI_CWF_336 >> 8);
952 header->packetLength[1] = (unsigned char) (TM_LEN_SCI_CWF_336 );
953 header->packetLength[1] = (unsigned char) (TM_LEN_SCI_CWF_336 );
953 header->hkBIA = pa_bia_status_info;
954 header->hkBIA = pa_bia_status_info;
954 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
955 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
955 header->blkNr[0] = (unsigned char) (BLK_NR_CWF >> 8);
956 header->blkNr[0] = (unsigned char) (BLK_NR_CWF >> 8);
956 header->blkNr[1] = (unsigned char) (BLK_NR_CWF );
957 header->blkNr[1] = (unsigned char) (BLK_NR_CWF );
957
958
958 for (i=0; i<NB_PACKETS_PER_GROUP_OF_CWF; i++) // send waveform
959 for (i=0; i<NB_PACKETS_PER_GROUP_OF_CWF; i++) // send waveform
959 {
960 {
960 spw_ioctl_send_CWF.data = (char*) &dataPtr[ (i * BLK_NR_CWF * NB_WORDS_SWF_BLK) ];
961 spw_ioctl_send_CWF.data = (char*) &dataPtr[ (i * BLK_NR_CWF * NB_WORDS_SWF_BLK) ];
961 spw_ioctl_send_CWF.hdr = (char*) header;
962 spw_ioctl_send_CWF.hdr = (char*) header;
962 // BUILD THE DATA
963 // BUILD THE DATA
963 spw_ioctl_send_CWF.dlen = BLK_NR_CWF * NB_BYTES_SWF_BLK;
964 spw_ioctl_send_CWF.dlen = BLK_NR_CWF * NB_BYTES_SWF_BLK;
964
965
965 // SET PACKET SEQUENCE CONTROL
966 // SET PACKET SEQUENCE CONTROL
966 increment_seq_counter_source_id( header->packetSequenceControl, sid );
967 increment_seq_counter_source_id( header->packetSequenceControl, sid );
967
968
968 // SET SID
969 // SET SID
969 header->sid = sid;
970 header->sid = sid;
970
971
971 // SET PACKET TIME
972 // SET PACKET TIME
972 compute_acquisition_time( coarseTime, fineTime, sid, i, header->acquisitionTime);
973 compute_acquisition_time( coarseTime, fineTime, sid, i, header->acquisitionTime);
973 //
974 //
974 header->time[0] = header->acquisitionTime[0];
975 header->time[0] = header->acquisitionTime[0];
975 header->time[1] = header->acquisitionTime[1];
976 header->time[1] = header->acquisitionTime[1];
976 header->time[2] = header->acquisitionTime[2];
977 header->time[2] = header->acquisitionTime[2];
977 header->time[3] = header->acquisitionTime[3];
978 header->time[3] = header->acquisitionTime[3];
978 header->time[4] = header->acquisitionTime[4];
979 header->time[4] = header->acquisitionTime[4];
979 header->time[5] = header->acquisitionTime[5];
980 header->time[5] = header->acquisitionTime[5];
980
981
981 // SET PACKET ID
982 // SET PACKET ID
982 if ( (sid == SID_SBM1_CWF_F1) || (sid == SID_SBM2_CWF_F2) )
983 if ( (sid == SID_SBM1_CWF_F1) || (sid == SID_SBM2_CWF_F2) )
983 {
984 {
984 header->packetID[0] = (unsigned char) (APID_TM_SCIENCE_SBM1_SBM2 >> 8);
985 header->packetID[0] = (unsigned char) (APID_TM_SCIENCE_SBM1_SBM2 >> 8);
985 header->packetID[1] = (unsigned char) (APID_TM_SCIENCE_SBM1_SBM2);
986 header->packetID[1] = (unsigned char) (APID_TM_SCIENCE_SBM1_SBM2);
986 }
987 }
987 else
988 else
988 {
989 {
989 header->packetID[0] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST >> 8);
990 header->packetID[0] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST >> 8);
990 header->packetID[1] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST);
991 header->packetID[1] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST);
991 }
992 }
992
993
993 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_CWF );
994 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_CWF );
994 if (status != RTEMS_SUCCESSFUL) {
995 if (status != RTEMS_SUCCESSFUL) {
995 ret = LFR_DEFAULT;
996 ret = LFR_DEFAULT;
996 }
997 }
997 }
998 }
998
999
999 return ret;
1000 return ret;
1000 }
1001 }
1001
1002
1002 int spw_send_waveform_SWF( ring_node *ring_node_to_send,
1003 int spw_send_waveform_SWF( ring_node *ring_node_to_send,
1003 Header_TM_LFR_SCIENCE_SWF_t *header )
1004 Header_TM_LFR_SCIENCE_SWF_t *header )
1004 {
1005 {
1005 /** This function sends SWF CCSDS packets (F2, F1 or F0).
1006 /** This function sends SWF CCSDS packets (F2, F1 or F0).
1006 *
1007 *
1007 * @param waveform points to the buffer containing the data that will be send.
1008 * @param waveform points to the buffer containing the data that will be send.
1008 * @param sid is the source identifier of the data that will be sent.
1009 * @param sid is the source identifier of the data that will be sent.
1009 * @param headerSWF points to a table of headers that have been prepared for the data transmission.
1010 * @param headerSWF points to a table of headers that have been prepared for the data transmission.
1010 * @param queue_id is the id of the rtems queue to which spw_ioctl_pkt_send structures will be send. The structures
1011 * @param queue_id is the id of the rtems queue to which spw_ioctl_pkt_send structures will be send. The structures
1011 * contain information to setup the transmission of the data packets.
1012 * contain information to setup the transmission of the data packets.
1012 *
1013 *
1013 * One group of 2048 samples is sent as 7 consecutive packets, 6 packets containing 340 blocks and 8 packets containing 8 blocks.
1014 * One group of 2048 samples is sent as 7 consecutive packets, 6 packets containing 340 blocks and 8 packets containing 8 blocks.
1014 *
1015 *
1015 */
1016 */
1016
1017
1017 unsigned int i;
1018 unsigned int i;
1018 int ret;
1019 int ret;
1019 unsigned int coarseTime;
1020 unsigned int coarseTime;
1020 unsigned int fineTime;
1021 unsigned int fineTime;
1021 rtems_status_code status;
1022 rtems_status_code status;
1022 spw_ioctl_pkt_send spw_ioctl_send_SWF;
1023 spw_ioctl_pkt_send spw_ioctl_send_SWF;
1023 int *dataPtr;
1024 int *dataPtr;
1024 unsigned char sid;
1025 unsigned char sid;
1025
1026
1026 spw_ioctl_send_SWF.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_SWF;
1027 spw_ioctl_send_SWF.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_SWF;
1027 spw_ioctl_send_SWF.options = 0;
1028 spw_ioctl_send_SWF.options = 0;
1028
1029
1029 ret = LFR_DEFAULT;
1030 ret = LFR_DEFAULT;
1030
1031
1031 coarseTime = ring_node_to_send->coarseTime;
1032 coarseTime = ring_node_to_send->coarseTime;
1032 fineTime = ring_node_to_send->fineTime;
1033 fineTime = ring_node_to_send->fineTime;
1033 dataPtr = (int*) ring_node_to_send->buffer_address;
1034 dataPtr = (int*) ring_node_to_send->buffer_address;
1034 sid = ring_node_to_send->sid;
1035 sid = ring_node_to_send->sid;
1035
1036
1036 header->hkBIA = pa_bia_status_info;
1037 header->hkBIA = pa_bia_status_info;
1037 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
1038 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
1038
1039
1039 for (i=0; i<7; i++) // send waveform
1040 for (i=0; i<7; i++) // send waveform
1040 {
1041 {
1041 spw_ioctl_send_SWF.data = (char*) &dataPtr[ (i * BLK_NR_304 * NB_WORDS_SWF_BLK) ];
1042 spw_ioctl_send_SWF.data = (char*) &dataPtr[ (i * BLK_NR_304 * NB_WORDS_SWF_BLK) ];
1042 spw_ioctl_send_SWF.hdr = (char*) header;
1043 spw_ioctl_send_SWF.hdr = (char*) header;
1043
1044
1044 // SET PACKET SEQUENCE CONTROL
1045 // SET PACKET SEQUENCE CONTROL
1045 increment_seq_counter_source_id( header->packetSequenceControl, sid );
1046 increment_seq_counter_source_id( header->packetSequenceControl, sid );
1046
1047
1047 // SET PACKET LENGTH AND BLKNR
1048 // SET PACKET LENGTH AND BLKNR
1048 if (i == 6)
1049 if (i == 6)
1049 {
1050 {
1050 spw_ioctl_send_SWF.dlen = BLK_NR_224 * NB_BYTES_SWF_BLK;
1051 spw_ioctl_send_SWF.dlen = BLK_NR_224 * NB_BYTES_SWF_BLK;
1051 header->packetLength[0] = (unsigned char) (TM_LEN_SCI_SWF_224 >> 8);
1052 header->packetLength[0] = (unsigned char) (TM_LEN_SCI_SWF_224 >> 8);
1052 header->packetLength[1] = (unsigned char) (TM_LEN_SCI_SWF_224 );
1053 header->packetLength[1] = (unsigned char) (TM_LEN_SCI_SWF_224 );
1053 header->blkNr[0] = (unsigned char) (BLK_NR_224 >> 8);
1054 header->blkNr[0] = (unsigned char) (BLK_NR_224 >> 8);
1054 header->blkNr[1] = (unsigned char) (BLK_NR_224 );
1055 header->blkNr[1] = (unsigned char) (BLK_NR_224 );
1055 }
1056 }
1056 else
1057 else
1057 {
1058 {
1058 spw_ioctl_send_SWF.dlen = BLK_NR_304 * NB_BYTES_SWF_BLK;
1059 spw_ioctl_send_SWF.dlen = BLK_NR_304 * NB_BYTES_SWF_BLK;
1059 header->packetLength[0] = (unsigned char) (TM_LEN_SCI_SWF_304 >> 8);
1060 header->packetLength[0] = (unsigned char) (TM_LEN_SCI_SWF_304 >> 8);
1060 header->packetLength[1] = (unsigned char) (TM_LEN_SCI_SWF_304 );
1061 header->packetLength[1] = (unsigned char) (TM_LEN_SCI_SWF_304 );
1061 header->blkNr[0] = (unsigned char) (BLK_NR_304 >> 8);
1062 header->blkNr[0] = (unsigned char) (BLK_NR_304 >> 8);
1062 header->blkNr[1] = (unsigned char) (BLK_NR_304 );
1063 header->blkNr[1] = (unsigned char) (BLK_NR_304 );
1063 }
1064 }
1064
1065
1065 // SET PACKET TIME
1066 // SET PACKET TIME
1066 compute_acquisition_time( coarseTime, fineTime, sid, i, header->acquisitionTime );
1067 compute_acquisition_time( coarseTime, fineTime, sid, i, header->acquisitionTime );
1067 //
1068 //
1068 header->time[0] = header->acquisitionTime[0];
1069 header->time[0] = header->acquisitionTime[0];
1069 header->time[1] = header->acquisitionTime[1];
1070 header->time[1] = header->acquisitionTime[1];
1070 header->time[2] = header->acquisitionTime[2];
1071 header->time[2] = header->acquisitionTime[2];
1071 header->time[3] = header->acquisitionTime[3];
1072 header->time[3] = header->acquisitionTime[3];
1072 header->time[4] = header->acquisitionTime[4];
1073 header->time[4] = header->acquisitionTime[4];
1073 header->time[5] = header->acquisitionTime[5];
1074 header->time[5] = header->acquisitionTime[5];
1074
1075
1075 // SET SID
1076 // SET SID
1076 header->sid = sid;
1077 header->sid = sid;
1077
1078
1078 // SET PKTNR
1079 // SET PKTNR
1079 header->pktNr = i+1; // PKT_NR
1080 header->pktNr = i+1; // PKT_NR
1080
1081
1081 // SEND PACKET
1082 // SEND PACKET
1082 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_SWF );
1083 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_SWF );
1083 if (status != RTEMS_SUCCESSFUL) {
1084 if (status != RTEMS_SUCCESSFUL) {
1084 ret = LFR_DEFAULT;
1085 ret = LFR_DEFAULT;
1085 }
1086 }
1086 }
1087 }
1087
1088
1088 return ret;
1089 return ret;
1089 }
1090 }
1090
1091
1091 int spw_send_waveform_CWF3_light( ring_node *ring_node_to_send,
1092 int spw_send_waveform_CWF3_light( ring_node *ring_node_to_send,
1092 Header_TM_LFR_SCIENCE_CWF_t *header )
1093 Header_TM_LFR_SCIENCE_CWF_t *header )
1093 {
1094 {
1094 /** This function sends CWF_F3 CCSDS packets without the b1, b2 and b3 data.
1095 /** This function sends CWF_F3 CCSDS packets without the b1, b2 and b3 data.
1095 *
1096 *
1096 * @param waveform points to the buffer containing the data that will be send.
1097 * @param waveform points to the buffer containing the data that will be send.
1097 * @param headerCWF points to a table of headers that have been prepared for the data transmission.
1098 * @param headerCWF points to a table of headers that have been prepared for the data transmission.
1098 * @param queue_id is the id of the rtems queue to which spw_ioctl_pkt_send structures will be send. The structures
1099 * @param queue_id is the id of the rtems queue to which spw_ioctl_pkt_send structures will be send. The structures
1099 * contain information to setup the transmission of the data packets.
1100 * contain information to setup the transmission of the data packets.
1100 *
1101 *
1101 * By default, CWF_F3 packet are send without the b1, b2 and b3 data. This function rebuilds a data buffer
1102 * By default, CWF_F3 packet are send without the b1, b2 and b3 data. This function rebuilds a data buffer
1102 * from the incoming data and sends it in 7 packets, 6 containing 340 blocks and 1 one containing 8 blocks.
1103 * from the incoming data and sends it in 7 packets, 6 containing 340 blocks and 1 one containing 8 blocks.
1103 *
1104 *
1104 */
1105 */
1105
1106
1106 unsigned int i;
1107 unsigned int i;
1107 int ret;
1108 int ret;
1108 unsigned int coarseTime;
1109 unsigned int coarseTime;
1109 unsigned int fineTime;
1110 unsigned int fineTime;
1110 rtems_status_code status;
1111 rtems_status_code status;
1111 spw_ioctl_pkt_send spw_ioctl_send_CWF;
1112 spw_ioctl_pkt_send spw_ioctl_send_CWF;
1112 char *dataPtr;
1113 char *dataPtr;
1113 unsigned char sid;
1114 unsigned char sid;
1114
1115
1115 spw_ioctl_send_CWF.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_CWF;
1116 spw_ioctl_send_CWF.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_CWF;
1116 spw_ioctl_send_CWF.options = 0;
1117 spw_ioctl_send_CWF.options = 0;
1117
1118
1118 ret = LFR_DEFAULT;
1119 ret = LFR_DEFAULT;
1119 sid = ring_node_to_send->sid;
1120 sid = ring_node_to_send->sid;
1120
1121
1121 coarseTime = ring_node_to_send->coarseTime;
1122 coarseTime = ring_node_to_send->coarseTime;
1122 fineTime = ring_node_to_send->fineTime;
1123 fineTime = ring_node_to_send->fineTime;
1123 dataPtr = (char*) ring_node_to_send->buffer_address;
1124 dataPtr = (char*) ring_node_to_send->buffer_address;
1124
1125
1125 header->packetLength[0] = (unsigned char) (TM_LEN_SCI_CWF_672 >> 8);
1126 header->packetLength[0] = (unsigned char) (TM_LEN_SCI_CWF_672 >> 8);
1126 header->packetLength[1] = (unsigned char) (TM_LEN_SCI_CWF_672 );
1127 header->packetLength[1] = (unsigned char) (TM_LEN_SCI_CWF_672 );
1127 header->hkBIA = pa_bia_status_info;
1128 header->hkBIA = pa_bia_status_info;
1128 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
1129 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
1129 header->blkNr[0] = (unsigned char) (BLK_NR_CWF_SHORT_F3 >> 8);
1130 header->blkNr[0] = (unsigned char) (BLK_NR_CWF_SHORT_F3 >> 8);
1130 header->blkNr[1] = (unsigned char) (BLK_NR_CWF_SHORT_F3 );
1131 header->blkNr[1] = (unsigned char) (BLK_NR_CWF_SHORT_F3 );
1131
1132
1132 //*********************
1133 //*********************
1133 // SEND CWF3_light DATA
1134 // SEND CWF3_light DATA
1134 for (i=0; i<NB_PACKETS_PER_GROUP_OF_CWF_LIGHT; i++) // send waveform
1135 for (i=0; i<NB_PACKETS_PER_GROUP_OF_CWF_LIGHT; i++) // send waveform
1135 {
1136 {
1136 spw_ioctl_send_CWF.data = (char*) &dataPtr[ (i * BLK_NR_CWF_SHORT_F3 * NB_BYTES_CWF3_LIGHT_BLK) ];
1137 spw_ioctl_send_CWF.data = (char*) &dataPtr[ (i * BLK_NR_CWF_SHORT_F3 * NB_BYTES_CWF3_LIGHT_BLK) ];
1137 spw_ioctl_send_CWF.hdr = (char*) header;
1138 spw_ioctl_send_CWF.hdr = (char*) header;
1138 // BUILD THE DATA
1139 // BUILD THE DATA
1139 spw_ioctl_send_CWF.dlen = BLK_NR_CWF_SHORT_F3 * NB_BYTES_CWF3_LIGHT_BLK;
1140 spw_ioctl_send_CWF.dlen = BLK_NR_CWF_SHORT_F3 * NB_BYTES_CWF3_LIGHT_BLK;
1140
1141
1141 // SET PACKET SEQUENCE COUNTER
1142 // SET PACKET SEQUENCE COUNTER
1142 increment_seq_counter_source_id( header->packetSequenceControl, sid );
1143 increment_seq_counter_source_id( header->packetSequenceControl, sid );
1143
1144
1144 // SET SID
1145 // SET SID
1145 header->sid = sid;
1146 header->sid = sid;
1146
1147
1147 // SET PACKET TIME
1148 // SET PACKET TIME
1148 compute_acquisition_time( coarseTime, fineTime, SID_NORM_CWF_F3, i, header->acquisitionTime );
1149 compute_acquisition_time( coarseTime, fineTime, SID_NORM_CWF_F3, i, header->acquisitionTime );
1149 //
1150 //
1150 header->time[0] = header->acquisitionTime[0];
1151 header->time[0] = header->acquisitionTime[0];
1151 header->time[1] = header->acquisitionTime[1];
1152 header->time[1] = header->acquisitionTime[1];
1152 header->time[2] = header->acquisitionTime[2];
1153 header->time[2] = header->acquisitionTime[2];
1153 header->time[3] = header->acquisitionTime[3];
1154 header->time[3] = header->acquisitionTime[3];
1154 header->time[4] = header->acquisitionTime[4];
1155 header->time[4] = header->acquisitionTime[4];
1155 header->time[5] = header->acquisitionTime[5];
1156 header->time[5] = header->acquisitionTime[5];
1156
1157
1157 // SET PACKET ID
1158 // SET PACKET ID
1158 header->packetID[0] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST >> 8);
1159 header->packetID[0] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST >> 8);
1159 header->packetID[1] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST);
1160 header->packetID[1] = (unsigned char) (APID_TM_SCIENCE_NORMAL_BURST);
1160
1161
1161 // SEND PACKET
1162 // SEND PACKET
1162 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_CWF );
1163 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_CWF );
1163 if (status != RTEMS_SUCCESSFUL) {
1164 if (status != RTEMS_SUCCESSFUL) {
1164 ret = LFR_DEFAULT;
1165 ret = LFR_DEFAULT;
1165 }
1166 }
1166 }
1167 }
1167
1168
1168 return ret;
1169 return ret;
1169 }
1170 }
1170
1171
1171 void spw_send_asm_f0( ring_node *ring_node_to_send,
1172 void spw_send_asm_f0( ring_node *ring_node_to_send,
1172 Header_TM_LFR_SCIENCE_ASM_t *header )
1173 Header_TM_LFR_SCIENCE_ASM_t *header )
1173 {
1174 {
1174 unsigned int i;
1175 unsigned int i;
1175 unsigned int length = 0;
1176 unsigned int length = 0;
1176 rtems_status_code status;
1177 rtems_status_code status;
1177 unsigned int sid;
1178 unsigned int sid;
1178 float *spectral_matrix;
1179 float *spectral_matrix;
1179 int coarseTime;
1180 int coarseTime;
1180 int fineTime;
1181 int fineTime;
1181 spw_ioctl_pkt_send spw_ioctl_send_ASM;
1182 spw_ioctl_pkt_send spw_ioctl_send_ASM;
1182
1183
1183 sid = ring_node_to_send->sid;
1184 sid = ring_node_to_send->sid;
1184 spectral_matrix = (float*) ring_node_to_send->buffer_address;
1185 spectral_matrix = (float*) ring_node_to_send->buffer_address;
1185 coarseTime = ring_node_to_send->coarseTime;
1186 coarseTime = ring_node_to_send->coarseTime;
1186 fineTime = ring_node_to_send->fineTime;
1187 fineTime = ring_node_to_send->fineTime;
1187
1188
1188 header->biaStatusInfo = pa_bia_status_info;
1189 header->biaStatusInfo = pa_bia_status_info;
1189 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
1190 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
1190
1191
1191 for (i=0; i<3; i++)
1192 for (i=0; i<3; i++)
1192 {
1193 {
1193 if ((i==0) || (i==1))
1194 if ((i==0) || (i==1))
1194 {
1195 {
1195 spw_ioctl_send_ASM.dlen = DLEN_ASM_F0_PKT_1;
1196 spw_ioctl_send_ASM.dlen = DLEN_ASM_F0_PKT_1;
1196 spw_ioctl_send_ASM.data = (char *) &spectral_matrix[
1197 spw_ioctl_send_ASM.data = (char *) &spectral_matrix[
1197 ( (ASM_F0_INDICE_START + (i*NB_BINS_PER_PKT_ASM_F0_1) ) * NB_VALUES_PER_SM )
1198 ( (ASM_F0_INDICE_START + (i*NB_BINS_PER_PKT_ASM_F0_1) ) * NB_VALUES_PER_SM )
1198 ];
1199 ];
1199 length = PACKET_LENGTH_TM_LFR_SCIENCE_ASM_F0_1;
1200 length = PACKET_LENGTH_TM_LFR_SCIENCE_ASM_F0_1;
1200 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6;
1201 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6;
1201 header->pa_lfr_asm_blk_nr[0] = (unsigned char) ( (NB_BINS_PER_PKT_ASM_F0_1) >> 8 ); // BLK_NR MSB
1202 header->pa_lfr_asm_blk_nr[0] = (unsigned char) ( (NB_BINS_PER_PKT_ASM_F0_1) >> 8 ); // BLK_NR MSB
1202 header->pa_lfr_asm_blk_nr[1] = (unsigned char) (NB_BINS_PER_PKT_ASM_F0_1); // BLK_NR LSB
1203 header->pa_lfr_asm_blk_nr[1] = (unsigned char) (NB_BINS_PER_PKT_ASM_F0_1); // BLK_NR LSB
1203 }
1204 }
1204 else
1205 else
1205 {
1206 {
1206 spw_ioctl_send_ASM.dlen = DLEN_ASM_F0_PKT_2;
1207 spw_ioctl_send_ASM.dlen = DLEN_ASM_F0_PKT_2;
1207 spw_ioctl_send_ASM.data = (char*) &spectral_matrix[
1208 spw_ioctl_send_ASM.data = (char*) &spectral_matrix[
1208 ( (ASM_F0_INDICE_START + (i*NB_BINS_PER_PKT_ASM_F0_1) ) * NB_VALUES_PER_SM )
1209 ( (ASM_F0_INDICE_START + (i*NB_BINS_PER_PKT_ASM_F0_1) ) * NB_VALUES_PER_SM )
1209 ];
1210 ];
1210 length = PACKET_LENGTH_TM_LFR_SCIENCE_ASM_F0_2;
1211 length = PACKET_LENGTH_TM_LFR_SCIENCE_ASM_F0_2;
1211 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6;
1212 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6;
1212 header->pa_lfr_asm_blk_nr[0] = (unsigned char) ( (NB_BINS_PER_PKT_ASM_F0_2) >> 8 ); // BLK_NR MSB
1213 header->pa_lfr_asm_blk_nr[0] = (unsigned char) ( (NB_BINS_PER_PKT_ASM_F0_2) >> 8 ); // BLK_NR MSB
1213 header->pa_lfr_asm_blk_nr[1] = (unsigned char) (NB_BINS_PER_PKT_ASM_F0_2); // BLK_NR LSB
1214 header->pa_lfr_asm_blk_nr[1] = (unsigned char) (NB_BINS_PER_PKT_ASM_F0_2); // BLK_NR LSB
1214 }
1215 }
1215
1216
1216 spw_ioctl_send_ASM.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_ASM;
1217 spw_ioctl_send_ASM.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_ASM;
1217 spw_ioctl_send_ASM.hdr = (char *) header;
1218 spw_ioctl_send_ASM.hdr = (char *) header;
1218 spw_ioctl_send_ASM.options = 0;
1219 spw_ioctl_send_ASM.options = 0;
1219
1220
1220 // (2) BUILD THE HEADER
1221 // (2) BUILD THE HEADER
1221 increment_seq_counter_source_id( header->packetSequenceControl, sid );
1222 increment_seq_counter_source_id( header->packetSequenceControl, sid );
1222 header->packetLength[0] = (unsigned char) (length>>8);
1223 header->packetLength[0] = (unsigned char) (length>>8);
1223 header->packetLength[1] = (unsigned char) (length);
1224 header->packetLength[1] = (unsigned char) (length);
1224 header->sid = (unsigned char) sid; // SID
1225 header->sid = (unsigned char) sid; // SID
1225 header->pa_lfr_pkt_cnt_asm = 3;
1226 header->pa_lfr_pkt_cnt_asm = 3;
1226 header->pa_lfr_pkt_nr_asm = (unsigned char) (i+1);
1227 header->pa_lfr_pkt_nr_asm = (unsigned char) (i+1);
1227
1228
1228 // (3) SET PACKET TIME
1229 // (3) SET PACKET TIME
1229 header->time[0] = (unsigned char) (coarseTime>>24);
1230 header->time[0] = (unsigned char) (coarseTime>>24);
1230 header->time[1] = (unsigned char) (coarseTime>>16);
1231 header->time[1] = (unsigned char) (coarseTime>>16);
1231 header->time[2] = (unsigned char) (coarseTime>>8);
1232 header->time[2] = (unsigned char) (coarseTime>>8);
1232 header->time[3] = (unsigned char) (coarseTime);
1233 header->time[3] = (unsigned char) (coarseTime);
1233 header->time[4] = (unsigned char) (fineTime>>8);
1234 header->time[4] = (unsigned char) (fineTime>>8);
1234 header->time[5] = (unsigned char) (fineTime);
1235 header->time[5] = (unsigned char) (fineTime);
1235 //
1236 //
1236 header->acquisitionTime[0] = header->time[0];
1237 header->acquisitionTime[0] = header->time[0];
1237 header->acquisitionTime[1] = header->time[1];
1238 header->acquisitionTime[1] = header->time[1];
1238 header->acquisitionTime[2] = header->time[2];
1239 header->acquisitionTime[2] = header->time[2];
1239 header->acquisitionTime[3] = header->time[3];
1240 header->acquisitionTime[3] = header->time[3];
1240 header->acquisitionTime[4] = header->time[4];
1241 header->acquisitionTime[4] = header->time[4];
1241 header->acquisitionTime[5] = header->time[5];
1242 header->acquisitionTime[5] = header->time[5];
1242
1243
1243 // (4) SEND PACKET
1244 // (4) SEND PACKET
1244 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_ASM );
1245 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_ASM );
1245 if (status != RTEMS_SUCCESSFUL) {
1246 if (status != RTEMS_SUCCESSFUL) {
1246 PRINTF1("in ASM_send *** ERR %d\n", (int) status)
1247 PRINTF1("in ASM_send *** ERR %d\n", (int) status)
1247 }
1248 }
1248 }
1249 }
1249 }
1250 }
1250
1251
1251 void spw_send_asm_f1( ring_node *ring_node_to_send,
1252 void spw_send_asm_f1( ring_node *ring_node_to_send,
1252 Header_TM_LFR_SCIENCE_ASM_t *header )
1253 Header_TM_LFR_SCIENCE_ASM_t *header )
1253 {
1254 {
1254 unsigned int i;
1255 unsigned int i;
1255 unsigned int length = 0;
1256 unsigned int length = 0;
1256 rtems_status_code status;
1257 rtems_status_code status;
1257 unsigned int sid;
1258 unsigned int sid;
1258 float *spectral_matrix;
1259 float *spectral_matrix;
1259 int coarseTime;
1260 int coarseTime;
1260 int fineTime;
1261 int fineTime;
1261 spw_ioctl_pkt_send spw_ioctl_send_ASM;
1262 spw_ioctl_pkt_send spw_ioctl_send_ASM;
1262
1263
1263 sid = ring_node_to_send->sid;
1264 sid = ring_node_to_send->sid;
1264 spectral_matrix = (float*) ring_node_to_send->buffer_address;
1265 spectral_matrix = (float*) ring_node_to_send->buffer_address;
1265 coarseTime = ring_node_to_send->coarseTime;
1266 coarseTime = ring_node_to_send->coarseTime;
1266 fineTime = ring_node_to_send->fineTime;
1267 fineTime = ring_node_to_send->fineTime;
1267
1268
1268 header->biaStatusInfo = pa_bia_status_info;
1269 header->biaStatusInfo = pa_bia_status_info;
1269 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
1270 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
1270
1271
1271 for (i=0; i<3; i++)
1272 for (i=0; i<3; i++)
1272 {
1273 {
1273 if ((i==0) || (i==1))
1274 if ((i==0) || (i==1))
1274 {
1275 {
1275 spw_ioctl_send_ASM.dlen = DLEN_ASM_F1_PKT_1;
1276 spw_ioctl_send_ASM.dlen = DLEN_ASM_F1_PKT_1;
1276 spw_ioctl_send_ASM.data = (char *) &spectral_matrix[
1277 spw_ioctl_send_ASM.data = (char *) &spectral_matrix[
1277 ( (ASM_F1_INDICE_START + (i*NB_BINS_PER_PKT_ASM_F1_1) ) * NB_VALUES_PER_SM )
1278 ( (ASM_F1_INDICE_START + (i*NB_BINS_PER_PKT_ASM_F1_1) ) * NB_VALUES_PER_SM )
1278 ];
1279 ];
1279 length = PACKET_LENGTH_TM_LFR_SCIENCE_ASM_F1_1;
1280 length = PACKET_LENGTH_TM_LFR_SCIENCE_ASM_F1_1;
1280 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6;
1281 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6;
1281 header->pa_lfr_asm_blk_nr[0] = (unsigned char) ( (NB_BINS_PER_PKT_ASM_F1_1) >> 8 ); // BLK_NR MSB
1282 header->pa_lfr_asm_blk_nr[0] = (unsigned char) ( (NB_BINS_PER_PKT_ASM_F1_1) >> 8 ); // BLK_NR MSB
1282 header->pa_lfr_asm_blk_nr[1] = (unsigned char) (NB_BINS_PER_PKT_ASM_F1_1); // BLK_NR LSB
1283 header->pa_lfr_asm_blk_nr[1] = (unsigned char) (NB_BINS_PER_PKT_ASM_F1_1); // BLK_NR LSB
1283 }
1284 }
1284 else
1285 else
1285 {
1286 {
1286 spw_ioctl_send_ASM.dlen = DLEN_ASM_F1_PKT_2;
1287 spw_ioctl_send_ASM.dlen = DLEN_ASM_F1_PKT_2;
1287 spw_ioctl_send_ASM.data = (char*) &spectral_matrix[
1288 spw_ioctl_send_ASM.data = (char*) &spectral_matrix[
1288 ( (ASM_F1_INDICE_START + (i*NB_BINS_PER_PKT_ASM_F1_1) ) * NB_VALUES_PER_SM )
1289 ( (ASM_F1_INDICE_START + (i*NB_BINS_PER_PKT_ASM_F1_1) ) * NB_VALUES_PER_SM )
1289 ];
1290 ];
1290 length = PACKET_LENGTH_TM_LFR_SCIENCE_ASM_F1_2;
1291 length = PACKET_LENGTH_TM_LFR_SCIENCE_ASM_F1_2;
1291 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6;
1292 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_6;
1292 header->pa_lfr_asm_blk_nr[0] = (unsigned char) ( (NB_BINS_PER_PKT_ASM_F1_2) >> 8 ); // BLK_NR MSB
1293 header->pa_lfr_asm_blk_nr[0] = (unsigned char) ( (NB_BINS_PER_PKT_ASM_F1_2) >> 8 ); // BLK_NR MSB
1293 header->pa_lfr_asm_blk_nr[1] = (unsigned char) (NB_BINS_PER_PKT_ASM_F1_2); // BLK_NR LSB
1294 header->pa_lfr_asm_blk_nr[1] = (unsigned char) (NB_BINS_PER_PKT_ASM_F1_2); // BLK_NR LSB
1294 }
1295 }
1295
1296
1296 spw_ioctl_send_ASM.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_ASM;
1297 spw_ioctl_send_ASM.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_ASM;
1297 spw_ioctl_send_ASM.hdr = (char *) header;
1298 spw_ioctl_send_ASM.hdr = (char *) header;
1298 spw_ioctl_send_ASM.options = 0;
1299 spw_ioctl_send_ASM.options = 0;
1299
1300
1300 // (2) BUILD THE HEADER
1301 // (2) BUILD THE HEADER
1301 increment_seq_counter_source_id( header->packetSequenceControl, sid );
1302 increment_seq_counter_source_id( header->packetSequenceControl, sid );
1302 header->packetLength[0] = (unsigned char) (length>>8);
1303 header->packetLength[0] = (unsigned char) (length>>8);
1303 header->packetLength[1] = (unsigned char) (length);
1304 header->packetLength[1] = (unsigned char) (length);
1304 header->sid = (unsigned char) sid; // SID
1305 header->sid = (unsigned char) sid; // SID
1305 header->pa_lfr_pkt_cnt_asm = 3;
1306 header->pa_lfr_pkt_cnt_asm = 3;
1306 header->pa_lfr_pkt_nr_asm = (unsigned char) (i+1);
1307 header->pa_lfr_pkt_nr_asm = (unsigned char) (i+1);
1307
1308
1308 // (3) SET PACKET TIME
1309 // (3) SET PACKET TIME
1309 header->time[0] = (unsigned char) (coarseTime>>24);
1310 header->time[0] = (unsigned char) (coarseTime>>24);
1310 header->time[1] = (unsigned char) (coarseTime>>16);
1311 header->time[1] = (unsigned char) (coarseTime>>16);
1311 header->time[2] = (unsigned char) (coarseTime>>8);
1312 header->time[2] = (unsigned char) (coarseTime>>8);
1312 header->time[3] = (unsigned char) (coarseTime);
1313 header->time[3] = (unsigned char) (coarseTime);
1313 header->time[4] = (unsigned char) (fineTime>>8);
1314 header->time[4] = (unsigned char) (fineTime>>8);
1314 header->time[5] = (unsigned char) (fineTime);
1315 header->time[5] = (unsigned char) (fineTime);
1315 //
1316 //
1316 header->acquisitionTime[0] = header->time[0];
1317 header->acquisitionTime[0] = header->time[0];
1317 header->acquisitionTime[1] = header->time[1];
1318 header->acquisitionTime[1] = header->time[1];
1318 header->acquisitionTime[2] = header->time[2];
1319 header->acquisitionTime[2] = header->time[2];
1319 header->acquisitionTime[3] = header->time[3];
1320 header->acquisitionTime[3] = header->time[3];
1320 header->acquisitionTime[4] = header->time[4];
1321 header->acquisitionTime[4] = header->time[4];
1321 header->acquisitionTime[5] = header->time[5];
1322 header->acquisitionTime[5] = header->time[5];
1322
1323
1323 // (4) SEND PACKET
1324 // (4) SEND PACKET
1324 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_ASM );
1325 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_ASM );
1325 if (status != RTEMS_SUCCESSFUL) {
1326 if (status != RTEMS_SUCCESSFUL) {
1326 PRINTF1("in ASM_send *** ERR %d\n", (int) status)
1327 PRINTF1("in ASM_send *** ERR %d\n", (int) status)
1327 }
1328 }
1328 }
1329 }
1329 }
1330 }
1330
1331
1331 void spw_send_asm_f2( ring_node *ring_node_to_send,
1332 void spw_send_asm_f2( ring_node *ring_node_to_send,
1332 Header_TM_LFR_SCIENCE_ASM_t *header )
1333 Header_TM_LFR_SCIENCE_ASM_t *header )
1333 {
1334 {
1334 unsigned int i;
1335 unsigned int i;
1335 unsigned int length = 0;
1336 unsigned int length = 0;
1336 rtems_status_code status;
1337 rtems_status_code status;
1337 unsigned int sid;
1338 unsigned int sid;
1338 float *spectral_matrix;
1339 float *spectral_matrix;
1339 int coarseTime;
1340 int coarseTime;
1340 int fineTime;
1341 int fineTime;
1341 spw_ioctl_pkt_send spw_ioctl_send_ASM;
1342 spw_ioctl_pkt_send spw_ioctl_send_ASM;
1342
1343
1343 sid = ring_node_to_send->sid;
1344 sid = ring_node_to_send->sid;
1344 spectral_matrix = (float*) ring_node_to_send->buffer_address;
1345 spectral_matrix = (float*) ring_node_to_send->buffer_address;
1345 coarseTime = ring_node_to_send->coarseTime;
1346 coarseTime = ring_node_to_send->coarseTime;
1346 fineTime = ring_node_to_send->fineTime;
1347 fineTime = ring_node_to_send->fineTime;
1347
1348
1348 header->biaStatusInfo = pa_bia_status_info;
1349 header->biaStatusInfo = pa_bia_status_info;
1349 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
1350 header->sy_lfr_common_parameters = parameter_dump_packet.sy_lfr_common_parameters;
1350
1351
1351 for (i=0; i<3; i++)
1352 for (i=0; i<3; i++)
1352 {
1353 {
1353
1354
1354 spw_ioctl_send_ASM.dlen = DLEN_ASM_F2_PKT;
1355 spw_ioctl_send_ASM.dlen = DLEN_ASM_F2_PKT;
1355 spw_ioctl_send_ASM.data = (char *) &spectral_matrix[
1356 spw_ioctl_send_ASM.data = (char *) &spectral_matrix[
1356 ( (ASM_F2_INDICE_START + (i*NB_BINS_PER_PKT_ASM_F2) ) * NB_VALUES_PER_SM )
1357 ( (ASM_F2_INDICE_START + (i*NB_BINS_PER_PKT_ASM_F2) ) * NB_VALUES_PER_SM )
1357 ];
1358 ];
1358 length = PACKET_LENGTH_TM_LFR_SCIENCE_ASM_F2;
1359 length = PACKET_LENGTH_TM_LFR_SCIENCE_ASM_F2;
1359 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_3;
1360 header->serviceSubType = TM_SUBTYPE_LFR_SCIENCE_3;
1360 header->pa_lfr_asm_blk_nr[0] = (unsigned char) ( (NB_BINS_PER_PKT_ASM_F2) >> 8 ); // BLK_NR MSB
1361 header->pa_lfr_asm_blk_nr[0] = (unsigned char) ( (NB_BINS_PER_PKT_ASM_F2) >> 8 ); // BLK_NR MSB
1361 header->pa_lfr_asm_blk_nr[1] = (unsigned char) (NB_BINS_PER_PKT_ASM_F2); // BLK_NR LSB
1362 header->pa_lfr_asm_blk_nr[1] = (unsigned char) (NB_BINS_PER_PKT_ASM_F2); // BLK_NR LSB
1362
1363
1363 spw_ioctl_send_ASM.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_ASM;
1364 spw_ioctl_send_ASM.hlen = HEADER_LENGTH_TM_LFR_SCIENCE_ASM;
1364 spw_ioctl_send_ASM.hdr = (char *) header;
1365 spw_ioctl_send_ASM.hdr = (char *) header;
1365 spw_ioctl_send_ASM.options = 0;
1366 spw_ioctl_send_ASM.options = 0;
1366
1367
1367 // (2) BUILD THE HEADER
1368 // (2) BUILD THE HEADER
1368 increment_seq_counter_source_id( header->packetSequenceControl, sid );
1369 increment_seq_counter_source_id( header->packetSequenceControl, sid );
1369 header->packetLength[0] = (unsigned char) (length>>8);
1370 header->packetLength[0] = (unsigned char) (length>>8);
1370 header->packetLength[1] = (unsigned char) (length);
1371 header->packetLength[1] = (unsigned char) (length);
1371 header->sid = (unsigned char) sid; // SID
1372 header->sid = (unsigned char) sid; // SID
1372 header->pa_lfr_pkt_cnt_asm = 3;
1373 header->pa_lfr_pkt_cnt_asm = 3;
1373 header->pa_lfr_pkt_nr_asm = (unsigned char) (i+1);
1374 header->pa_lfr_pkt_nr_asm = (unsigned char) (i+1);
1374
1375
1375 // (3) SET PACKET TIME
1376 // (3) SET PACKET TIME
1376 header->time[0] = (unsigned char) (coarseTime>>24);
1377 header->time[0] = (unsigned char) (coarseTime>>24);
1377 header->time[1] = (unsigned char) (coarseTime>>16);
1378 header->time[1] = (unsigned char) (coarseTime>>16);
1378 header->time[2] = (unsigned char) (coarseTime>>8);
1379 header->time[2] = (unsigned char) (coarseTime>>8);
1379 header->time[3] = (unsigned char) (coarseTime);
1380 header->time[3] = (unsigned char) (coarseTime);
1380 header->time[4] = (unsigned char) (fineTime>>8);
1381 header->time[4] = (unsigned char) (fineTime>>8);
1381 header->time[5] = (unsigned char) (fineTime);
1382 header->time[5] = (unsigned char) (fineTime);
1382 //
1383 //
1383 header->acquisitionTime[0] = header->time[0];
1384 header->acquisitionTime[0] = header->time[0];
1384 header->acquisitionTime[1] = header->time[1];
1385 header->acquisitionTime[1] = header->time[1];
1385 header->acquisitionTime[2] = header->time[2];
1386 header->acquisitionTime[2] = header->time[2];
1386 header->acquisitionTime[3] = header->time[3];
1387 header->acquisitionTime[3] = header->time[3];
1387 header->acquisitionTime[4] = header->time[4];
1388 header->acquisitionTime[4] = header->time[4];
1388 header->acquisitionTime[5] = header->time[5];
1389 header->acquisitionTime[5] = header->time[5];
1389
1390
1390 // (4) SEND PACKET
1391 // (4) SEND PACKET
1391 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_ASM );
1392 status = ioctl( fdSPW, SPACEWIRE_IOCTRL_SEND, &spw_ioctl_send_ASM );
1392 if (status != RTEMS_SUCCESSFUL) {
1393 if (status != RTEMS_SUCCESSFUL) {
1393 PRINTF1("in ASM_send *** ERR %d\n", (int) status)
1394 PRINTF1("in ASM_send *** ERR %d\n", (int) status)
1394 }
1395 }
1395 }
1396 }
1396 }
1397 }
1397
1398
1398 void spw_send_k_dump( ring_node *ring_node_to_send )
1399 void spw_send_k_dump( ring_node *ring_node_to_send )
1399 {
1400 {
1400 rtems_status_code status;
1401 rtems_status_code status;
1401 Packet_TM_LFR_KCOEFFICIENTS_DUMP_t *kcoefficients_dump;
1402 Packet_TM_LFR_KCOEFFICIENTS_DUMP_t *kcoefficients_dump;
1402 unsigned int packetLength;
1403 unsigned int packetLength;
1403 unsigned int size;
1404 unsigned int size;
1404
1405
1405 PRINTF("spw_send_k_dump\n")
1406 PRINTF("spw_send_k_dump\n")
1406
1407
1407 kcoefficients_dump = (Packet_TM_LFR_KCOEFFICIENTS_DUMP_t *) ring_node_to_send->buffer_address;
1408 kcoefficients_dump = (Packet_TM_LFR_KCOEFFICIENTS_DUMP_t *) ring_node_to_send->buffer_address;
1408
1409
1409 packetLength = kcoefficients_dump->packetLength[0] * 256 + kcoefficients_dump->packetLength[1];
1410 packetLength = kcoefficients_dump->packetLength[0] * 256 + kcoefficients_dump->packetLength[1];
1410
1411
1411 size = packetLength + CCSDS_TC_TM_PACKET_OFFSET + CCSDS_PROTOCOLE_EXTRA_BYTES;
1412 size = packetLength + CCSDS_TC_TM_PACKET_OFFSET + CCSDS_PROTOCOLE_EXTRA_BYTES;
1412
1413
1413 PRINTF2("packetLength %d, size %d\n", packetLength, size )
1414 PRINTF2("packetLength %d, size %d\n", packetLength, size )
1414
1415
1415 status = write( fdSPW, (char *) ring_node_to_send->buffer_address, size );
1416 status = write( fdSPW, (char *) ring_node_to_send->buffer_address, size );
1416
1417
1417 if (status == -1){
1418 if (status == -1){
1418 PRINTF2("in SEND *** (2.a) ERRNO = %d, size = %d\n", errno, size)
1419 PRINTF2("in SEND *** (2.a) ERRNO = %d, size = %d\n", errno, size)
1419 }
1420 }
1420
1421
1421 ring_node_to_send->status = 0x00;
1422 ring_node_to_send->status = 0x00;
1422 }
1423 }
@@ -1,1606 +1,1607
1 /** Functions and tasks related to TeleCommand handling.
1 /** Functions and tasks related to TeleCommand handling.
2 *
2 *
3 * @file
3 * @file
4 * @author P. LEROY
4 * @author P. LEROY
5 *
5 *
6 * A group of functions to handle TeleCommands:\n
6 * A group of functions to handle TeleCommands:\n
7 * action launching\n
7 * action launching\n
8 * TC parsing\n
8 * TC parsing\n
9 * ...
9 * ...
10 *
10 *
11 */
11 */
12
12
13 #include "tc_handler.h"
13 #include "tc_handler.h"
14 #include "math.h"
14 #include "math.h"
15
15
16 //***********
16 //***********
17 // RTEMS TASK
17 // RTEMS TASK
18
18
19 rtems_task actn_task( rtems_task_argument unused )
19 rtems_task actn_task( rtems_task_argument unused )
20 {
20 {
21 /** This RTEMS task is responsible for launching actions upton the reception of valid TeleCommands.
21 /** This RTEMS task is responsible for launching actions upton the reception of valid TeleCommands.
22 *
22 *
23 * @param unused is the starting argument of the RTEMS task
23 * @param unused is the starting argument of the RTEMS task
24 *
24 *
25 * The ACTN task waits for data coming from an RTEMS msesage queue. When data arrives, it launches specific actions depending
25 * The ACTN task waits for data coming from an RTEMS msesage queue. When data arrives, it launches specific actions depending
26 * on the incoming TeleCommand.
26 * on the incoming TeleCommand.
27 *
27 *
28 */
28 */
29
29
30 int result;
30 int result;
31 rtems_status_code status; // RTEMS status code
31 rtems_status_code status; // RTEMS status code
32 ccsdsTelecommandPacket_t TC; // TC sent to the ACTN task
32 ccsdsTelecommandPacket_t TC; // TC sent to the ACTN task
33 size_t size; // size of the incoming TC packet
33 size_t size; // size of the incoming TC packet
34 unsigned char subtype; // subtype of the current TC packet
34 unsigned char subtype; // subtype of the current TC packet
35 unsigned char time[6];
35 unsigned char time[6];
36 rtems_id queue_rcv_id;
36 rtems_id queue_rcv_id;
37 rtems_id queue_snd_id;
37 rtems_id queue_snd_id;
38
38
39 status = get_message_queue_id_recv( &queue_rcv_id );
39 status = get_message_queue_id_recv( &queue_rcv_id );
40 if (status != RTEMS_SUCCESSFUL)
40 if (status != RTEMS_SUCCESSFUL)
41 {
41 {
42 PRINTF1("in ACTN *** ERR get_message_queue_id_recv %d\n", status)
42 PRINTF1("in ACTN *** ERR get_message_queue_id_recv %d\n", status)
43 }
43 }
44
44
45 status = get_message_queue_id_send( &queue_snd_id );
45 status = get_message_queue_id_send( &queue_snd_id );
46 if (status != RTEMS_SUCCESSFUL)
46 if (status != RTEMS_SUCCESSFUL)
47 {
47 {
48 PRINTF1("in ACTN *** ERR get_message_queue_id_send %d\n", status)
48 PRINTF1("in ACTN *** ERR get_message_queue_id_send %d\n", status)
49 }
49 }
50
50
51 result = LFR_SUCCESSFUL;
51 result = LFR_SUCCESSFUL;
52 subtype = 0; // subtype of the current TC packet
52 subtype = 0; // subtype of the current TC packet
53
53
54 BOOT_PRINTF("in ACTN *** \n")
54 BOOT_PRINTF("in ACTN *** \n")
55
55
56 while(1)
56 while(1)
57 {
57 {
58 status = rtems_message_queue_receive( queue_rcv_id, (char*) &TC, &size,
58 status = rtems_message_queue_receive( queue_rcv_id, (char*) &TC, &size,
59 RTEMS_WAIT, RTEMS_NO_TIMEOUT);
59 RTEMS_WAIT, RTEMS_NO_TIMEOUT);
60 getTime( time ); // set time to the current time
60 getTime( time ); // set time to the current time
61 if (status!=RTEMS_SUCCESSFUL)
61 if (status!=RTEMS_SUCCESSFUL)
62 {
62 {
63 PRINTF1("ERR *** in task ACTN *** error receiving a message, code %d \n", status)
63 PRINTF1("ERR *** in task ACTN *** error receiving a message, code %d \n", status)
64 }
64 }
65 else
65 else
66 {
66 {
67 subtype = TC.serviceSubType;
67 subtype = TC.serviceSubType;
68 switch(subtype)
68 switch(subtype)
69 {
69 {
70 case TC_SUBTYPE_RESET:
70 case TC_SUBTYPE_RESET:
71 result = action_reset( &TC, queue_snd_id, time );
71 result = action_reset( &TC, queue_snd_id, time );
72 close_action( &TC, result, queue_snd_id );
72 close_action( &TC, result, queue_snd_id );
73 break;
73 break;
74 case TC_SUBTYPE_LOAD_COMM:
74 case TC_SUBTYPE_LOAD_COMM:
75 result = action_load_common_par( &TC );
75 result = action_load_common_par( &TC );
76 close_action( &TC, result, queue_snd_id );
76 close_action( &TC, result, queue_snd_id );
77 break;
77 break;
78 case TC_SUBTYPE_LOAD_NORM:
78 case TC_SUBTYPE_LOAD_NORM:
79 result = action_load_normal_par( &TC, queue_snd_id, time );
79 result = action_load_normal_par( &TC, queue_snd_id, time );
80 close_action( &TC, result, queue_snd_id );
80 close_action( &TC, result, queue_snd_id );
81 break;
81 break;
82 case TC_SUBTYPE_LOAD_BURST:
82 case TC_SUBTYPE_LOAD_BURST:
83 result = action_load_burst_par( &TC, queue_snd_id, time );
83 result = action_load_burst_par( &TC, queue_snd_id, time );
84 close_action( &TC, result, queue_snd_id );
84 close_action( &TC, result, queue_snd_id );
85 break;
85 break;
86 case TC_SUBTYPE_LOAD_SBM1:
86 case TC_SUBTYPE_LOAD_SBM1:
87 result = action_load_sbm1_par( &TC, queue_snd_id, time );
87 result = action_load_sbm1_par( &TC, queue_snd_id, time );
88 close_action( &TC, result, queue_snd_id );
88 close_action( &TC, result, queue_snd_id );
89 break;
89 break;
90 case TC_SUBTYPE_LOAD_SBM2:
90 case TC_SUBTYPE_LOAD_SBM2:
91 result = action_load_sbm2_par( &TC, queue_snd_id, time );
91 result = action_load_sbm2_par( &TC, queue_snd_id, time );
92 close_action( &TC, result, queue_snd_id );
92 close_action( &TC, result, queue_snd_id );
93 break;
93 break;
94 case TC_SUBTYPE_DUMP:
94 case TC_SUBTYPE_DUMP:
95 result = action_dump_par( &TC, queue_snd_id );
95 result = action_dump_par( &TC, queue_snd_id );
96 close_action( &TC, result, queue_snd_id );
96 close_action( &TC, result, queue_snd_id );
97 break;
97 break;
98 case TC_SUBTYPE_ENTER:
98 case TC_SUBTYPE_ENTER:
99 result = action_enter_mode( &TC, queue_snd_id );
99 result = action_enter_mode( &TC, queue_snd_id );
100 close_action( &TC, result, queue_snd_id );
100 close_action( &TC, result, queue_snd_id );
101 break;
101 break;
102 case TC_SUBTYPE_UPDT_INFO:
102 case TC_SUBTYPE_UPDT_INFO:
103 result = action_update_info( &TC, queue_snd_id );
103 result = action_update_info( &TC, queue_snd_id );
104 close_action( &TC, result, queue_snd_id );
104 close_action( &TC, result, queue_snd_id );
105 break;
105 break;
106 case TC_SUBTYPE_EN_CAL:
106 case TC_SUBTYPE_EN_CAL:
107 result = action_enable_calibration( &TC, queue_snd_id, time );
107 result = action_enable_calibration( &TC, queue_snd_id, time );
108 close_action( &TC, result, queue_snd_id );
108 close_action( &TC, result, queue_snd_id );
109 break;
109 break;
110 case TC_SUBTYPE_DIS_CAL:
110 case TC_SUBTYPE_DIS_CAL:
111 result = action_disable_calibration( &TC, queue_snd_id, time );
111 result = action_disable_calibration( &TC, queue_snd_id, time );
112 close_action( &TC, result, queue_snd_id );
112 close_action( &TC, result, queue_snd_id );
113 break;
113 break;
114 case TC_SUBTYPE_LOAD_K:
114 case TC_SUBTYPE_LOAD_K:
115 result = action_load_kcoefficients( &TC, queue_snd_id, time );
115 result = action_load_kcoefficients( &TC, queue_snd_id, time );
116 close_action( &TC, result, queue_snd_id );
116 close_action( &TC, result, queue_snd_id );
117 break;
117 break;
118 case TC_SUBTYPE_DUMP_K:
118 case TC_SUBTYPE_DUMP_K:
119 result = action_dump_kcoefficients( &TC, queue_snd_id, time );
119 result = action_dump_kcoefficients( &TC, queue_snd_id, time );
120 close_action( &TC, result, queue_snd_id );
120 close_action( &TC, result, queue_snd_id );
121 break;
121 break;
122 case TC_SUBTYPE_LOAD_FBINS:
122 case TC_SUBTYPE_LOAD_FBINS:
123 result = action_load_fbins_mask( &TC, queue_snd_id, time );
123 result = action_load_fbins_mask( &TC, queue_snd_id, time );
124 close_action( &TC, result, queue_snd_id );
124 close_action( &TC, result, queue_snd_id );
125 break;
125 break;
126 case TC_SUBTYPE_UPDT_TIME:
126 case TC_SUBTYPE_UPDT_TIME:
127 result = action_update_time( &TC );
127 result = action_update_time( &TC );
128 close_action( &TC, result, queue_snd_id );
128 close_action( &TC, result, queue_snd_id );
129 break;
129 break;
130 default:
130 default:
131 break;
131 break;
132 }
132 }
133 }
133 }
134 }
134 }
135 }
135 }
136
136
137 //***********
137 //***********
138 // TC ACTIONS
138 // TC ACTIONS
139
139
140 int action_reset(ccsdsTelecommandPacket_t *TC, rtems_id queue_id, unsigned char *time)
140 int action_reset(ccsdsTelecommandPacket_t *TC, rtems_id queue_id, unsigned char *time)
141 {
141 {
142 /** This function executes specific actions when a TC_LFR_RESET TeleCommand has been received.
142 /** This function executes specific actions when a TC_LFR_RESET TeleCommand has been received.
143 *
143 *
144 * @param TC points to the TeleCommand packet that is being processed
144 * @param TC points to the TeleCommand packet that is being processed
145 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
145 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
146 *
146 *
147 */
147 */
148
148
149 PRINTF("this is the end!!!\n")
149 PRINTF("this is the end!!!\n")
150 exit(0);
150 exit(0);
151 send_tm_lfr_tc_exe_not_implemented( TC, queue_id, time );
151 send_tm_lfr_tc_exe_not_implemented( TC, queue_id, time );
152 return LFR_DEFAULT;
152 return LFR_DEFAULT;
153 }
153 }
154
154
155 int action_enter_mode(ccsdsTelecommandPacket_t *TC, rtems_id queue_id )
155 int action_enter_mode(ccsdsTelecommandPacket_t *TC, rtems_id queue_id )
156 {
156 {
157 /** This function executes specific actions when a TC_LFR_ENTER_MODE TeleCommand has been received.
157 /** This function executes specific actions when a TC_LFR_ENTER_MODE TeleCommand has been received.
158 *
158 *
159 * @param TC points to the TeleCommand packet that is being processed
159 * @param TC points to the TeleCommand packet that is being processed
160 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
160 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
161 *
161 *
162 */
162 */
163
163
164 rtems_status_code status;
164 rtems_status_code status;
165 unsigned char requestedMode;
165 unsigned char requestedMode;
166 unsigned int *transitionCoarseTime_ptr;
166 unsigned int *transitionCoarseTime_ptr;
167 unsigned int transitionCoarseTime;
167 unsigned int transitionCoarseTime;
168 unsigned char * bytePosPtr;
168 unsigned char * bytePosPtr;
169
169
170 bytePosPtr = (unsigned char *) &TC->packetID;
170 bytePosPtr = (unsigned char *) &TC->packetID;
171
171
172 requestedMode = bytePosPtr[ BYTE_POS_CP_MODE_LFR_SET ];
172 requestedMode = bytePosPtr[ BYTE_POS_CP_MODE_LFR_SET ];
173 transitionCoarseTime_ptr = (unsigned int *) ( &bytePosPtr[ BYTE_POS_CP_LFR_ENTER_MODE_TIME ] );
173 transitionCoarseTime_ptr = (unsigned int *) ( &bytePosPtr[ BYTE_POS_CP_LFR_ENTER_MODE_TIME ] );
174 transitionCoarseTime = (*transitionCoarseTime_ptr) & 0x7fffffff;
174 transitionCoarseTime = (*transitionCoarseTime_ptr) & 0x7fffffff;
175
175
176 status = check_mode_value( requestedMode );
176 status = check_mode_value( requestedMode );
177
177
178 if ( status != LFR_SUCCESSFUL ) // the mode value is inconsistent
178 if ( status != LFR_SUCCESSFUL ) // the mode value is inconsistent
179 {
179 {
180 send_tm_lfr_tc_exe_inconsistent( TC, queue_id, BYTE_POS_CP_MODE_LFR_SET, requestedMode );
180 send_tm_lfr_tc_exe_inconsistent( TC, queue_id, BYTE_POS_CP_MODE_LFR_SET, requestedMode );
181 }
181 }
182
182
183 else // the mode value is valid, check the transition
183 else // the mode value is valid, check the transition
184 {
184 {
185 status = check_mode_transition(requestedMode);
185 status = check_mode_transition(requestedMode);
186 if (status != LFR_SUCCESSFUL)
186 if (status != LFR_SUCCESSFUL)
187 {
187 {
188 PRINTF("ERR *** in action_enter_mode *** check_mode_transition\n")
188 PRINTF("ERR *** in action_enter_mode *** check_mode_transition\n")
189 send_tm_lfr_tc_exe_not_executable( TC, queue_id );
189 send_tm_lfr_tc_exe_not_executable( TC, queue_id );
190 }
190 }
191 }
191 }
192
192
193 if ( status == LFR_SUCCESSFUL ) // the transition is valid, check the date
193 if ( status == LFR_SUCCESSFUL ) // the transition is valid, check the date
194 {
194 {
195 status = check_transition_date( transitionCoarseTime );
195 status = check_transition_date( transitionCoarseTime );
196 if (status != LFR_SUCCESSFUL)
196 if (status != LFR_SUCCESSFUL)
197 {
197 {
198 PRINTF("ERR *** in action_enter_mode *** check_transition_date\n")
198 PRINTF("ERR *** in action_enter_mode *** check_transition_date\n")
199 send_tm_lfr_tc_exe_inconsistent( TC, queue_id,
199 send_tm_lfr_tc_exe_inconsistent( TC, queue_id,
200 BYTE_POS_CP_LFR_ENTER_MODE_TIME,
200 BYTE_POS_CP_LFR_ENTER_MODE_TIME,
201 bytePosPtr[ BYTE_POS_CP_LFR_ENTER_MODE_TIME + 3 ] );
201 bytePosPtr[ BYTE_POS_CP_LFR_ENTER_MODE_TIME + 3 ] );
202 }
202 }
203 }
203 }
204
204
205 if ( status == LFR_SUCCESSFUL ) // the date is valid, enter the mode
205 if ( status == LFR_SUCCESSFUL ) // the date is valid, enter the mode
206 {
206 {
207 PRINTF1("OK *** in action_enter_mode *** enter mode %d\n", requestedMode);
207 PRINTF1("OK *** in action_enter_mode *** enter mode %d\n", requestedMode);
208
208
209 update_last_valid_transition_date( transitionCoarseTime );
209 update_last_valid_transition_date( transitionCoarseTime );
210
210
211 switch(requestedMode)
211 switch(requestedMode)
212 {
212 {
213 case LFR_MODE_STANDBY:
213 case LFR_MODE_STANDBY:
214 status = enter_mode_standby();
214 status = enter_mode_standby();
215 break;
215 break;
216 case LFR_MODE_NORMAL:
216 case LFR_MODE_NORMAL:
217 status = enter_mode_normal( transitionCoarseTime );
217 status = enter_mode_normal( transitionCoarseTime );
218 break;
218 break;
219 case LFR_MODE_BURST:
219 case LFR_MODE_BURST:
220 status = enter_mode_burst( transitionCoarseTime );
220 status = enter_mode_burst( transitionCoarseTime );
221 break;
221 break;
222 case LFR_MODE_SBM1:
222 case LFR_MODE_SBM1:
223 status = enter_mode_sbm1( transitionCoarseTime );
223 status = enter_mode_sbm1( transitionCoarseTime );
224 break;
224 break;
225 case LFR_MODE_SBM2:
225 case LFR_MODE_SBM2:
226 status = enter_mode_sbm2( transitionCoarseTime );
226 status = enter_mode_sbm2( transitionCoarseTime );
227 break;
227 break;
228 default:
228 default:
229 break;
229 break;
230 }
230 }
231 }
231 }
232
232
233 return status;
233 return status;
234 }
234 }
235
235
236 int action_update_info(ccsdsTelecommandPacket_t *TC, rtems_id queue_id)
236 int action_update_info(ccsdsTelecommandPacket_t *TC, rtems_id queue_id)
237 {
237 {
238 /** This function executes specific actions when a TC_LFR_UPDATE_INFO TeleCommand has been received.
238 /** This function executes specific actions when a TC_LFR_UPDATE_INFO TeleCommand has been received.
239 *
239 *
240 * @param TC points to the TeleCommand packet that is being processed
240 * @param TC points to the TeleCommand packet that is being processed
241 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
241 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
242 *
242 *
243 * @return LFR directive status code:
243 * @return LFR directive status code:
244 * - LFR_DEFAULT
244 * - LFR_DEFAULT
245 * - LFR_SUCCESSFUL
245 * - LFR_SUCCESSFUL
246 *
246 *
247 */
247 */
248
248
249 unsigned int val;
249 unsigned int val;
250 int result;
250 int result;
251 unsigned int status;
251 unsigned int status;
252 unsigned char mode;
252 unsigned char mode;
253 unsigned char * bytePosPtr;
253 unsigned char * bytePosPtr;
254
254
255 bytePosPtr = (unsigned char *) &TC->packetID;
255 bytePosPtr = (unsigned char *) &TC->packetID;
256
256
257 // check LFR mode
257 // check LFR mode
258 mode = (bytePosPtr[ BYTE_POS_UPDATE_INFO_PARAMETERS_SET5 ] & 0x1e) >> 1;
258 mode = (bytePosPtr[ BYTE_POS_UPDATE_INFO_PARAMETERS_SET5 ] & 0x1e) >> 1;
259 status = check_update_info_hk_lfr_mode( mode );
259 status = check_update_info_hk_lfr_mode( mode );
260 if (status == LFR_SUCCESSFUL) // check TDS mode
260 if (status == LFR_SUCCESSFUL) // check TDS mode
261 {
261 {
262 mode = (bytePosPtr[ BYTE_POS_UPDATE_INFO_PARAMETERS_SET6 ] & 0xf0) >> 4;
262 mode = (bytePosPtr[ BYTE_POS_UPDATE_INFO_PARAMETERS_SET6 ] & 0xf0) >> 4;
263 status = check_update_info_hk_tds_mode( mode );
263 status = check_update_info_hk_tds_mode( mode );
264 }
264 }
265 if (status == LFR_SUCCESSFUL) // check THR mode
265 if (status == LFR_SUCCESSFUL) // check THR mode
266 {
266 {
267 mode = (bytePosPtr[ BYTE_POS_UPDATE_INFO_PARAMETERS_SET6 ] & 0x0f);
267 mode = (bytePosPtr[ BYTE_POS_UPDATE_INFO_PARAMETERS_SET6 ] & 0x0f);
268 status = check_update_info_hk_thr_mode( mode );
268 status = check_update_info_hk_thr_mode( mode );
269 }
269 }
270 if (status == LFR_SUCCESSFUL) // if the parameter check is successful
270 if (status == LFR_SUCCESSFUL) // if the parameter check is successful
271 {
271 {
272 val = housekeeping_packet.hk_lfr_update_info_tc_cnt[0] * 256
272 val = housekeeping_packet.hk_lfr_update_info_tc_cnt[0] * 256
273 + housekeeping_packet.hk_lfr_update_info_tc_cnt[1];
273 + housekeeping_packet.hk_lfr_update_info_tc_cnt[1];
274 val++;
274 val++;
275 housekeeping_packet.hk_lfr_update_info_tc_cnt[0] = (unsigned char) (val >> 8);
275 housekeeping_packet.hk_lfr_update_info_tc_cnt[0] = (unsigned char) (val >> 8);
276 housekeeping_packet.hk_lfr_update_info_tc_cnt[1] = (unsigned char) (val);
276 housekeeping_packet.hk_lfr_update_info_tc_cnt[1] = (unsigned char) (val);
277 }
277 }
278
278
279 // pa_bia_status_info
279 // pa_bia_status_info
280 // => pa_bia_mode_mux_set 3 bits
280 // => pa_bia_mode_mux_set 3 bits
281 // => pa_bia_mode_hv_enabled 1 bit
281 // => pa_bia_mode_hv_enabled 1 bit
282 // => pa_bia_mode_bias1_enabled 1 bit
282 // => pa_bia_mode_bias1_enabled 1 bit
283 // => pa_bia_mode_bias2_enabled 1 bit
283 // => pa_bia_mode_bias2_enabled 1 bit
284 // => pa_bia_mode_bias3_enabled 1 bit
284 // => pa_bia_mode_bias3_enabled 1 bit
285 // => pa_bia_on_off (cp_dpu_bias_on_off)
285 // => pa_bia_on_off (cp_dpu_bias_on_off)
286 pa_bia_status_info = bytePosPtr[ BYTE_POS_UPDATE_INFO_PARAMETERS_SET2 ] & 0xfe; // [1111 1110]
286 pa_bia_status_info = bytePosPtr[ BYTE_POS_UPDATE_INFO_PARAMETERS_SET2 ] & 0xfe; // [1111 1110]
287 pa_bia_status_info = pa_bia_status_info
287 pa_bia_status_info = pa_bia_status_info
288 | (bytePosPtr[ BYTE_POS_UPDATE_INFO_PARAMETERS_SET1 ] & 0x1);
288 | (bytePosPtr[ BYTE_POS_UPDATE_INFO_PARAMETERS_SET1 ] & 0x1);
289
289
290 result = status;
290 result = status;
291
291
292 return result;
292 return result;
293 }
293 }
294
294
295 int action_enable_calibration(ccsdsTelecommandPacket_t *TC, rtems_id queue_id, unsigned char *time)
295 int action_enable_calibration(ccsdsTelecommandPacket_t *TC, rtems_id queue_id, unsigned char *time)
296 {
296 {
297 /** This function executes specific actions when a TC_LFR_ENABLE_CALIBRATION TeleCommand has been received.
297 /** This function executes specific actions when a TC_LFR_ENABLE_CALIBRATION TeleCommand has been received.
298 *
298 *
299 * @param TC points to the TeleCommand packet that is being processed
299 * @param TC points to the TeleCommand packet that is being processed
300 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
300 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
301 *
301 *
302 */
302 */
303
303
304 int result;
304 int result;
305
305
306 result = LFR_DEFAULT;
306 result = LFR_DEFAULT;
307
307
308 setCalibration( true );
308 setCalibration( true );
309
309
310 result = LFR_SUCCESSFUL;
310 result = LFR_SUCCESSFUL;
311
311
312 return result;
312 return result;
313 }
313 }
314
314
315 int action_disable_calibration(ccsdsTelecommandPacket_t *TC, rtems_id queue_id, unsigned char *time)
315 int action_disable_calibration(ccsdsTelecommandPacket_t *TC, rtems_id queue_id, unsigned char *time)
316 {
316 {
317 /** This function executes specific actions when a TC_LFR_DISABLE_CALIBRATION TeleCommand has been received.
317 /** This function executes specific actions when a TC_LFR_DISABLE_CALIBRATION TeleCommand has been received.
318 *
318 *
319 * @param TC points to the TeleCommand packet that is being processed
319 * @param TC points to the TeleCommand packet that is being processed
320 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
320 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
321 *
321 *
322 */
322 */
323
323
324 int result;
324 int result;
325
325
326 result = LFR_DEFAULT;
326 result = LFR_DEFAULT;
327
327
328 setCalibration( false );
328 setCalibration( false );
329
329
330 result = LFR_SUCCESSFUL;
330 result = LFR_SUCCESSFUL;
331
331
332 return result;
332 return result;
333 }
333 }
334
334
335 int action_update_time(ccsdsTelecommandPacket_t *TC)
335 int action_update_time(ccsdsTelecommandPacket_t *TC)
336 {
336 {
337 /** This function executes specific actions when a TC_LFR_UPDATE_TIME TeleCommand has been received.
337 /** This function executes specific actions when a TC_LFR_UPDATE_TIME TeleCommand has been received.
338 *
338 *
339 * @param TC points to the TeleCommand packet that is being processed
339 * @param TC points to the TeleCommand packet that is being processed
340 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
340 * @param queue_id is the id of the queue which handles TM transmission by the SpaceWire driver
341 *
341 *
342 * @return LFR_SUCCESSFUL
342 * @return LFR_SUCCESSFUL
343 *
343 *
344 */
344 */
345
345
346 unsigned int val;
346 unsigned int val;
347
347
348 time_management_regs->coarse_time_load = (TC->dataAndCRC[0] << 24)
348 time_management_regs->coarse_time_load = (TC->dataAndCRC[0] << 24)
349 + (TC->dataAndCRC[1] << 16)
349 + (TC->dataAndCRC[1] << 16)
350 + (TC->dataAndCRC[2] << 8)
350 + (TC->dataAndCRC[2] << 8)
351 + TC->dataAndCRC[3];
351 + TC->dataAndCRC[3];
352
352
353 val = housekeeping_packet.hk_lfr_update_time_tc_cnt[0] * 256
353 val = housekeeping_packet.hk_lfr_update_time_tc_cnt[0] * 256
354 + housekeeping_packet.hk_lfr_update_time_tc_cnt[1];
354 + housekeeping_packet.hk_lfr_update_time_tc_cnt[1];
355 val++;
355 val++;
356 housekeeping_packet.hk_lfr_update_time_tc_cnt[0] = (unsigned char) (val >> 8);
356 housekeeping_packet.hk_lfr_update_time_tc_cnt[0] = (unsigned char) (val >> 8);
357 housekeeping_packet.hk_lfr_update_time_tc_cnt[1] = (unsigned char) (val);
357 housekeeping_packet.hk_lfr_update_time_tc_cnt[1] = (unsigned char) (val);
358
358
359 return LFR_SUCCESSFUL;
359 return LFR_SUCCESSFUL;
360 }
360 }
361
361
362 //*******************
362 //*******************
363 // ENTERING THE MODES
363 // ENTERING THE MODES
364 int check_mode_value( unsigned char requestedMode )
364 int check_mode_value( unsigned char requestedMode )
365 {
365 {
366 int status;
366 int status;
367
367
368 if ( (requestedMode != LFR_MODE_STANDBY)
368 if ( (requestedMode != LFR_MODE_STANDBY)
369 && (requestedMode != LFR_MODE_NORMAL) && (requestedMode != LFR_MODE_BURST)
369 && (requestedMode != LFR_MODE_NORMAL) && (requestedMode != LFR_MODE_BURST)
370 && (requestedMode != LFR_MODE_SBM1) && (requestedMode != LFR_MODE_SBM2) )
370 && (requestedMode != LFR_MODE_SBM1) && (requestedMode != LFR_MODE_SBM2) )
371 {
371 {
372 status = LFR_DEFAULT;
372 status = LFR_DEFAULT;
373 }
373 }
374 else
374 else
375 {
375 {
376 status = LFR_SUCCESSFUL;
376 status = LFR_SUCCESSFUL;
377 }
377 }
378
378
379 return status;
379 return status;
380 }
380 }
381
381
382 int check_mode_transition( unsigned char requestedMode )
382 int check_mode_transition( unsigned char requestedMode )
383 {
383 {
384 /** This function checks the validity of the transition requested by the TC_LFR_ENTER_MODE.
384 /** This function checks the validity of the transition requested by the TC_LFR_ENTER_MODE.
385 *
385 *
386 * @param requestedMode is the mode requested by the TC_LFR_ENTER_MODE
386 * @param requestedMode is the mode requested by the TC_LFR_ENTER_MODE
387 *
387 *
388 * @return LFR directive status codes:
388 * @return LFR directive status codes:
389 * - LFR_SUCCESSFUL - the transition is authorized
389 * - LFR_SUCCESSFUL - the transition is authorized
390 * - LFR_DEFAULT - the transition is not authorized
390 * - LFR_DEFAULT - the transition is not authorized
391 *
391 *
392 */
392 */
393
393
394 int status;
394 int status;
395
395
396 switch (requestedMode)
396 switch (requestedMode)
397 {
397 {
398 case LFR_MODE_STANDBY:
398 case LFR_MODE_STANDBY:
399 if ( lfrCurrentMode == LFR_MODE_STANDBY ) {
399 if ( lfrCurrentMode == LFR_MODE_STANDBY ) {
400 status = LFR_DEFAULT;
400 status = LFR_DEFAULT;
401 }
401 }
402 else
402 else
403 {
403 {
404 status = LFR_SUCCESSFUL;
404 status = LFR_SUCCESSFUL;
405 }
405 }
406 break;
406 break;
407 case LFR_MODE_NORMAL:
407 case LFR_MODE_NORMAL:
408 if ( lfrCurrentMode == LFR_MODE_NORMAL ) {
408 if ( lfrCurrentMode == LFR_MODE_NORMAL ) {
409 status = LFR_DEFAULT;
409 status = LFR_DEFAULT;
410 }
410 }
411 else {
411 else {
412 status = LFR_SUCCESSFUL;
412 status = LFR_SUCCESSFUL;
413 }
413 }
414 break;
414 break;
415 case LFR_MODE_BURST:
415 case LFR_MODE_BURST:
416 if ( lfrCurrentMode == LFR_MODE_BURST ) {
416 if ( lfrCurrentMode == LFR_MODE_BURST ) {
417 status = LFR_DEFAULT;
417 status = LFR_DEFAULT;
418 }
418 }
419 else {
419 else {
420 status = LFR_SUCCESSFUL;
420 status = LFR_SUCCESSFUL;
421 }
421 }
422 break;
422 break;
423 case LFR_MODE_SBM1:
423 case LFR_MODE_SBM1:
424 if ( lfrCurrentMode == LFR_MODE_SBM1 ) {
424 if ( lfrCurrentMode == LFR_MODE_SBM1 ) {
425 status = LFR_DEFAULT;
425 status = LFR_DEFAULT;
426 }
426 }
427 else {
427 else {
428 status = LFR_SUCCESSFUL;
428 status = LFR_SUCCESSFUL;
429 }
429 }
430 break;
430 break;
431 case LFR_MODE_SBM2:
431 case LFR_MODE_SBM2:
432 if ( lfrCurrentMode == LFR_MODE_SBM2 ) {
432 if ( lfrCurrentMode == LFR_MODE_SBM2 ) {
433 status = LFR_DEFAULT;
433 status = LFR_DEFAULT;
434 }
434 }
435 else {
435 else {
436 status = LFR_SUCCESSFUL;
436 status = LFR_SUCCESSFUL;
437 }
437 }
438 break;
438 break;
439 default:
439 default:
440 status = LFR_DEFAULT;
440 status = LFR_DEFAULT;
441 break;
441 break;
442 }
442 }
443
443
444 return status;
444 return status;
445 }
445 }
446
446
447 void update_last_valid_transition_date( unsigned int transitionCoarseTime )
447 void update_last_valid_transition_date( unsigned int transitionCoarseTime )
448 {
448 {
449 lastValidEnterModeTime = transitionCoarseTime;
449 lastValidEnterModeTime = transitionCoarseTime;
450 PRINTF1("lastValidEnterModeTime = %x\n", transitionCoarseTime);
450 }
451 }
451
452
452 int check_transition_date( unsigned int transitionCoarseTime )
453 int check_transition_date( unsigned int transitionCoarseTime )
453 {
454 {
454 int status;
455 int status;
455 unsigned int localCoarseTime;
456 unsigned int localCoarseTime;
456 unsigned int deltaCoarseTime;
457 unsigned int deltaCoarseTime;
457
458
458 status = LFR_SUCCESSFUL;
459 status = LFR_SUCCESSFUL;
459
460
460 if (transitionCoarseTime == 0) // transition time = 0 means an instant transition
461 if (transitionCoarseTime == 0) // transition time = 0 means an instant transition
461 {
462 {
462 status = LFR_SUCCESSFUL;
463 status = LFR_SUCCESSFUL;
463 }
464 }
464 else
465 else
465 {
466 {
466 localCoarseTime = time_management_regs->coarse_time & 0x7fffffff;
467 localCoarseTime = time_management_regs->coarse_time & 0x7fffffff;
467
468
468 PRINTF2("localTime = %x, transitionTime = %x\n", localCoarseTime, transitionCoarseTime)
469 PRINTF2("localTime = %x, transitionTime = %x\n", localCoarseTime, transitionCoarseTime);
469
470
470 if ( transitionCoarseTime <= localCoarseTime ) // SSS-CP-EQS-322
471 if ( transitionCoarseTime <= localCoarseTime ) // SSS-CP-EQS-322
471 {
472 {
472 status = LFR_DEFAULT;
473 status = LFR_DEFAULT;
473 PRINTF("ERR *** in check_transition_date *** transitionCoarseTime <= localCoarseTime\n")
474 PRINTF("ERR *** in check_transition_date *** transitionCoarseTime <= localCoarseTime\n");
474 }
475 }
475
476
476 if (status == LFR_SUCCESSFUL)
477 if (status == LFR_SUCCESSFUL)
477 {
478 {
478 deltaCoarseTime = transitionCoarseTime - localCoarseTime;
479 deltaCoarseTime = transitionCoarseTime - localCoarseTime;
479 if ( deltaCoarseTime > 3 ) // SSS-CP-EQS-323
480 if ( deltaCoarseTime > 3 ) // SSS-CP-EQS-323
480 {
481 {
481 status = LFR_DEFAULT;
482 status = LFR_DEFAULT;
482 PRINTF1("ERR *** in check_transition_date *** deltaCoarseTime = %x\n", deltaCoarseTime)
483 PRINTF1("ERR *** in check_transition_date *** deltaCoarseTime = %x\n", deltaCoarseTime)
483 }
484 }
484 }
485 }
485 }
486 }
486
487
487 return status;
488 return status;
488 }
489 }
489
490
490 int restart_asm_activities( unsigned char lfrRequestedMode )
491 int restart_asm_activities( unsigned char lfrRequestedMode )
491 {
492 {
492 rtems_status_code status;
493 rtems_status_code status;
493
494
494 status = stop_spectral_matrices();
495 status = stop_spectral_matrices();
495
496
496 status = restart_asm_tasks( lfrRequestedMode );
497 status = restart_asm_tasks( lfrRequestedMode );
497
498
498 launch_spectral_matrix();
499 launch_spectral_matrix();
499
500
500 return status;
501 return status;
501 }
502 }
502
503
503 int stop_spectral_matrices( void )
504 int stop_spectral_matrices( void )
504 {
505 {
505 /** This function stops and restarts the current mode average spectral matrices activities.
506 /** This function stops and restarts the current mode average spectral matrices activities.
506 *
507 *
507 * @return RTEMS directive status codes:
508 * @return RTEMS directive status codes:
508 * - RTEMS_SUCCESSFUL - task restarted successfully
509 * - RTEMS_SUCCESSFUL - task restarted successfully
509 * - RTEMS_INVALID_ID - task id invalid
510 * - RTEMS_INVALID_ID - task id invalid
510 * - RTEMS_ALREADY_SUSPENDED - task already suspended
511 * - RTEMS_ALREADY_SUSPENDED - task already suspended
511 *
512 *
512 */
513 */
513
514
514 rtems_status_code status;
515 rtems_status_code status;
515
516
516 status = RTEMS_SUCCESSFUL;
517 status = RTEMS_SUCCESSFUL;
517
518
518 // (1) mask interruptions
519 // (1) mask interruptions
519 LEON_Mask_interrupt( IRQ_SPECTRAL_MATRIX ); // clear spectral matrix interrupt
520 LEON_Mask_interrupt( IRQ_SPECTRAL_MATRIX ); // clear spectral matrix interrupt
520
521
521 // (2) reset spectral matrices registers
522 // (2) reset spectral matrices registers
522 set_sm_irq_onNewMatrix( 0 ); // stop the spectral matrices
523 set_sm_irq_onNewMatrix( 0 ); // stop the spectral matrices
523 reset_sm_status();
524 reset_sm_status();
524
525
525 // (3) clear interruptions
526 // (3) clear interruptions
526 LEON_Clear_interrupt( IRQ_SPECTRAL_MATRIX ); // clear spectral matrix interrupt
527 LEON_Clear_interrupt( IRQ_SPECTRAL_MATRIX ); // clear spectral matrix interrupt
527
528
528 // suspend several tasks
529 // suspend several tasks
529 if (lfrCurrentMode != LFR_MODE_STANDBY) {
530 if (lfrCurrentMode != LFR_MODE_STANDBY) {
530 status = suspend_asm_tasks();
531 status = suspend_asm_tasks();
531 }
532 }
532
533
533 if (status != RTEMS_SUCCESSFUL)
534 if (status != RTEMS_SUCCESSFUL)
534 {
535 {
535 PRINTF1("in stop_current_mode *** in suspend_science_tasks *** ERR code: %d\n", status)
536 PRINTF1("in stop_current_mode *** in suspend_science_tasks *** ERR code: %d\n", status)
536 }
537 }
537
538
538 return status;
539 return status;
539 }
540 }
540
541
541 int stop_current_mode( void )
542 int stop_current_mode( void )
542 {
543 {
543 /** This function stops the current mode by masking interrupt lines and suspending science tasks.
544 /** This function stops the current mode by masking interrupt lines and suspending science tasks.
544 *
545 *
545 * @return RTEMS directive status codes:
546 * @return RTEMS directive status codes:
546 * - RTEMS_SUCCESSFUL - task restarted successfully
547 * - RTEMS_SUCCESSFUL - task restarted successfully
547 * - RTEMS_INVALID_ID - task id invalid
548 * - RTEMS_INVALID_ID - task id invalid
548 * - RTEMS_ALREADY_SUSPENDED - task already suspended
549 * - RTEMS_ALREADY_SUSPENDED - task already suspended
549 *
550 *
550 */
551 */
551
552
552 rtems_status_code status;
553 rtems_status_code status;
553
554
554 status = RTEMS_SUCCESSFUL;
555 status = RTEMS_SUCCESSFUL;
555
556
556 // (1) mask interruptions
557 // (1) mask interruptions
557 LEON_Mask_interrupt( IRQ_WAVEFORM_PICKER ); // mask waveform picker interrupt
558 LEON_Mask_interrupt( IRQ_WAVEFORM_PICKER ); // mask waveform picker interrupt
558 LEON_Mask_interrupt( IRQ_SPECTRAL_MATRIX ); // clear spectral matrix interrupt
559 LEON_Mask_interrupt( IRQ_SPECTRAL_MATRIX ); // clear spectral matrix interrupt
559
560
560 // (2) reset waveform picker registers
561 // (2) reset waveform picker registers
561 reset_wfp_burst_enable(); // reset burst and enable bits
562 reset_wfp_burst_enable(); // reset burst and enable bits
562 reset_wfp_status(); // reset all the status bits
563 reset_wfp_status(); // reset all the status bits
563
564
564 // (3) reset spectral matrices registers
565 // (3) reset spectral matrices registers
565 set_sm_irq_onNewMatrix( 0 ); // stop the spectral matrices
566 set_sm_irq_onNewMatrix( 0 ); // stop the spectral matrices
566 reset_sm_status();
567 reset_sm_status();
567
568
568 // reset lfr VHDL module
569 // reset lfr VHDL module
569 reset_lfr();
570 reset_lfr();
570
571
571 reset_extractSWF(); // reset the extractSWF flag to false
572 reset_extractSWF(); // reset the extractSWF flag to false
572
573
573 // (4) clear interruptions
574 // (4) clear interruptions
574 LEON_Clear_interrupt( IRQ_WAVEFORM_PICKER ); // clear waveform picker interrupt
575 LEON_Clear_interrupt( IRQ_WAVEFORM_PICKER ); // clear waveform picker interrupt
575 LEON_Clear_interrupt( IRQ_SPECTRAL_MATRIX ); // clear spectral matrix interrupt
576 LEON_Clear_interrupt( IRQ_SPECTRAL_MATRIX ); // clear spectral matrix interrupt
576
577
577 // suspend several tasks
578 // suspend several tasks
578 if (lfrCurrentMode != LFR_MODE_STANDBY) {
579 if (lfrCurrentMode != LFR_MODE_STANDBY) {
579 status = suspend_science_tasks();
580 status = suspend_science_tasks();
580 }
581 }
581
582
582 if (status != RTEMS_SUCCESSFUL)
583 if (status != RTEMS_SUCCESSFUL)
583 {
584 {
584 PRINTF1("in stop_current_mode *** in suspend_science_tasks *** ERR code: %d\n", status)
585 PRINTF1("in stop_current_mode *** in suspend_science_tasks *** ERR code: %d\n", status)
585 }
586 }
586
587
587 return status;
588 return status;
588 }
589 }
589
590
590 int enter_mode_standby()
591 int enter_mode_standby()
591 {
592 {
592 /** This function is used to put LFR in the STANDBY mode.
593 /** This function is used to put LFR in the STANDBY mode.
593 *
594 *
594 * @param transitionCoarseTime is the requested transition time contained in the TC_LFR_ENTER_MODE
595 * @param transitionCoarseTime is the requested transition time contained in the TC_LFR_ENTER_MODE
595 *
596 *
596 * @return RTEMS directive status codes:
597 * @return RTEMS directive status codes:
597 * - RTEMS_SUCCESSFUL - task restarted successfully
598 * - RTEMS_SUCCESSFUL - task restarted successfully
598 * - RTEMS_INVALID_ID - task id invalid
599 * - RTEMS_INVALID_ID - task id invalid
599 * - RTEMS_INCORRECT_STATE - task never started
600 * - RTEMS_INCORRECT_STATE - task never started
600 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
601 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
601 *
602 *
602 * The STANDBY mode does not depends on a specific transition date, the effect of the TC_LFR_ENTER_MODE
603 * The STANDBY mode does not depends on a specific transition date, the effect of the TC_LFR_ENTER_MODE
603 * is immediate.
604 * is immediate.
604 *
605 *
605 */
606 */
606
607
607 int status;
608 int status;
608
609
609 status = stop_current_mode(); // STOP THE CURRENT MODE
610 status = stop_current_mode(); // STOP THE CURRENT MODE
610
611
611 #ifdef PRINT_TASK_STATISTICS
612 #ifdef PRINT_TASK_STATISTICS
612 rtems_cpu_usage_report();
613 rtems_cpu_usage_report();
613 #endif
614 #endif
614
615
615 #ifdef PRINT_STACK_REPORT
616 #ifdef PRINT_STACK_REPORT
616 PRINTF("stack report selected\n")
617 PRINTF("stack report selected\n")
617 rtems_stack_checker_report_usage();
618 rtems_stack_checker_report_usage();
618 #endif
619 #endif
619
620
620 return status;
621 return status;
621 }
622 }
622
623
623 int enter_mode_normal( unsigned int transitionCoarseTime )
624 int enter_mode_normal( unsigned int transitionCoarseTime )
624 {
625 {
625 /** This function is used to start the NORMAL mode.
626 /** This function is used to start the NORMAL mode.
626 *
627 *
627 * @param transitionCoarseTime is the requested transition time contained in the TC_LFR_ENTER_MODE
628 * @param transitionCoarseTime is the requested transition time contained in the TC_LFR_ENTER_MODE
628 *
629 *
629 * @return RTEMS directive status codes:
630 * @return RTEMS directive status codes:
630 * - RTEMS_SUCCESSFUL - task restarted successfully
631 * - RTEMS_SUCCESSFUL - task restarted successfully
631 * - RTEMS_INVALID_ID - task id invalid
632 * - RTEMS_INVALID_ID - task id invalid
632 * - RTEMS_INCORRECT_STATE - task never started
633 * - RTEMS_INCORRECT_STATE - task never started
633 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
634 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
634 *
635 *
635 * The way the NORMAL mode is started depends on the LFR current mode. If LFR is in SBM1 or SBM2,
636 * The way the NORMAL mode is started depends on the LFR current mode. If LFR is in SBM1 or SBM2,
636 * the snapshots are not restarted, only ASM, BP and CWF data generation are affected.
637 * the snapshots are not restarted, only ASM, BP and CWF data generation are affected.
637 *
638 *
638 */
639 */
639
640
640 int status;
641 int status;
641
642
642 #ifdef PRINT_TASK_STATISTICS
643 #ifdef PRINT_TASK_STATISTICS
643 rtems_cpu_usage_reset();
644 rtems_cpu_usage_reset();
644 #endif
645 #endif
645
646
646 status = RTEMS_UNSATISFIED;
647 status = RTEMS_UNSATISFIED;
647
648
648 switch( lfrCurrentMode )
649 switch( lfrCurrentMode )
649 {
650 {
650 case LFR_MODE_STANDBY:
651 case LFR_MODE_STANDBY:
651 status = restart_science_tasks( LFR_MODE_NORMAL ); // restart science tasks
652 status = restart_science_tasks( LFR_MODE_NORMAL ); // restart science tasks
652 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
653 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
653 {
654 {
654 launch_spectral_matrix( );
655 launch_spectral_matrix( );
655 launch_waveform_picker( LFR_MODE_NORMAL, transitionCoarseTime );
656 launch_waveform_picker( LFR_MODE_NORMAL, transitionCoarseTime );
656 }
657 }
657 break;
658 break;
658 case LFR_MODE_BURST:
659 case LFR_MODE_BURST:
659 status = stop_current_mode(); // stop the current mode
660 status = stop_current_mode(); // stop the current mode
660 status = restart_science_tasks( LFR_MODE_NORMAL ); // restart the science tasks
661 status = restart_science_tasks( LFR_MODE_NORMAL ); // restart the science tasks
661 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
662 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
662 {
663 {
663 launch_spectral_matrix( );
664 launch_spectral_matrix( );
664 launch_waveform_picker( LFR_MODE_NORMAL, transitionCoarseTime );
665 launch_waveform_picker( LFR_MODE_NORMAL, transitionCoarseTime );
665 }
666 }
666 break;
667 break;
667 case LFR_MODE_SBM1:
668 case LFR_MODE_SBM1:
668 restart_asm_activities( LFR_MODE_NORMAL ); // this is necessary to restart ASM tasks to update the parameters
669 restart_asm_activities( LFR_MODE_NORMAL ); // this is necessary to restart ASM tasks to update the parameters
669 status = LFR_SUCCESSFUL; // lfrCurrentMode will be updated after the execution of close_action
670 status = LFR_SUCCESSFUL; // lfrCurrentMode will be updated after the execution of close_action
670 break;
671 break;
671 case LFR_MODE_SBM2:
672 case LFR_MODE_SBM2:
672 restart_asm_activities( LFR_MODE_NORMAL ); // this is necessary to restart ASM tasks to update the parameters
673 restart_asm_activities( LFR_MODE_NORMAL ); // this is necessary to restart ASM tasks to update the parameters
673 status = LFR_SUCCESSFUL; // lfrCurrentMode will be updated after the execution of close_action
674 status = LFR_SUCCESSFUL; // lfrCurrentMode will be updated after the execution of close_action
674 break;
675 break;
675 default:
676 default:
676 break;
677 break;
677 }
678 }
678
679
679 if (status != RTEMS_SUCCESSFUL)
680 if (status != RTEMS_SUCCESSFUL)
680 {
681 {
681 PRINTF1("ERR *** in enter_mode_normal *** status = %d\n", status)
682 PRINTF1("ERR *** in enter_mode_normal *** status = %d\n", status)
682 status = RTEMS_UNSATISFIED;
683 status = RTEMS_UNSATISFIED;
683 }
684 }
684
685
685 return status;
686 return status;
686 }
687 }
687
688
688 int enter_mode_burst( unsigned int transitionCoarseTime )
689 int enter_mode_burst( unsigned int transitionCoarseTime )
689 {
690 {
690 /** This function is used to start the BURST mode.
691 /** This function is used to start the BURST mode.
691 *
692 *
692 * @param transitionCoarseTime is the requested transition time contained in the TC_LFR_ENTER_MODE
693 * @param transitionCoarseTime is the requested transition time contained in the TC_LFR_ENTER_MODE
693 *
694 *
694 * @return RTEMS directive status codes:
695 * @return RTEMS directive status codes:
695 * - RTEMS_SUCCESSFUL - task restarted successfully
696 * - RTEMS_SUCCESSFUL - task restarted successfully
696 * - RTEMS_INVALID_ID - task id invalid
697 * - RTEMS_INVALID_ID - task id invalid
697 * - RTEMS_INCORRECT_STATE - task never started
698 * - RTEMS_INCORRECT_STATE - task never started
698 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
699 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
699 *
700 *
700 * The way the BURST mode is started does not depend on the LFR current mode.
701 * The way the BURST mode is started does not depend on the LFR current mode.
701 *
702 *
702 */
703 */
703
704
704
705
705 int status;
706 int status;
706
707
707 #ifdef PRINT_TASK_STATISTICS
708 #ifdef PRINT_TASK_STATISTICS
708 rtems_cpu_usage_reset();
709 rtems_cpu_usage_reset();
709 #endif
710 #endif
710
711
711 status = stop_current_mode(); // stop the current mode
712 status = stop_current_mode(); // stop the current mode
712 status = restart_science_tasks( LFR_MODE_BURST ); // restart the science tasks
713 status = restart_science_tasks( LFR_MODE_BURST ); // restart the science tasks
713 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
714 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
714 {
715 {
715 launch_spectral_matrix( );
716 launch_spectral_matrix( );
716 launch_waveform_picker( LFR_MODE_BURST, transitionCoarseTime );
717 launch_waveform_picker( LFR_MODE_BURST, transitionCoarseTime );
717 }
718 }
718
719
719 if (status != RTEMS_SUCCESSFUL)
720 if (status != RTEMS_SUCCESSFUL)
720 {
721 {
721 PRINTF1("ERR *** in enter_mode_burst *** status = %d\n", status)
722 PRINTF1("ERR *** in enter_mode_burst *** status = %d\n", status)
722 status = RTEMS_UNSATISFIED;
723 status = RTEMS_UNSATISFIED;
723 }
724 }
724
725
725 return status;
726 return status;
726 }
727 }
727
728
728 int enter_mode_sbm1( unsigned int transitionCoarseTime )
729 int enter_mode_sbm1( unsigned int transitionCoarseTime )
729 {
730 {
730 /** This function is used to start the SBM1 mode.
731 /** This function is used to start the SBM1 mode.
731 *
732 *
732 * @param transitionCoarseTime is the requested transition time contained in the TC_LFR_ENTER_MODE
733 * @param transitionCoarseTime is the requested transition time contained in the TC_LFR_ENTER_MODE
733 *
734 *
734 * @return RTEMS directive status codes:
735 * @return RTEMS directive status codes:
735 * - RTEMS_SUCCESSFUL - task restarted successfully
736 * - RTEMS_SUCCESSFUL - task restarted successfully
736 * - RTEMS_INVALID_ID - task id invalid
737 * - RTEMS_INVALID_ID - task id invalid
737 * - RTEMS_INCORRECT_STATE - task never started
738 * - RTEMS_INCORRECT_STATE - task never started
738 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
739 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
739 *
740 *
740 * The way the SBM1 mode is started depends on the LFR current mode. If LFR is in NORMAL or SBM2,
741 * The way the SBM1 mode is started depends on the LFR current mode. If LFR is in NORMAL or SBM2,
741 * the snapshots are not restarted, only ASM, BP and CWF data generation are affected. In other
742 * the snapshots are not restarted, only ASM, BP and CWF data generation are affected. In other
742 * cases, the acquisition is completely restarted.
743 * cases, the acquisition is completely restarted.
743 *
744 *
744 */
745 */
745
746
746 int status;
747 int status;
747
748
748 #ifdef PRINT_TASK_STATISTICS
749 #ifdef PRINT_TASK_STATISTICS
749 rtems_cpu_usage_reset();
750 rtems_cpu_usage_reset();
750 #endif
751 #endif
751
752
752 status = RTEMS_UNSATISFIED;
753 status = RTEMS_UNSATISFIED;
753
754
754 switch( lfrCurrentMode )
755 switch( lfrCurrentMode )
755 {
756 {
756 case LFR_MODE_STANDBY:
757 case LFR_MODE_STANDBY:
757 status = restart_science_tasks( LFR_MODE_SBM1 ); // restart science tasks
758 status = restart_science_tasks( LFR_MODE_SBM1 ); // restart science tasks
758 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
759 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
759 {
760 {
760 launch_spectral_matrix( );
761 launch_spectral_matrix( );
761 launch_waveform_picker( LFR_MODE_SBM1, transitionCoarseTime );
762 launch_waveform_picker( LFR_MODE_SBM1, transitionCoarseTime );
762 }
763 }
763 break;
764 break;
764 case LFR_MODE_NORMAL: // lfrCurrentMode will be updated after the execution of close_action
765 case LFR_MODE_NORMAL: // lfrCurrentMode will be updated after the execution of close_action
765 restart_asm_activities( LFR_MODE_SBM1 );
766 restart_asm_activities( LFR_MODE_SBM1 );
766 status = LFR_SUCCESSFUL;
767 status = LFR_SUCCESSFUL;
767 break;
768 break;
768 case LFR_MODE_BURST:
769 case LFR_MODE_BURST:
769 status = stop_current_mode(); // stop the current mode
770 status = stop_current_mode(); // stop the current mode
770 status = restart_science_tasks( LFR_MODE_SBM1 ); // restart the science tasks
771 status = restart_science_tasks( LFR_MODE_SBM1 ); // restart the science tasks
771 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
772 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
772 {
773 {
773 launch_spectral_matrix( );
774 launch_spectral_matrix( );
774 launch_waveform_picker( LFR_MODE_SBM1, transitionCoarseTime );
775 launch_waveform_picker( LFR_MODE_SBM1, transitionCoarseTime );
775 }
776 }
776 break;
777 break;
777 case LFR_MODE_SBM2:
778 case LFR_MODE_SBM2:
778 restart_asm_activities( LFR_MODE_SBM1 );
779 restart_asm_activities( LFR_MODE_SBM1 );
779 status = LFR_SUCCESSFUL; // lfrCurrentMode will be updated after the execution of close_action
780 status = LFR_SUCCESSFUL; // lfrCurrentMode will be updated after the execution of close_action
780 break;
781 break;
781 default:
782 default:
782 break;
783 break;
783 }
784 }
784
785
785 if (status != RTEMS_SUCCESSFUL)
786 if (status != RTEMS_SUCCESSFUL)
786 {
787 {
787 PRINTF1("ERR *** in enter_mode_sbm1 *** status = %d\n", status)
788 PRINTF1("ERR *** in enter_mode_sbm1 *** status = %d\n", status)
788 status = RTEMS_UNSATISFIED;
789 status = RTEMS_UNSATISFIED;
789 }
790 }
790
791
791 return status;
792 return status;
792 }
793 }
793
794
794 int enter_mode_sbm2( unsigned int transitionCoarseTime )
795 int enter_mode_sbm2( unsigned int transitionCoarseTime )
795 {
796 {
796 /** This function is used to start the SBM2 mode.
797 /** This function is used to start the SBM2 mode.
797 *
798 *
798 * @param transitionCoarseTime is the requested transition time contained in the TC_LFR_ENTER_MODE
799 * @param transitionCoarseTime is the requested transition time contained in the TC_LFR_ENTER_MODE
799 *
800 *
800 * @return RTEMS directive status codes:
801 * @return RTEMS directive status codes:
801 * - RTEMS_SUCCESSFUL - task restarted successfully
802 * - RTEMS_SUCCESSFUL - task restarted successfully
802 * - RTEMS_INVALID_ID - task id invalid
803 * - RTEMS_INVALID_ID - task id invalid
803 * - RTEMS_INCORRECT_STATE - task never started
804 * - RTEMS_INCORRECT_STATE - task never started
804 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
805 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
805 *
806 *
806 * The way the SBM2 mode is started depends on the LFR current mode. If LFR is in NORMAL or SBM1,
807 * The way the SBM2 mode is started depends on the LFR current mode. If LFR is in NORMAL or SBM1,
807 * the snapshots are not restarted, only ASM, BP and CWF data generation are affected. In other
808 * the snapshots are not restarted, only ASM, BP and CWF data generation are affected. In other
808 * cases, the acquisition is completely restarted.
809 * cases, the acquisition is completely restarted.
809 *
810 *
810 */
811 */
811
812
812 int status;
813 int status;
813
814
814 #ifdef PRINT_TASK_STATISTICS
815 #ifdef PRINT_TASK_STATISTICS
815 rtems_cpu_usage_reset();
816 rtems_cpu_usage_reset();
816 #endif
817 #endif
817
818
818 status = RTEMS_UNSATISFIED;
819 status = RTEMS_UNSATISFIED;
819
820
820 switch( lfrCurrentMode )
821 switch( lfrCurrentMode )
821 {
822 {
822 case LFR_MODE_STANDBY:
823 case LFR_MODE_STANDBY:
823 status = restart_science_tasks( LFR_MODE_SBM2 ); // restart science tasks
824 status = restart_science_tasks( LFR_MODE_SBM2 ); // restart science tasks
824 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
825 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
825 {
826 {
826 launch_spectral_matrix( );
827 launch_spectral_matrix( );
827 launch_waveform_picker( LFR_MODE_SBM2, transitionCoarseTime );
828 launch_waveform_picker( LFR_MODE_SBM2, transitionCoarseTime );
828 }
829 }
829 break;
830 break;
830 case LFR_MODE_NORMAL:
831 case LFR_MODE_NORMAL:
831 restart_asm_activities( LFR_MODE_SBM2 );
832 restart_asm_activities( LFR_MODE_SBM2 );
832 status = LFR_SUCCESSFUL; // lfrCurrentMode will be updated after the execution of close_action
833 status = LFR_SUCCESSFUL; // lfrCurrentMode will be updated after the execution of close_action
833 break;
834 break;
834 case LFR_MODE_BURST:
835 case LFR_MODE_BURST:
835 status = stop_current_mode(); // stop the current mode
836 status = stop_current_mode(); // stop the current mode
836 status = restart_science_tasks( LFR_MODE_SBM2 ); // restart the science tasks
837 status = restart_science_tasks( LFR_MODE_SBM2 ); // restart the science tasks
837 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
838 if (status == RTEMS_SUCCESSFUL) // relaunch spectral_matrix and waveform_picker modules
838 {
839 {
839 launch_spectral_matrix( );
840 launch_spectral_matrix( );
840 launch_waveform_picker( LFR_MODE_SBM2, transitionCoarseTime );
841 launch_waveform_picker( LFR_MODE_SBM2, transitionCoarseTime );
841 }
842 }
842 break;
843 break;
843 case LFR_MODE_SBM1:
844 case LFR_MODE_SBM1:
844 restart_asm_activities( LFR_MODE_SBM2 );
845 restart_asm_activities( LFR_MODE_SBM2 );
845 status = LFR_SUCCESSFUL; // lfrCurrentMode will be updated after the execution of close_action
846 status = LFR_SUCCESSFUL; // lfrCurrentMode will be updated after the execution of close_action
846 break;
847 break;
847 default:
848 default:
848 break;
849 break;
849 }
850 }
850
851
851 if (status != RTEMS_SUCCESSFUL)
852 if (status != RTEMS_SUCCESSFUL)
852 {
853 {
853 PRINTF1("ERR *** in enter_mode_sbm2 *** status = %d\n", status)
854 PRINTF1("ERR *** in enter_mode_sbm2 *** status = %d\n", status)
854 status = RTEMS_UNSATISFIED;
855 status = RTEMS_UNSATISFIED;
855 }
856 }
856
857
857 return status;
858 return status;
858 }
859 }
859
860
860 int restart_science_tasks( unsigned char lfrRequestedMode )
861 int restart_science_tasks( unsigned char lfrRequestedMode )
861 {
862 {
862 /** This function is used to restart all science tasks.
863 /** This function is used to restart all science tasks.
863 *
864 *
864 * @return RTEMS directive status codes:
865 * @return RTEMS directive status codes:
865 * - RTEMS_SUCCESSFUL - task restarted successfully
866 * - RTEMS_SUCCESSFUL - task restarted successfully
866 * - RTEMS_INVALID_ID - task id invalid
867 * - RTEMS_INVALID_ID - task id invalid
867 * - RTEMS_INCORRECT_STATE - task never started
868 * - RTEMS_INCORRECT_STATE - task never started
868 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
869 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
869 *
870 *
870 * Science tasks are AVF0, PRC0, WFRM, CWF3, CW2, CWF1
871 * Science tasks are AVF0, PRC0, WFRM, CWF3, CW2, CWF1
871 *
872 *
872 */
873 */
873
874
874 rtems_status_code status[10];
875 rtems_status_code status[10];
875 rtems_status_code ret;
876 rtems_status_code ret;
876
877
877 ret = RTEMS_SUCCESSFUL;
878 ret = RTEMS_SUCCESSFUL;
878
879
879 status[0] = rtems_task_restart( Task_id[TASKID_AVF0], lfrRequestedMode );
880 status[0] = rtems_task_restart( Task_id[TASKID_AVF0], lfrRequestedMode );
880 if (status[0] != RTEMS_SUCCESSFUL)
881 if (status[0] != RTEMS_SUCCESSFUL)
881 {
882 {
882 PRINTF1("in restart_science_task *** AVF0 ERR %d\n", status[0])
883 PRINTF1("in restart_science_task *** AVF0 ERR %d\n", status[0])
883 }
884 }
884
885
885 status[1] = rtems_task_restart( Task_id[TASKID_PRC0], lfrRequestedMode );
886 status[1] = rtems_task_restart( Task_id[TASKID_PRC0], lfrRequestedMode );
886 if (status[1] != RTEMS_SUCCESSFUL)
887 if (status[1] != RTEMS_SUCCESSFUL)
887 {
888 {
888 PRINTF1("in restart_science_task *** PRC0 ERR %d\n", status[1])
889 PRINTF1("in restart_science_task *** PRC0 ERR %d\n", status[1])
889 }
890 }
890
891
891 status[2] = rtems_task_restart( Task_id[TASKID_WFRM],1 );
892 status[2] = rtems_task_restart( Task_id[TASKID_WFRM],1 );
892 if (status[2] != RTEMS_SUCCESSFUL)
893 if (status[2] != RTEMS_SUCCESSFUL)
893 {
894 {
894 PRINTF1("in restart_science_task *** WFRM ERR %d\n", status[2])
895 PRINTF1("in restart_science_task *** WFRM ERR %d\n", status[2])
895 }
896 }
896
897
897 status[3] = rtems_task_restart( Task_id[TASKID_CWF3],1 );
898 status[3] = rtems_task_restart( Task_id[TASKID_CWF3],1 );
898 if (status[3] != RTEMS_SUCCESSFUL)
899 if (status[3] != RTEMS_SUCCESSFUL)
899 {
900 {
900 PRINTF1("in restart_science_task *** CWF3 ERR %d\n", status[3])
901 PRINTF1("in restart_science_task *** CWF3 ERR %d\n", status[3])
901 }
902 }
902
903
903 status[4] = rtems_task_restart( Task_id[TASKID_CWF2],1 );
904 status[4] = rtems_task_restart( Task_id[TASKID_CWF2],1 );
904 if (status[4] != RTEMS_SUCCESSFUL)
905 if (status[4] != RTEMS_SUCCESSFUL)
905 {
906 {
906 PRINTF1("in restart_science_task *** CWF2 ERR %d\n", status[4])
907 PRINTF1("in restart_science_task *** CWF2 ERR %d\n", status[4])
907 }
908 }
908
909
909 status[5] = rtems_task_restart( Task_id[TASKID_CWF1],1 );
910 status[5] = rtems_task_restart( Task_id[TASKID_CWF1],1 );
910 if (status[5] != RTEMS_SUCCESSFUL)
911 if (status[5] != RTEMS_SUCCESSFUL)
911 {
912 {
912 PRINTF1("in restart_science_task *** CWF1 ERR %d\n", status[5])
913 PRINTF1("in restart_science_task *** CWF1 ERR %d\n", status[5])
913 }
914 }
914
915
915 status[6] = rtems_task_restart( Task_id[TASKID_AVF1], lfrRequestedMode );
916 status[6] = rtems_task_restart( Task_id[TASKID_AVF1], lfrRequestedMode );
916 if (status[6] != RTEMS_SUCCESSFUL)
917 if (status[6] != RTEMS_SUCCESSFUL)
917 {
918 {
918 PRINTF1("in restart_science_task *** AVF1 ERR %d\n", status[6])
919 PRINTF1("in restart_science_task *** AVF1 ERR %d\n", status[6])
919 }
920 }
920
921
921 status[7] = rtems_task_restart( Task_id[TASKID_PRC1],lfrRequestedMode );
922 status[7] = rtems_task_restart( Task_id[TASKID_PRC1],lfrRequestedMode );
922 if (status[7] != RTEMS_SUCCESSFUL)
923 if (status[7] != RTEMS_SUCCESSFUL)
923 {
924 {
924 PRINTF1("in restart_science_task *** PRC1 ERR %d\n", status[7])
925 PRINTF1("in restart_science_task *** PRC1 ERR %d\n", status[7])
925 }
926 }
926
927
927 status[8] = rtems_task_restart( Task_id[TASKID_AVF2], 1 );
928 status[8] = rtems_task_restart( Task_id[TASKID_AVF2], 1 );
928 if (status[8] != RTEMS_SUCCESSFUL)
929 if (status[8] != RTEMS_SUCCESSFUL)
929 {
930 {
930 PRINTF1("in restart_science_task *** AVF2 ERR %d\n", status[8])
931 PRINTF1("in restart_science_task *** AVF2 ERR %d\n", status[8])
931 }
932 }
932
933
933 status[9] = rtems_task_restart( Task_id[TASKID_PRC2], 1 );
934 status[9] = rtems_task_restart( Task_id[TASKID_PRC2], 1 );
934 if (status[9] != RTEMS_SUCCESSFUL)
935 if (status[9] != RTEMS_SUCCESSFUL)
935 {
936 {
936 PRINTF1("in restart_science_task *** PRC2 ERR %d\n", status[9])
937 PRINTF1("in restart_science_task *** PRC2 ERR %d\n", status[9])
937 }
938 }
938
939
939 if ( (status[0] != RTEMS_SUCCESSFUL) || (status[1] != RTEMS_SUCCESSFUL) ||
940 if ( (status[0] != RTEMS_SUCCESSFUL) || (status[1] != RTEMS_SUCCESSFUL) ||
940 (status[2] != RTEMS_SUCCESSFUL) || (status[3] != RTEMS_SUCCESSFUL) ||
941 (status[2] != RTEMS_SUCCESSFUL) || (status[3] != RTEMS_SUCCESSFUL) ||
941 (status[4] != RTEMS_SUCCESSFUL) || (status[5] != RTEMS_SUCCESSFUL) ||
942 (status[4] != RTEMS_SUCCESSFUL) || (status[5] != RTEMS_SUCCESSFUL) ||
942 (status[6] != RTEMS_SUCCESSFUL) || (status[7] != RTEMS_SUCCESSFUL) ||
943 (status[6] != RTEMS_SUCCESSFUL) || (status[7] != RTEMS_SUCCESSFUL) ||
943 (status[8] != RTEMS_SUCCESSFUL) || (status[9] != RTEMS_SUCCESSFUL) )
944 (status[8] != RTEMS_SUCCESSFUL) || (status[9] != RTEMS_SUCCESSFUL) )
944 {
945 {
945 ret = RTEMS_UNSATISFIED;
946 ret = RTEMS_UNSATISFIED;
946 }
947 }
947
948
948 return ret;
949 return ret;
949 }
950 }
950
951
951 int restart_asm_tasks( unsigned char lfrRequestedMode )
952 int restart_asm_tasks( unsigned char lfrRequestedMode )
952 {
953 {
953 /** This function is used to restart average spectral matrices tasks.
954 /** This function is used to restart average spectral matrices tasks.
954 *
955 *
955 * @return RTEMS directive status codes:
956 * @return RTEMS directive status codes:
956 * - RTEMS_SUCCESSFUL - task restarted successfully
957 * - RTEMS_SUCCESSFUL - task restarted successfully
957 * - RTEMS_INVALID_ID - task id invalid
958 * - RTEMS_INVALID_ID - task id invalid
958 * - RTEMS_INCORRECT_STATE - task never started
959 * - RTEMS_INCORRECT_STATE - task never started
959 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
960 * - RTEMS_ILLEGAL_ON_REMOTE_OBJECT - cannot restart remote task
960 *
961 *
961 * ASM tasks are AVF0, PRC0, AVF1, PRC1, AVF2 and PRC2
962 * ASM tasks are AVF0, PRC0, AVF1, PRC1, AVF2 and PRC2
962 *
963 *
963 */
964 */
964
965
965 rtems_status_code status[6];
966 rtems_status_code status[6];
966 rtems_status_code ret;
967 rtems_status_code ret;
967
968
968 ret = RTEMS_SUCCESSFUL;
969 ret = RTEMS_SUCCESSFUL;
969
970
970 status[0] = rtems_task_restart( Task_id[TASKID_AVF0], lfrRequestedMode );
971 status[0] = rtems_task_restart( Task_id[TASKID_AVF0], lfrRequestedMode );
971 if (status[0] != RTEMS_SUCCESSFUL)
972 if (status[0] != RTEMS_SUCCESSFUL)
972 {
973 {
973 PRINTF1("in restart_science_task *** AVF0 ERR %d\n", status[0])
974 PRINTF1("in restart_science_task *** AVF0 ERR %d\n", status[0])
974 }
975 }
975
976
976 status[1] = rtems_task_restart( Task_id[TASKID_PRC0], lfrRequestedMode );
977 status[1] = rtems_task_restart( Task_id[TASKID_PRC0], lfrRequestedMode );
977 if (status[1] != RTEMS_SUCCESSFUL)
978 if (status[1] != RTEMS_SUCCESSFUL)
978 {
979 {
979 PRINTF1("in restart_science_task *** PRC0 ERR %d\n", status[1])
980 PRINTF1("in restart_science_task *** PRC0 ERR %d\n", status[1])
980 }
981 }
981
982
982 status[2] = rtems_task_restart( Task_id[TASKID_AVF1], lfrRequestedMode );
983 status[2] = rtems_task_restart( Task_id[TASKID_AVF1], lfrRequestedMode );
983 if (status[2] != RTEMS_SUCCESSFUL)
984 if (status[2] != RTEMS_SUCCESSFUL)
984 {
985 {
985 PRINTF1("in restart_science_task *** AVF1 ERR %d\n", status[2])
986 PRINTF1("in restart_science_task *** AVF1 ERR %d\n", status[2])
986 }
987 }
987
988
988 status[3] = rtems_task_restart( Task_id[TASKID_PRC1],lfrRequestedMode );
989 status[3] = rtems_task_restart( Task_id[TASKID_PRC1],lfrRequestedMode );
989 if (status[3] != RTEMS_SUCCESSFUL)
990 if (status[3] != RTEMS_SUCCESSFUL)
990 {
991 {
991 PRINTF1("in restart_science_task *** PRC1 ERR %d\n", status[3])
992 PRINTF1("in restart_science_task *** PRC1 ERR %d\n", status[3])
992 }
993 }
993
994
994 status[4] = rtems_task_restart( Task_id[TASKID_AVF2], 1 );
995 status[4] = rtems_task_restart( Task_id[TASKID_AVF2], 1 );
995 if (status[4] != RTEMS_SUCCESSFUL)
996 if (status[4] != RTEMS_SUCCESSFUL)
996 {
997 {
997 PRINTF1("in restart_science_task *** AVF2 ERR %d\n", status[4])
998 PRINTF1("in restart_science_task *** AVF2 ERR %d\n", status[4])
998 }
999 }
999
1000
1000 status[5] = rtems_task_restart( Task_id[TASKID_PRC2], 1 );
1001 status[5] = rtems_task_restart( Task_id[TASKID_PRC2], 1 );
1001 if (status[5] != RTEMS_SUCCESSFUL)
1002 if (status[5] != RTEMS_SUCCESSFUL)
1002 {
1003 {
1003 PRINTF1("in restart_science_task *** PRC2 ERR %d\n", status[5])
1004 PRINTF1("in restart_science_task *** PRC2 ERR %d\n", status[5])
1004 }
1005 }
1005
1006
1006 if ( (status[0] != RTEMS_SUCCESSFUL) || (status[1] != RTEMS_SUCCESSFUL) ||
1007 if ( (status[0] != RTEMS_SUCCESSFUL) || (status[1] != RTEMS_SUCCESSFUL) ||
1007 (status[2] != RTEMS_SUCCESSFUL) || (status[3] != RTEMS_SUCCESSFUL) ||
1008 (status[2] != RTEMS_SUCCESSFUL) || (status[3] != RTEMS_SUCCESSFUL) ||
1008 (status[4] != RTEMS_SUCCESSFUL) || (status[5] != RTEMS_SUCCESSFUL) )
1009 (status[4] != RTEMS_SUCCESSFUL) || (status[5] != RTEMS_SUCCESSFUL) )
1009 {
1010 {
1010 ret = RTEMS_UNSATISFIED;
1011 ret = RTEMS_UNSATISFIED;
1011 }
1012 }
1012
1013
1013 return ret;
1014 return ret;
1014 }
1015 }
1015
1016
1016 int suspend_science_tasks( void )
1017 int suspend_science_tasks( void )
1017 {
1018 {
1018 /** This function suspends the science tasks.
1019 /** This function suspends the science tasks.
1019 *
1020 *
1020 * @return RTEMS directive status codes:
1021 * @return RTEMS directive status codes:
1021 * - RTEMS_SUCCESSFUL - task restarted successfully
1022 * - RTEMS_SUCCESSFUL - task restarted successfully
1022 * - RTEMS_INVALID_ID - task id invalid
1023 * - RTEMS_INVALID_ID - task id invalid
1023 * - RTEMS_ALREADY_SUSPENDED - task already suspended
1024 * - RTEMS_ALREADY_SUSPENDED - task already suspended
1024 *
1025 *
1025 */
1026 */
1026
1027
1027 rtems_status_code status;
1028 rtems_status_code status;
1028
1029
1029 PRINTF("in suspend_science_tasks\n")
1030 PRINTF("in suspend_science_tasks\n")
1030
1031
1031 status = rtems_task_suspend( Task_id[TASKID_AVF0] ); // suspend AVF0
1032 status = rtems_task_suspend( Task_id[TASKID_AVF0] ); // suspend AVF0
1032 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1033 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1033 {
1034 {
1034 PRINTF1("in suspend_science_task *** AVF0 ERR %d\n", status)
1035 PRINTF1("in suspend_science_task *** AVF0 ERR %d\n", status)
1035 }
1036 }
1036 else
1037 else
1037 {
1038 {
1038 status = RTEMS_SUCCESSFUL;
1039 status = RTEMS_SUCCESSFUL;
1039 }
1040 }
1040 if (status == RTEMS_SUCCESSFUL) // suspend PRC0
1041 if (status == RTEMS_SUCCESSFUL) // suspend PRC0
1041 {
1042 {
1042 status = rtems_task_suspend( Task_id[TASKID_PRC0] );
1043 status = rtems_task_suspend( Task_id[TASKID_PRC0] );
1043 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1044 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1044 {
1045 {
1045 PRINTF1("in suspend_science_task *** PRC0 ERR %d\n", status)
1046 PRINTF1("in suspend_science_task *** PRC0 ERR %d\n", status)
1046 }
1047 }
1047 else
1048 else
1048 {
1049 {
1049 status = RTEMS_SUCCESSFUL;
1050 status = RTEMS_SUCCESSFUL;
1050 }
1051 }
1051 }
1052 }
1052 if (status == RTEMS_SUCCESSFUL) // suspend AVF1
1053 if (status == RTEMS_SUCCESSFUL) // suspend AVF1
1053 {
1054 {
1054 status = rtems_task_suspend( Task_id[TASKID_AVF1] );
1055 status = rtems_task_suspend( Task_id[TASKID_AVF1] );
1055 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1056 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1056 {
1057 {
1057 PRINTF1("in suspend_science_task *** AVF1 ERR %d\n", status)
1058 PRINTF1("in suspend_science_task *** AVF1 ERR %d\n", status)
1058 }
1059 }
1059 else
1060 else
1060 {
1061 {
1061 status = RTEMS_SUCCESSFUL;
1062 status = RTEMS_SUCCESSFUL;
1062 }
1063 }
1063 }
1064 }
1064 if (status == RTEMS_SUCCESSFUL) // suspend PRC1
1065 if (status == RTEMS_SUCCESSFUL) // suspend PRC1
1065 {
1066 {
1066 status = rtems_task_suspend( Task_id[TASKID_PRC1] );
1067 status = rtems_task_suspend( Task_id[TASKID_PRC1] );
1067 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1068 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1068 {
1069 {
1069 PRINTF1("in suspend_science_task *** PRC1 ERR %d\n", status)
1070 PRINTF1("in suspend_science_task *** PRC1 ERR %d\n", status)
1070 }
1071 }
1071 else
1072 else
1072 {
1073 {
1073 status = RTEMS_SUCCESSFUL;
1074 status = RTEMS_SUCCESSFUL;
1074 }
1075 }
1075 }
1076 }
1076 if (status == RTEMS_SUCCESSFUL) // suspend AVF2
1077 if (status == RTEMS_SUCCESSFUL) // suspend AVF2
1077 {
1078 {
1078 status = rtems_task_suspend( Task_id[TASKID_AVF2] );
1079 status = rtems_task_suspend( Task_id[TASKID_AVF2] );
1079 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1080 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1080 {
1081 {
1081 PRINTF1("in suspend_science_task *** AVF2 ERR %d\n", status)
1082 PRINTF1("in suspend_science_task *** AVF2 ERR %d\n", status)
1082 }
1083 }
1083 else
1084 else
1084 {
1085 {
1085 status = RTEMS_SUCCESSFUL;
1086 status = RTEMS_SUCCESSFUL;
1086 }
1087 }
1087 }
1088 }
1088 if (status == RTEMS_SUCCESSFUL) // suspend PRC2
1089 if (status == RTEMS_SUCCESSFUL) // suspend PRC2
1089 {
1090 {
1090 status = rtems_task_suspend( Task_id[TASKID_PRC2] );
1091 status = rtems_task_suspend( Task_id[TASKID_PRC2] );
1091 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1092 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1092 {
1093 {
1093 PRINTF1("in suspend_science_task *** PRC2 ERR %d\n", status)
1094 PRINTF1("in suspend_science_task *** PRC2 ERR %d\n", status)
1094 }
1095 }
1095 else
1096 else
1096 {
1097 {
1097 status = RTEMS_SUCCESSFUL;
1098 status = RTEMS_SUCCESSFUL;
1098 }
1099 }
1099 }
1100 }
1100 if (status == RTEMS_SUCCESSFUL) // suspend WFRM
1101 if (status == RTEMS_SUCCESSFUL) // suspend WFRM
1101 {
1102 {
1102 status = rtems_task_suspend( Task_id[TASKID_WFRM] );
1103 status = rtems_task_suspend( Task_id[TASKID_WFRM] );
1103 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1104 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1104 {
1105 {
1105 PRINTF1("in suspend_science_task *** WFRM ERR %d\n", status)
1106 PRINTF1("in suspend_science_task *** WFRM ERR %d\n", status)
1106 }
1107 }
1107 else
1108 else
1108 {
1109 {
1109 status = RTEMS_SUCCESSFUL;
1110 status = RTEMS_SUCCESSFUL;
1110 }
1111 }
1111 }
1112 }
1112 if (status == RTEMS_SUCCESSFUL) // suspend CWF3
1113 if (status == RTEMS_SUCCESSFUL) // suspend CWF3
1113 {
1114 {
1114 status = rtems_task_suspend( Task_id[TASKID_CWF3] );
1115 status = rtems_task_suspend( Task_id[TASKID_CWF3] );
1115 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1116 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1116 {
1117 {
1117 PRINTF1("in suspend_science_task *** CWF3 ERR %d\n", status)
1118 PRINTF1("in suspend_science_task *** CWF3 ERR %d\n", status)
1118 }
1119 }
1119 else
1120 else
1120 {
1121 {
1121 status = RTEMS_SUCCESSFUL;
1122 status = RTEMS_SUCCESSFUL;
1122 }
1123 }
1123 }
1124 }
1124 if (status == RTEMS_SUCCESSFUL) // suspend CWF2
1125 if (status == RTEMS_SUCCESSFUL) // suspend CWF2
1125 {
1126 {
1126 status = rtems_task_suspend( Task_id[TASKID_CWF2] );
1127 status = rtems_task_suspend( Task_id[TASKID_CWF2] );
1127 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1128 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1128 {
1129 {
1129 PRINTF1("in suspend_science_task *** CWF2 ERR %d\n", status)
1130 PRINTF1("in suspend_science_task *** CWF2 ERR %d\n", status)
1130 }
1131 }
1131 else
1132 else
1132 {
1133 {
1133 status = RTEMS_SUCCESSFUL;
1134 status = RTEMS_SUCCESSFUL;
1134 }
1135 }
1135 }
1136 }
1136 if (status == RTEMS_SUCCESSFUL) // suspend CWF1
1137 if (status == RTEMS_SUCCESSFUL) // suspend CWF1
1137 {
1138 {
1138 status = rtems_task_suspend( Task_id[TASKID_CWF1] );
1139 status = rtems_task_suspend( Task_id[TASKID_CWF1] );
1139 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1140 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1140 {
1141 {
1141 PRINTF1("in suspend_science_task *** CWF1 ERR %d\n", status)
1142 PRINTF1("in suspend_science_task *** CWF1 ERR %d\n", status)
1142 }
1143 }
1143 else
1144 else
1144 {
1145 {
1145 status = RTEMS_SUCCESSFUL;
1146 status = RTEMS_SUCCESSFUL;
1146 }
1147 }
1147 }
1148 }
1148
1149
1149 return status;
1150 return status;
1150 }
1151 }
1151
1152
1152 int suspend_asm_tasks( void )
1153 int suspend_asm_tasks( void )
1153 {
1154 {
1154 /** This function suspends the science tasks.
1155 /** This function suspends the science tasks.
1155 *
1156 *
1156 * @return RTEMS directive status codes:
1157 * @return RTEMS directive status codes:
1157 * - RTEMS_SUCCESSFUL - task restarted successfully
1158 * - RTEMS_SUCCESSFUL - task restarted successfully
1158 * - RTEMS_INVALID_ID - task id invalid
1159 * - RTEMS_INVALID_ID - task id invalid
1159 * - RTEMS_ALREADY_SUSPENDED - task already suspended
1160 * - RTEMS_ALREADY_SUSPENDED - task already suspended
1160 *
1161 *
1161 */
1162 */
1162
1163
1163 rtems_status_code status;
1164 rtems_status_code status;
1164
1165
1165 PRINTF("in suspend_science_tasks\n")
1166 PRINTF("in suspend_science_tasks\n")
1166
1167
1167 status = rtems_task_suspend( Task_id[TASKID_AVF0] ); // suspend AVF0
1168 status = rtems_task_suspend( Task_id[TASKID_AVF0] ); // suspend AVF0
1168 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1169 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1169 {
1170 {
1170 PRINTF1("in suspend_science_task *** AVF0 ERR %d\n", status)
1171 PRINTF1("in suspend_science_task *** AVF0 ERR %d\n", status)
1171 }
1172 }
1172 else
1173 else
1173 {
1174 {
1174 status = RTEMS_SUCCESSFUL;
1175 status = RTEMS_SUCCESSFUL;
1175 }
1176 }
1176
1177
1177 if (status == RTEMS_SUCCESSFUL) // suspend PRC0
1178 if (status == RTEMS_SUCCESSFUL) // suspend PRC0
1178 {
1179 {
1179 status = rtems_task_suspend( Task_id[TASKID_PRC0] );
1180 status = rtems_task_suspend( Task_id[TASKID_PRC0] );
1180 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1181 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1181 {
1182 {
1182 PRINTF1("in suspend_science_task *** PRC0 ERR %d\n", status)
1183 PRINTF1("in suspend_science_task *** PRC0 ERR %d\n", status)
1183 }
1184 }
1184 else
1185 else
1185 {
1186 {
1186 status = RTEMS_SUCCESSFUL;
1187 status = RTEMS_SUCCESSFUL;
1187 }
1188 }
1188 }
1189 }
1189
1190
1190 if (status == RTEMS_SUCCESSFUL) // suspend AVF1
1191 if (status == RTEMS_SUCCESSFUL) // suspend AVF1
1191 {
1192 {
1192 status = rtems_task_suspend( Task_id[TASKID_AVF1] );
1193 status = rtems_task_suspend( Task_id[TASKID_AVF1] );
1193 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1194 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1194 {
1195 {
1195 PRINTF1("in suspend_science_task *** AVF1 ERR %d\n", status)
1196 PRINTF1("in suspend_science_task *** AVF1 ERR %d\n", status)
1196 }
1197 }
1197 else
1198 else
1198 {
1199 {
1199 status = RTEMS_SUCCESSFUL;
1200 status = RTEMS_SUCCESSFUL;
1200 }
1201 }
1201 }
1202 }
1202
1203
1203 if (status == RTEMS_SUCCESSFUL) // suspend PRC1
1204 if (status == RTEMS_SUCCESSFUL) // suspend PRC1
1204 {
1205 {
1205 status = rtems_task_suspend( Task_id[TASKID_PRC1] );
1206 status = rtems_task_suspend( Task_id[TASKID_PRC1] );
1206 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1207 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1207 {
1208 {
1208 PRINTF1("in suspend_science_task *** PRC1 ERR %d\n", status)
1209 PRINTF1("in suspend_science_task *** PRC1 ERR %d\n", status)
1209 }
1210 }
1210 else
1211 else
1211 {
1212 {
1212 status = RTEMS_SUCCESSFUL;
1213 status = RTEMS_SUCCESSFUL;
1213 }
1214 }
1214 }
1215 }
1215
1216
1216 if (status == RTEMS_SUCCESSFUL) // suspend AVF2
1217 if (status == RTEMS_SUCCESSFUL) // suspend AVF2
1217 {
1218 {
1218 status = rtems_task_suspend( Task_id[TASKID_AVF2] );
1219 status = rtems_task_suspend( Task_id[TASKID_AVF2] );
1219 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1220 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1220 {
1221 {
1221 PRINTF1("in suspend_science_task *** AVF2 ERR %d\n", status)
1222 PRINTF1("in suspend_science_task *** AVF2 ERR %d\n", status)
1222 }
1223 }
1223 else
1224 else
1224 {
1225 {
1225 status = RTEMS_SUCCESSFUL;
1226 status = RTEMS_SUCCESSFUL;
1226 }
1227 }
1227 }
1228 }
1228
1229
1229 if (status == RTEMS_SUCCESSFUL) // suspend PRC2
1230 if (status == RTEMS_SUCCESSFUL) // suspend PRC2
1230 {
1231 {
1231 status = rtems_task_suspend( Task_id[TASKID_PRC2] );
1232 status = rtems_task_suspend( Task_id[TASKID_PRC2] );
1232 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1233 if ((status != RTEMS_SUCCESSFUL) && (status != RTEMS_ALREADY_SUSPENDED))
1233 {
1234 {
1234 PRINTF1("in suspend_science_task *** PRC2 ERR %d\n", status)
1235 PRINTF1("in suspend_science_task *** PRC2 ERR %d\n", status)
1235 }
1236 }
1236 else
1237 else
1237 {
1238 {
1238 status = RTEMS_SUCCESSFUL;
1239 status = RTEMS_SUCCESSFUL;
1239 }
1240 }
1240 }
1241 }
1241
1242
1242 return status;
1243 return status;
1243 }
1244 }
1244
1245
1245 void launch_waveform_picker( unsigned char mode, unsigned int transitionCoarseTime )
1246 void launch_waveform_picker( unsigned char mode, unsigned int transitionCoarseTime )
1246 {
1247 {
1247 WFP_reset_current_ring_nodes();
1248 WFP_reset_current_ring_nodes();
1248
1249
1249 reset_waveform_picker_regs();
1250 reset_waveform_picker_regs();
1250
1251
1251 set_wfp_burst_enable_register( mode );
1252 set_wfp_burst_enable_register( mode );
1252
1253
1253 LEON_Clear_interrupt( IRQ_WAVEFORM_PICKER );
1254 LEON_Clear_interrupt( IRQ_WAVEFORM_PICKER );
1254 LEON_Unmask_interrupt( IRQ_WAVEFORM_PICKER );
1255 LEON_Unmask_interrupt( IRQ_WAVEFORM_PICKER );
1255
1256
1256 if (transitionCoarseTime == 0)
1257 if (transitionCoarseTime == 0)
1257 {
1258 {
1258 // instant transition means transition on the next valid date
1259 // instant transition means transition on the next valid date
1259 // this is mandatory to have a good snapshot period a a good correction of the snapshot period
1260 // this is mandatory to have a good snapshot period a a good correction of the snapshot period
1260 waveform_picker_regs->start_date = time_management_regs->coarse_time + 1;
1261 waveform_picker_regs->start_date = time_management_regs->coarse_time + 1;
1261 }
1262 }
1262 else
1263 else
1263 {
1264 {
1264 waveform_picker_regs->start_date = transitionCoarseTime;
1265 waveform_picker_regs->start_date = transitionCoarseTime;
1265 }
1266 }
1266
1267
1267 }
1268 }
1268
1269
1269 void launch_spectral_matrix( void )
1270 void launch_spectral_matrix( void )
1270 {
1271 {
1271 SM_reset_current_ring_nodes();
1272 SM_reset_current_ring_nodes();
1272
1273
1273 reset_spectral_matrix_regs();
1274 reset_spectral_matrix_regs();
1274
1275
1275 reset_nb_sm();
1276 reset_nb_sm();
1276
1277
1277 set_sm_irq_onNewMatrix( 1 );
1278 set_sm_irq_onNewMatrix( 1 );
1278
1279
1279 LEON_Clear_interrupt( IRQ_SPECTRAL_MATRIX );
1280 LEON_Clear_interrupt( IRQ_SPECTRAL_MATRIX );
1280 LEON_Unmask_interrupt( IRQ_SPECTRAL_MATRIX );
1281 LEON_Unmask_interrupt( IRQ_SPECTRAL_MATRIX );
1281
1282
1282 }
1283 }
1283
1284
1284 void set_sm_irq_onNewMatrix( unsigned char value )
1285 void set_sm_irq_onNewMatrix( unsigned char value )
1285 {
1286 {
1286 if (value == 1)
1287 if (value == 1)
1287 {
1288 {
1288 spectral_matrix_regs->config = spectral_matrix_regs->config | 0x01;
1289 spectral_matrix_regs->config = spectral_matrix_regs->config | 0x01;
1289 }
1290 }
1290 else
1291 else
1291 {
1292 {
1292 spectral_matrix_regs->config = spectral_matrix_regs->config & 0xfffffffe; // 1110
1293 spectral_matrix_regs->config = spectral_matrix_regs->config & 0xfffffffe; // 1110
1293 }
1294 }
1294 }
1295 }
1295
1296
1296 void set_sm_irq_onError( unsigned char value )
1297 void set_sm_irq_onError( unsigned char value )
1297 {
1298 {
1298 if (value == 1)
1299 if (value == 1)
1299 {
1300 {
1300 spectral_matrix_regs->config = spectral_matrix_regs->config | 0x02;
1301 spectral_matrix_regs->config = spectral_matrix_regs->config | 0x02;
1301 }
1302 }
1302 else
1303 else
1303 {
1304 {
1304 spectral_matrix_regs->config = spectral_matrix_regs->config & 0xfffffffd; // 1101
1305 spectral_matrix_regs->config = spectral_matrix_regs->config & 0xfffffffd; // 1101
1305 }
1306 }
1306 }
1307 }
1307
1308
1308 //*****************************
1309 //*****************************
1309 // CONFIGURE CALIBRATION SIGNAL
1310 // CONFIGURE CALIBRATION SIGNAL
1310 void setCalibrationPrescaler( unsigned int prescaler )
1311 void setCalibrationPrescaler( unsigned int prescaler )
1311 {
1312 {
1312 // prescaling of the master clock (25 MHz)
1313 // prescaling of the master clock (25 MHz)
1313 // master clock is divided by 2^prescaler
1314 // master clock is divided by 2^prescaler
1314 time_management_regs->calPrescaler = prescaler;
1315 time_management_regs->calPrescaler = prescaler;
1315 }
1316 }
1316
1317
1317 void setCalibrationDivisor( unsigned int divisionFactor )
1318 void setCalibrationDivisor( unsigned int divisionFactor )
1318 {
1319 {
1319 // division of the prescaled clock by the division factor
1320 // division of the prescaled clock by the division factor
1320 time_management_regs->calDivisor = divisionFactor;
1321 time_management_regs->calDivisor = divisionFactor;
1321 }
1322 }
1322
1323
1323 void setCalibrationData( void ){
1324 void setCalibrationData( void ){
1324 unsigned int k;
1325 unsigned int k;
1325 unsigned short data;
1326 unsigned short data;
1326 float val;
1327 float val;
1327 float f0;
1328 float f0;
1328 float f1;
1329 float f1;
1329 float fs;
1330 float fs;
1330 float Ts;
1331 float Ts;
1331 float scaleFactor;
1332 float scaleFactor;
1332
1333
1333 f0 = 625;
1334 f0 = 625;
1334 f1 = 10000;
1335 f1 = 10000;
1335 fs = 160256.410;
1336 fs = 160256.410;
1336 Ts = 1. / fs;
1337 Ts = 1. / fs;
1337 scaleFactor = 0.250 / 0.000654; // 191, 500 mVpp, 2 sinus waves => 500 mVpp each, amplitude = 250 mV
1338 scaleFactor = 0.250 / 0.000654; // 191, 500 mVpp, 2 sinus waves => 500 mVpp each, amplitude = 250 mV
1338
1339
1339 time_management_regs->calDataPtr = 0x00;
1340 time_management_regs->calDataPtr = 0x00;
1340
1341
1341 // build the signal for the SCM calibration
1342 // build the signal for the SCM calibration
1342 for (k=0; k<256; k++)
1343 for (k=0; k<256; k++)
1343 {
1344 {
1344 val = sin( 2 * pi * f0 * k * Ts )
1345 val = sin( 2 * pi * f0 * k * Ts )
1345 + sin( 2 * pi * f1 * k * Ts );
1346 + sin( 2 * pi * f1 * k * Ts );
1346 data = (unsigned short) ((val * scaleFactor) + 2048);
1347 data = (unsigned short) ((val * scaleFactor) + 2048);
1347 time_management_regs->calData = data & 0xfff;
1348 time_management_regs->calData = data & 0xfff;
1348 }
1349 }
1349 }
1350 }
1350
1351
1351 void setCalibrationDataInterleaved( void ){
1352 void setCalibrationDataInterleaved( void ){
1352 unsigned int k;
1353 unsigned int k;
1353 float val;
1354 float val;
1354 float f0;
1355 float f0;
1355 float f1;
1356 float f1;
1356 float fs;
1357 float fs;
1357 float Ts;
1358 float Ts;
1358 unsigned short data[384];
1359 unsigned short data[384];
1359 unsigned char *dataPtr;
1360 unsigned char *dataPtr;
1360
1361
1361 f0 = 625;
1362 f0 = 625;
1362 f1 = 10000;
1363 f1 = 10000;
1363 fs = 240384.615;
1364 fs = 240384.615;
1364 Ts = 1. / fs;
1365 Ts = 1. / fs;
1365
1366
1366 time_management_regs->calDataPtr = 0x00;
1367 time_management_regs->calDataPtr = 0x00;
1367
1368
1368 // build the signal for the SCM calibration
1369 // build the signal for the SCM calibration
1369 for (k=0; k<384; k++)
1370 for (k=0; k<384; k++)
1370 {
1371 {
1371 val = sin( 2 * pi * f0 * k * Ts )
1372 val = sin( 2 * pi * f0 * k * Ts )
1372 + sin( 2 * pi * f1 * k * Ts );
1373 + sin( 2 * pi * f1 * k * Ts );
1373 data[k] = (unsigned short) (val * 512 + 2048);
1374 data[k] = (unsigned short) (val * 512 + 2048);
1374 }
1375 }
1375
1376
1376 // write the signal in interleaved mode
1377 // write the signal in interleaved mode
1377 for (k=0; k<128; k++)
1378 for (k=0; k<128; k++)
1378 {
1379 {
1379 dataPtr = (unsigned char*) &data[k*3 + 2];
1380 dataPtr = (unsigned char*) &data[k*3 + 2];
1380 time_management_regs->calData = (data[k*3] & 0xfff)
1381 time_management_regs->calData = (data[k*3] & 0xfff)
1381 + ( (dataPtr[0] & 0x3f) << 12);
1382 + ( (dataPtr[0] & 0x3f) << 12);
1382 time_management_regs->calData = (data[k*3 + 1] & 0xfff)
1383 time_management_regs->calData = (data[k*3 + 1] & 0xfff)
1383 + ( (dataPtr[1] & 0x3f) << 12);
1384 + ( (dataPtr[1] & 0x3f) << 12);
1384 }
1385 }
1385 }
1386 }
1386
1387
1387 void setCalibrationReload( bool state)
1388 void setCalibrationReload( bool state)
1388 {
1389 {
1389 if (state == true)
1390 if (state == true)
1390 {
1391 {
1391 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl | 0x00000010; // [0001 0000]
1392 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl | 0x00000010; // [0001 0000]
1392 }
1393 }
1393 else
1394 else
1394 {
1395 {
1395 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl & 0xffffffef; // [1110 1111]
1396 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl & 0xffffffef; // [1110 1111]
1396 }
1397 }
1397 }
1398 }
1398
1399
1399 void setCalibrationEnable( bool state )
1400 void setCalibrationEnable( bool state )
1400 {
1401 {
1401 // this bit drives the multiplexer
1402 // this bit drives the multiplexer
1402 if (state == true)
1403 if (state == true)
1403 {
1404 {
1404 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl | 0x00000040; // [0100 0000]
1405 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl | 0x00000040; // [0100 0000]
1405 }
1406 }
1406 else
1407 else
1407 {
1408 {
1408 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl & 0xffffffbf; // [1011 1111]
1409 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl & 0xffffffbf; // [1011 1111]
1409 }
1410 }
1410 }
1411 }
1411
1412
1412 void setCalibrationInterleaved( bool state )
1413 void setCalibrationInterleaved( bool state )
1413 {
1414 {
1414 // this bit drives the multiplexer
1415 // this bit drives the multiplexer
1415 if (state == true)
1416 if (state == true)
1416 {
1417 {
1417 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl | 0x00000020; // [0010 0000]
1418 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl | 0x00000020; // [0010 0000]
1418 }
1419 }
1419 else
1420 else
1420 {
1421 {
1421 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl & 0xffffffdf; // [1101 1111]
1422 time_management_regs->calDACCtrl = time_management_regs->calDACCtrl & 0xffffffdf; // [1101 1111]
1422 }
1423 }
1423 }
1424 }
1424
1425
1425 void setCalibration( bool state )
1426 void setCalibration( bool state )
1426 {
1427 {
1427 if (state == true)
1428 if (state == true)
1428 {
1429 {
1429 setCalibrationEnable( true );
1430 setCalibrationEnable( true );
1430 setCalibrationReload( false );
1431 setCalibrationReload( false );
1431 set_hk_lfr_calib_enable( true );
1432 set_hk_lfr_calib_enable( true );
1432 }
1433 }
1433 else
1434 else
1434 {
1435 {
1435 setCalibrationEnable( false );
1436 setCalibrationEnable( false );
1436 setCalibrationReload( true );
1437 setCalibrationReload( true );
1437 set_hk_lfr_calib_enable( false );
1438 set_hk_lfr_calib_enable( false );
1438 }
1439 }
1439 }
1440 }
1440
1441
1441 void configureCalibration( bool interleaved )
1442 void configureCalibration( bool interleaved )
1442 {
1443 {
1443 setCalibration( false );
1444 setCalibration( false );
1444 if ( interleaved == true )
1445 if ( interleaved == true )
1445 {
1446 {
1446 setCalibrationInterleaved( true );
1447 setCalibrationInterleaved( true );
1447 setCalibrationPrescaler( 0 ); // 25 MHz => 25 000 000
1448 setCalibrationPrescaler( 0 ); // 25 MHz => 25 000 000
1448 setCalibrationDivisor( 26 ); // => 240 384
1449 setCalibrationDivisor( 26 ); // => 240 384
1449 setCalibrationDataInterleaved();
1450 setCalibrationDataInterleaved();
1450 }
1451 }
1451 else
1452 else
1452 {
1453 {
1453 setCalibrationPrescaler( 0 ); // 25 MHz => 25 000 000
1454 setCalibrationPrescaler( 0 ); // 25 MHz => 25 000 000
1454 setCalibrationDivisor( 38 ); // => 160 256 (39 - 1)
1455 setCalibrationDivisor( 38 ); // => 160 256 (39 - 1)
1455 setCalibrationData();
1456 setCalibrationData();
1456 }
1457 }
1457 }
1458 }
1458
1459
1459 //****************
1460 //****************
1460 // CLOSING ACTIONS
1461 // CLOSING ACTIONS
1461 void update_last_TC_exe( ccsdsTelecommandPacket_t *TC, unsigned char * time )
1462 void update_last_TC_exe( ccsdsTelecommandPacket_t *TC, unsigned char * time )
1462 {
1463 {
1463 /** This function is used to update the HK packets statistics after a successful TC execution.
1464 /** This function is used to update the HK packets statistics after a successful TC execution.
1464 *
1465 *
1465 * @param TC points to the TC being processed
1466 * @param TC points to the TC being processed
1466 * @param time is the time used to date the TC execution
1467 * @param time is the time used to date the TC execution
1467 *
1468 *
1468 */
1469 */
1469
1470
1470 unsigned int val;
1471 unsigned int val;
1471
1472
1472 housekeeping_packet.hk_lfr_last_exe_tc_id[0] = TC->packetID[0];
1473 housekeeping_packet.hk_lfr_last_exe_tc_id[0] = TC->packetID[0];
1473 housekeeping_packet.hk_lfr_last_exe_tc_id[1] = TC->packetID[1];
1474 housekeeping_packet.hk_lfr_last_exe_tc_id[1] = TC->packetID[1];
1474 housekeeping_packet.hk_lfr_last_exe_tc_type[0] = 0x00;
1475 housekeeping_packet.hk_lfr_last_exe_tc_type[0] = 0x00;
1475 housekeeping_packet.hk_lfr_last_exe_tc_type[1] = TC->serviceType;
1476 housekeeping_packet.hk_lfr_last_exe_tc_type[1] = TC->serviceType;
1476 housekeeping_packet.hk_lfr_last_exe_tc_subtype[0] = 0x00;
1477 housekeeping_packet.hk_lfr_last_exe_tc_subtype[0] = 0x00;
1477 housekeeping_packet.hk_lfr_last_exe_tc_subtype[1] = TC->serviceSubType;
1478 housekeeping_packet.hk_lfr_last_exe_tc_subtype[1] = TC->serviceSubType;
1478 housekeeping_packet.hk_lfr_last_exe_tc_time[0] = time[0];
1479 housekeeping_packet.hk_lfr_last_exe_tc_time[0] = time[0];
1479 housekeeping_packet.hk_lfr_last_exe_tc_time[1] = time[1];
1480 housekeeping_packet.hk_lfr_last_exe_tc_time[1] = time[1];
1480 housekeeping_packet.hk_lfr_last_exe_tc_time[2] = time[2];
1481 housekeeping_packet.hk_lfr_last_exe_tc_time[2] = time[2];
1481 housekeeping_packet.hk_lfr_last_exe_tc_time[3] = time[3];
1482 housekeeping_packet.hk_lfr_last_exe_tc_time[3] = time[3];
1482 housekeeping_packet.hk_lfr_last_exe_tc_time[4] = time[4];
1483 housekeeping_packet.hk_lfr_last_exe_tc_time[4] = time[4];
1483 housekeeping_packet.hk_lfr_last_exe_tc_time[5] = time[5];
1484 housekeeping_packet.hk_lfr_last_exe_tc_time[5] = time[5];
1484
1485
1485 val = housekeeping_packet.hk_lfr_exe_tc_cnt[0] * 256 + housekeeping_packet.hk_lfr_exe_tc_cnt[1];
1486 val = housekeeping_packet.hk_lfr_exe_tc_cnt[0] * 256 + housekeeping_packet.hk_lfr_exe_tc_cnt[1];
1486 val++;
1487 val++;
1487 housekeeping_packet.hk_lfr_exe_tc_cnt[0] = (unsigned char) (val >> 8);
1488 housekeeping_packet.hk_lfr_exe_tc_cnt[0] = (unsigned char) (val >> 8);
1488 housekeeping_packet.hk_lfr_exe_tc_cnt[1] = (unsigned char) (val);
1489 housekeeping_packet.hk_lfr_exe_tc_cnt[1] = (unsigned char) (val);
1489 }
1490 }
1490
1491
1491 void update_last_TC_rej(ccsdsTelecommandPacket_t *TC, unsigned char * time )
1492 void update_last_TC_rej(ccsdsTelecommandPacket_t *TC, unsigned char * time )
1492 {
1493 {
1493 /** This function is used to update the HK packets statistics after a TC rejection.
1494 /** This function is used to update the HK packets statistics after a TC rejection.
1494 *
1495 *
1495 * @param TC points to the TC being processed
1496 * @param TC points to the TC being processed
1496 * @param time is the time used to date the TC rejection
1497 * @param time is the time used to date the TC rejection
1497 *
1498 *
1498 */
1499 */
1499
1500
1500 unsigned int val;
1501 unsigned int val;
1501
1502
1502 housekeeping_packet.hk_lfr_last_rej_tc_id[0] = TC->packetID[0];
1503 housekeeping_packet.hk_lfr_last_rej_tc_id[0] = TC->packetID[0];
1503 housekeeping_packet.hk_lfr_last_rej_tc_id[1] = TC->packetID[1];
1504 housekeeping_packet.hk_lfr_last_rej_tc_id[1] = TC->packetID[1];
1504 housekeeping_packet.hk_lfr_last_rej_tc_type[0] = 0x00;
1505 housekeeping_packet.hk_lfr_last_rej_tc_type[0] = 0x00;
1505 housekeeping_packet.hk_lfr_last_rej_tc_type[1] = TC->serviceType;
1506 housekeeping_packet.hk_lfr_last_rej_tc_type[1] = TC->serviceType;
1506 housekeeping_packet.hk_lfr_last_rej_tc_subtype[0] = 0x00;
1507 housekeeping_packet.hk_lfr_last_rej_tc_subtype[0] = 0x00;
1507 housekeeping_packet.hk_lfr_last_rej_tc_subtype[1] = TC->serviceSubType;
1508 housekeeping_packet.hk_lfr_last_rej_tc_subtype[1] = TC->serviceSubType;
1508 housekeeping_packet.hk_lfr_last_rej_tc_time[0] = time[0];
1509 housekeeping_packet.hk_lfr_last_rej_tc_time[0] = time[0];
1509 housekeeping_packet.hk_lfr_last_rej_tc_time[1] = time[1];
1510 housekeeping_packet.hk_lfr_last_rej_tc_time[1] = time[1];
1510 housekeeping_packet.hk_lfr_last_rej_tc_time[2] = time[2];
1511 housekeeping_packet.hk_lfr_last_rej_tc_time[2] = time[2];
1511 housekeeping_packet.hk_lfr_last_rej_tc_time[3] = time[3];
1512 housekeeping_packet.hk_lfr_last_rej_tc_time[3] = time[3];
1512 housekeeping_packet.hk_lfr_last_rej_tc_time[4] = time[4];
1513 housekeeping_packet.hk_lfr_last_rej_tc_time[4] = time[4];
1513 housekeeping_packet.hk_lfr_last_rej_tc_time[5] = time[5];
1514 housekeeping_packet.hk_lfr_last_rej_tc_time[5] = time[5];
1514
1515
1515 val = housekeeping_packet.hk_lfr_rej_tc_cnt[0] * 256 + housekeeping_packet.hk_lfr_rej_tc_cnt[1];
1516 val = housekeeping_packet.hk_lfr_rej_tc_cnt[0] * 256 + housekeeping_packet.hk_lfr_rej_tc_cnt[1];
1516 val++;
1517 val++;
1517 housekeeping_packet.hk_lfr_rej_tc_cnt[0] = (unsigned char) (val >> 8);
1518 housekeeping_packet.hk_lfr_rej_tc_cnt[0] = (unsigned char) (val >> 8);
1518 housekeeping_packet.hk_lfr_rej_tc_cnt[1] = (unsigned char) (val);
1519 housekeeping_packet.hk_lfr_rej_tc_cnt[1] = (unsigned char) (val);
1519 }
1520 }
1520
1521
1521 void close_action(ccsdsTelecommandPacket_t *TC, int result, rtems_id queue_id )
1522 void close_action(ccsdsTelecommandPacket_t *TC, int result, rtems_id queue_id )
1522 {
1523 {
1523 /** This function is the last step of the TC execution workflow.
1524 /** This function is the last step of the TC execution workflow.
1524 *
1525 *
1525 * @param TC points to the TC being processed
1526 * @param TC points to the TC being processed
1526 * @param result is the result of the TC execution (LFR_SUCCESSFUL / LFR_DEFAULT)
1527 * @param result is the result of the TC execution (LFR_SUCCESSFUL / LFR_DEFAULT)
1527 * @param queue_id is the id of the RTEMS message queue used to send TM packets
1528 * @param queue_id is the id of the RTEMS message queue used to send TM packets
1528 * @param time is the time used to date the TC execution
1529 * @param time is the time used to date the TC execution
1529 *
1530 *
1530 */
1531 */
1531
1532
1532 unsigned char requestedMode;
1533 unsigned char requestedMode;
1533
1534
1534 if (result == LFR_SUCCESSFUL)
1535 if (result == LFR_SUCCESSFUL)
1535 {
1536 {
1536 if ( !( (TC->serviceType==TC_TYPE_TIME) & (TC->serviceSubType==TC_SUBTYPE_UPDT_TIME) )
1537 if ( !( (TC->serviceType==TC_TYPE_TIME) & (TC->serviceSubType==TC_SUBTYPE_UPDT_TIME) )
1537 &
1538 &
1538 !( (TC->serviceType==TC_TYPE_GEN) & (TC->serviceSubType==TC_SUBTYPE_UPDT_INFO))
1539 !( (TC->serviceType==TC_TYPE_GEN) & (TC->serviceSubType==TC_SUBTYPE_UPDT_INFO))
1539 )
1540 )
1540 {
1541 {
1541 send_tm_lfr_tc_exe_success( TC, queue_id );
1542 send_tm_lfr_tc_exe_success( TC, queue_id );
1542 }
1543 }
1543 if ( (TC->serviceType == TC_TYPE_GEN) & (TC->serviceSubType == TC_SUBTYPE_ENTER) )
1544 if ( (TC->serviceType == TC_TYPE_GEN) & (TC->serviceSubType == TC_SUBTYPE_ENTER) )
1544 {
1545 {
1545 //**********************************
1546 //**********************************
1546 // UPDATE THE LFRMODE LOCAL VARIABLE
1547 // UPDATE THE LFRMODE LOCAL VARIABLE
1547 requestedMode = TC->dataAndCRC[1];
1548 requestedMode = TC->dataAndCRC[1];
1548 housekeeping_packet.lfr_status_word[0] = (unsigned char) ((requestedMode << 4) + 0x0d);
1549 housekeeping_packet.lfr_status_word[0] = (unsigned char) ((requestedMode << 4) + 0x0d);
1549 updateLFRCurrentMode();
1550 updateLFRCurrentMode();
1550 }
1551 }
1551 }
1552 }
1552 else if (result == LFR_EXE_ERROR)
1553 else if (result == LFR_EXE_ERROR)
1553 {
1554 {
1554 send_tm_lfr_tc_exe_error( TC, queue_id );
1555 send_tm_lfr_tc_exe_error( TC, queue_id );
1555 }
1556 }
1556 }
1557 }
1557
1558
1558 //***************************
1559 //***************************
1559 // Interrupt Service Routines
1560 // Interrupt Service Routines
1560 rtems_isr commutation_isr1( rtems_vector_number vector )
1561 rtems_isr commutation_isr1( rtems_vector_number vector )
1561 {
1562 {
1562 if (rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_0 ) != RTEMS_SUCCESSFUL) {
1563 if (rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_0 ) != RTEMS_SUCCESSFUL) {
1563 PRINTF("In commutation_isr1 *** Error sending event to DUMB\n")
1564 PRINTF("In commutation_isr1 *** Error sending event to DUMB\n")
1564 }
1565 }
1565 }
1566 }
1566
1567
1567 rtems_isr commutation_isr2( rtems_vector_number vector )
1568 rtems_isr commutation_isr2( rtems_vector_number vector )
1568 {
1569 {
1569 if (rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_0 ) != RTEMS_SUCCESSFUL) {
1570 if (rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_0 ) != RTEMS_SUCCESSFUL) {
1570 PRINTF("In commutation_isr2 *** Error sending event to DUMB\n")
1571 PRINTF("In commutation_isr2 *** Error sending event to DUMB\n")
1571 }
1572 }
1572 }
1573 }
1573
1574
1574 //****************
1575 //****************
1575 // OTHER FUNCTIONS
1576 // OTHER FUNCTIONS
1576 void updateLFRCurrentMode()
1577 void updateLFRCurrentMode()
1577 {
1578 {
1578 /** This function updates the value of the global variable lfrCurrentMode.
1579 /** This function updates the value of the global variable lfrCurrentMode.
1579 *
1580 *
1580 * lfrCurrentMode is a parameter used by several functions to know in which mode LFR is running.
1581 * lfrCurrentMode is a parameter used by several functions to know in which mode LFR is running.
1581 *
1582 *
1582 */
1583 */
1583 // update the local value of lfrCurrentMode with the value contained in the housekeeping_packet structure
1584 // update the local value of lfrCurrentMode with the value contained in the housekeeping_packet structure
1584 lfrCurrentMode = (housekeeping_packet.lfr_status_word[0] & 0xf0) >> 4;
1585 lfrCurrentMode = (housekeeping_packet.lfr_status_word[0] & 0xf0) >> 4;
1585 }
1586 }
1586
1587
1587 void set_lfr_soft_reset( unsigned char value )
1588 void set_lfr_soft_reset( unsigned char value )
1588 {
1589 {
1589 if (value == 1)
1590 if (value == 1)
1590 {
1591 {
1591 time_management_regs->ctrl = time_management_regs->ctrl | 0x00000004; // [0100]
1592 time_management_regs->ctrl = time_management_regs->ctrl | 0x00000004; // [0100]
1592 }
1593 }
1593 else
1594 else
1594 {
1595 {
1595 time_management_regs->ctrl = time_management_regs->ctrl & 0xfffffffb; // [1011]
1596 time_management_regs->ctrl = time_management_regs->ctrl & 0xfffffffb; // [1011]
1596 }
1597 }
1597 }
1598 }
1598
1599
1599 void reset_lfr( void )
1600 void reset_lfr( void )
1600 {
1601 {
1601 set_lfr_soft_reset( 1 );
1602 set_lfr_soft_reset( 1 );
1602
1603
1603 set_lfr_soft_reset( 0 );
1604 set_lfr_soft_reset( 0 );
1604
1605
1605 set_hk_lfr_sc_potential_flag( true );
1606 set_hk_lfr_sc_potential_flag( true );
1606 }
1607 }
@@ -1,1196 +1,1214
1 /** Functions and tasks related to waveform packet generation.
1 /** Functions and tasks related to waveform packet generation.
2 *
2 *
3 * @file
3 * @file
4 * @author P. LEROY
4 * @author P. LEROY
5 *
5 *
6 * A group of functions to handle waveforms, in snapshot or continuous format.\n
6 * A group of functions to handle waveforms, in snapshot or continuous format.\n
7 *
7 *
8 */
8 */
9
9
10 #include "wf_handler.h"
10 #include "wf_handler.h"
11
11
12 //***************
12 //***************
13 // waveform rings
13 // waveform rings
14 // F0
14 // F0
15 ring_node waveform_ring_f0[NB_RING_NODES_F0];
15 ring_node waveform_ring_f0[NB_RING_NODES_F0];
16 ring_node *current_ring_node_f0;
16 ring_node *current_ring_node_f0;
17 ring_node *ring_node_to_send_swf_f0;
17 ring_node *ring_node_to_send_swf_f0;
18 // F1
18 // F1
19 ring_node waveform_ring_f1[NB_RING_NODES_F1];
19 ring_node waveform_ring_f1[NB_RING_NODES_F1];
20 ring_node *current_ring_node_f1;
20 ring_node *current_ring_node_f1;
21 ring_node *ring_node_to_send_swf_f1;
21 ring_node *ring_node_to_send_swf_f1;
22 ring_node *ring_node_to_send_cwf_f1;
22 ring_node *ring_node_to_send_cwf_f1;
23 // F2
23 // F2
24 ring_node waveform_ring_f2[NB_RING_NODES_F2];
24 ring_node waveform_ring_f2[NB_RING_NODES_F2];
25 ring_node *current_ring_node_f2;
25 ring_node *current_ring_node_f2;
26 ring_node *ring_node_to_send_swf_f2;
26 ring_node *ring_node_to_send_swf_f2;
27 ring_node *ring_node_to_send_cwf_f2;
27 ring_node *ring_node_to_send_cwf_f2;
28 // F3
28 // F3
29 ring_node waveform_ring_f3[NB_RING_NODES_F3];
29 ring_node waveform_ring_f3[NB_RING_NODES_F3];
30 ring_node *current_ring_node_f3;
30 ring_node *current_ring_node_f3;
31 ring_node *ring_node_to_send_cwf_f3;
31 ring_node *ring_node_to_send_cwf_f3;
32 char wf_cont_f3_light[ (NB_SAMPLES_PER_SNAPSHOT) * NB_BYTES_CWF3_LIGHT_BLK ];
32 char wf_cont_f3_light[ (NB_SAMPLES_PER_SNAPSHOT) * NB_BYTES_CWF3_LIGHT_BLK ];
33
33
34 bool extractSWF1 = false;
34 bool extractSWF1 = false;
35 bool extractSWF2 = false;
35 bool extractSWF2 = false;
36 bool swf0_ready_flag_f1 = false;
36 bool swf0_ready_flag_f1 = false;
37 bool swf0_ready_flag_f2 = false;
37 bool swf0_ready_flag_f2 = false;
38 bool swf1_ready = false;
38 bool swf1_ready = false;
39 bool swf2_ready = false;
39 bool swf2_ready = false;
40
40
41 int swf1_extracted[ (NB_SAMPLES_PER_SNAPSHOT * NB_WORDS_SWF_BLK) ];
41 int swf1_extracted[ (NB_SAMPLES_PER_SNAPSHOT * NB_WORDS_SWF_BLK) ];
42 int swf2_extracted[ (NB_SAMPLES_PER_SNAPSHOT * NB_WORDS_SWF_BLK) ];
42 int swf2_extracted[ (NB_SAMPLES_PER_SNAPSHOT * NB_WORDS_SWF_BLK) ];
43 ring_node ring_node_swf1_extracted;
43 ring_node ring_node_swf1_extracted;
44 ring_node ring_node_swf2_extracted;
44 ring_node ring_node_swf2_extracted;
45
45
46 //*********************
46 //*********************
47 // Interrupt SubRoutine
47 // Interrupt SubRoutine
48
48
49 ring_node * getRingNodeToSendCWF( unsigned char frequencyChannel)
49 ring_node * getRingNodeToSendCWF( unsigned char frequencyChannel)
50 {
50 {
51 ring_node *node;
51 ring_node *node;
52
52
53 node = NULL;
53 node = NULL;
54 switch ( frequencyChannel ) {
54 switch ( frequencyChannel ) {
55 case 1:
55 case 1:
56 node = ring_node_to_send_cwf_f1;
56 node = ring_node_to_send_cwf_f1;
57 break;
57 break;
58 case 2:
58 case 2:
59 node = ring_node_to_send_cwf_f2;
59 node = ring_node_to_send_cwf_f2;
60 break;
60 break;
61 case 3:
61 case 3:
62 node = ring_node_to_send_cwf_f3;
62 node = ring_node_to_send_cwf_f3;
63 break;
63 break;
64 default:
64 default:
65 break;
65 break;
66 }
66 }
67
67
68 return node;
68 return node;
69 }
69 }
70
70
71 ring_node * getRingNodeToSendSWF( unsigned char frequencyChannel)
71 ring_node * getRingNodeToSendSWF( unsigned char frequencyChannel)
72 {
72 {
73 ring_node *node;
73 ring_node *node;
74
74
75 node = NULL;
75 node = NULL;
76 switch ( frequencyChannel ) {
76 switch ( frequencyChannel ) {
77 case 0:
77 case 0:
78 node = ring_node_to_send_swf_f0;
78 node = ring_node_to_send_swf_f0;
79 break;
79 break;
80 case 1:
80 case 1:
81 node = ring_node_to_send_swf_f1;
81 node = ring_node_to_send_swf_f1;
82 break;
82 break;
83 case 2:
83 case 2:
84 node = ring_node_to_send_swf_f2;
84 node = ring_node_to_send_swf_f2;
85 break;
85 break;
86 default:
86 default:
87 break;
87 break;
88 }
88 }
89
89
90 return node;
90 return node;
91 }
91 }
92
92
93 void reset_extractSWF( void )
93 void reset_extractSWF( void )
94 {
94 {
95 extractSWF1 = false;
95 extractSWF1 = false;
96 extractSWF2 = false;
96 extractSWF2 = false;
97 swf0_ready_flag_f1 = false;
97 swf0_ready_flag_f1 = false;
98 swf0_ready_flag_f2 = false;
98 swf0_ready_flag_f2 = false;
99 swf1_ready = false;
99 swf1_ready = false;
100 swf2_ready = false;
100 swf2_ready = false;
101 }
101 }
102
102
103 inline void waveforms_isr_f3( void )
103 inline void waveforms_isr_f3( void )
104 {
104 {
105 rtems_status_code spare_status;
105 rtems_status_code spare_status;
106
106
107 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
107 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
108 || (lfrCurrentMode == LFR_MODE_SBM1) || (lfrCurrentMode == LFR_MODE_SBM2) )
108 || (lfrCurrentMode == LFR_MODE_SBM1) || (lfrCurrentMode == LFR_MODE_SBM2) )
109 { // in modes other than STANDBY and BURST, send the CWF_F3 data
109 { // in modes other than STANDBY and BURST, send the CWF_F3 data
110 //***
110 //***
111 // F3
111 // F3
112 if ( (waveform_picker_regs->status & 0xc0) != 0x00 ) { // [1100 0000] check the f3 full bits
112 if ( (waveform_picker_regs->status & 0xc0) != 0x00 ) { // [1100 0000] check the f3 full bits
113 ring_node_to_send_cwf_f3 = current_ring_node_f3->previous;
113 ring_node_to_send_cwf_f3 = current_ring_node_f3->previous;
114 current_ring_node_f3 = current_ring_node_f3->next;
114 current_ring_node_f3 = current_ring_node_f3->next;
115 if ((waveform_picker_regs->status & 0x40) == 0x40){ // [0100 0000] f3 buffer 0 is full
115 if ((waveform_picker_regs->status & 0x40) == 0x40){ // [0100 0000] f3 buffer 0 is full
116 ring_node_to_send_cwf_f3->coarseTime = waveform_picker_regs->f3_0_coarse_time;
116 ring_node_to_send_cwf_f3->coarseTime = waveform_picker_regs->f3_0_coarse_time;
117 ring_node_to_send_cwf_f3->fineTime = waveform_picker_regs->f3_0_fine_time;
117 ring_node_to_send_cwf_f3->fineTime = waveform_picker_regs->f3_0_fine_time;
118 waveform_picker_regs->addr_data_f3_0 = current_ring_node_f3->buffer_address;
118 waveform_picker_regs->addr_data_f3_0 = current_ring_node_f3->buffer_address;
119 waveform_picker_regs->status = waveform_picker_regs->status & 0x00008840; // [1000 1000 0100 0000]
119 waveform_picker_regs->status = waveform_picker_regs->status & 0x00008840; // [1000 1000 0100 0000]
120 }
120 }
121 else if ((waveform_picker_regs->status & 0x80) == 0x80){ // [1000 0000] f3 buffer 1 is full
121 else if ((waveform_picker_regs->status & 0x80) == 0x80){ // [1000 0000] f3 buffer 1 is full
122 ring_node_to_send_cwf_f3->coarseTime = waveform_picker_regs->f3_1_coarse_time;
122 ring_node_to_send_cwf_f3->coarseTime = waveform_picker_regs->f3_1_coarse_time;
123 ring_node_to_send_cwf_f3->fineTime = waveform_picker_regs->f3_1_fine_time;
123 ring_node_to_send_cwf_f3->fineTime = waveform_picker_regs->f3_1_fine_time;
124 waveform_picker_regs->addr_data_f3_1 = current_ring_node_f3->buffer_address;
124 waveform_picker_regs->addr_data_f3_1 = current_ring_node_f3->buffer_address;
125 waveform_picker_regs->status = waveform_picker_regs->status & 0x00008880; // [1000 1000 1000 0000]
125 waveform_picker_regs->status = waveform_picker_regs->status & 0x00008880; // [1000 1000 1000 0000]
126 }
126 }
127 if (rtems_event_send( Task_id[TASKID_CWF3], RTEMS_EVENT_0 ) != RTEMS_SUCCESSFUL) {
127 if (rtems_event_send( Task_id[TASKID_CWF3], RTEMS_EVENT_0 ) != RTEMS_SUCCESSFUL) {
128 spare_status = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_0 );
128 spare_status = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_0 );
129 }
129 }
130 }
130 }
131 }
131 }
132 }
132 }
133
133
134 inline void waveforms_isr_burst( void )
134 inline void waveforms_isr_burst( void )
135 {
135 {
136 unsigned char status;
136 unsigned char status;
137 rtems_status_code spare_status;
137 rtems_status_code spare_status;
138
138
139 status = (waveform_picker_regs->status & 0x30) >> 4; // [0011 0000] get the status bits for f2
139 status = (waveform_picker_regs->status & 0x30) >> 4; // [0011 0000] get the status bits for f2
140
140
141
141
142 switch(status)
142 switch(status)
143 {
143 {
144 case 1:
144 case 1:
145 ring_node_to_send_cwf_f2 = current_ring_node_f2->previous;
145 ring_node_to_send_cwf_f2 = current_ring_node_f2->previous;
146 ring_node_to_send_cwf_f2->sid = SID_BURST_CWF_F2;
146 ring_node_to_send_cwf_f2->sid = SID_BURST_CWF_F2;
147 ring_node_to_send_cwf_f2->coarseTime = waveform_picker_regs->f2_0_coarse_time;
147 ring_node_to_send_cwf_f2->coarseTime = waveform_picker_regs->f2_0_coarse_time;
148 ring_node_to_send_cwf_f2->fineTime = waveform_picker_regs->f2_0_fine_time;
148 ring_node_to_send_cwf_f2->fineTime = waveform_picker_regs->f2_0_fine_time;
149 current_ring_node_f2 = current_ring_node_f2->next;
149 current_ring_node_f2 = current_ring_node_f2->next;
150 waveform_picker_regs->addr_data_f2_0 = current_ring_node_f2->buffer_address;
150 waveform_picker_regs->addr_data_f2_0 = current_ring_node_f2->buffer_address;
151 if (rtems_event_send( Task_id[TASKID_CWF2], RTEMS_EVENT_MODE_BURST ) != RTEMS_SUCCESSFUL) {
151 if (rtems_event_send( Task_id[TASKID_CWF2], RTEMS_EVENT_MODE_BURST ) != RTEMS_SUCCESSFUL) {
152 spare_status = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_0 );
152 spare_status = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_0 );
153 }
153 }
154 waveform_picker_regs->status = waveform_picker_regs->status & 0x00004410; // [0100 0100 0001 0000]
154 waveform_picker_regs->status = waveform_picker_regs->status & 0x00004410; // [0100 0100 0001 0000]
155 break;
155 break;
156 case 2:
156 case 2:
157 ring_node_to_send_cwf_f2 = current_ring_node_f2->previous;
157 ring_node_to_send_cwf_f2 = current_ring_node_f2->previous;
158 ring_node_to_send_cwf_f2->sid = SID_BURST_CWF_F2;
158 ring_node_to_send_cwf_f2->sid = SID_BURST_CWF_F2;
159 ring_node_to_send_cwf_f2->coarseTime = waveform_picker_regs->f2_1_coarse_time;
159 ring_node_to_send_cwf_f2->coarseTime = waveform_picker_regs->f2_1_coarse_time;
160 ring_node_to_send_cwf_f2->fineTime = waveform_picker_regs->f2_1_fine_time;
160 ring_node_to_send_cwf_f2->fineTime = waveform_picker_regs->f2_1_fine_time;
161 current_ring_node_f2 = current_ring_node_f2->next;
161 current_ring_node_f2 = current_ring_node_f2->next;
162 waveform_picker_regs->addr_data_f2_1 = current_ring_node_f2->buffer_address;
162 waveform_picker_regs->addr_data_f2_1 = current_ring_node_f2->buffer_address;
163 if (rtems_event_send( Task_id[TASKID_CWF2], RTEMS_EVENT_MODE_BURST ) != RTEMS_SUCCESSFUL) {
163 if (rtems_event_send( Task_id[TASKID_CWF2], RTEMS_EVENT_MODE_BURST ) != RTEMS_SUCCESSFUL) {
164 spare_status = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_0 );
164 spare_status = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_0 );
165 }
165 }
166 waveform_picker_regs->status = waveform_picker_regs->status & 0x00004420; // [0100 0100 0010 0000]
166 waveform_picker_regs->status = waveform_picker_regs->status & 0x00004420; // [0100 0100 0010 0000]
167 break;
167 break;
168 default:
168 default:
169 break;
169 break;
170 }
170 }
171 }
171 }
172
172
173 inline void waveform_isr_normal_sbm1_sbm2( void )
173 inline void waveform_isr_normal_sbm1_sbm2( void )
174 {
174 {
175 rtems_status_code status;
175 rtems_status_code status;
176
176
177 //***
177 //***
178 // F0
178 // F0
179 if ( (waveform_picker_regs->status & 0x03) != 0x00 ) // [0000 0011] check the f0 full bits
179 if ( (waveform_picker_regs->status & 0x03) != 0x00 ) // [0000 0011] check the f0 full bits
180 {
180 {
181 swf0_ready_flag_f1 = true;
181 swf0_ready_flag_f1 = true;
182 swf0_ready_flag_f2 = true;
182 swf0_ready_flag_f2 = true;
183 ring_node_to_send_swf_f0 = current_ring_node_f0->previous;
183 ring_node_to_send_swf_f0 = current_ring_node_f0->previous;
184 current_ring_node_f0 = current_ring_node_f0->next;
184 current_ring_node_f0 = current_ring_node_f0->next;
185 if ( (waveform_picker_regs->status & 0x01) == 0x01)
185 if ( (waveform_picker_regs->status & 0x01) == 0x01)
186 {
186 {
187
187
188 ring_node_to_send_swf_f0->coarseTime = waveform_picker_regs->f0_0_coarse_time;
188 ring_node_to_send_swf_f0->coarseTime = waveform_picker_regs->f0_0_coarse_time;
189 ring_node_to_send_swf_f0->fineTime = waveform_picker_regs->f0_0_fine_time;
189 ring_node_to_send_swf_f0->fineTime = waveform_picker_regs->f0_0_fine_time;
190 waveform_picker_regs->addr_data_f0_0 = current_ring_node_f0->buffer_address;
190 waveform_picker_regs->addr_data_f0_0 = current_ring_node_f0->buffer_address;
191 waveform_picker_regs->status = waveform_picker_regs->status & 0x00001101; // [0001 0001 0000 0001]
191 waveform_picker_regs->status = waveform_picker_regs->status & 0x00001101; // [0001 0001 0000 0001]
192 }
192 }
193 else if ( (waveform_picker_regs->status & 0x02) == 0x02)
193 else if ( (waveform_picker_regs->status & 0x02) == 0x02)
194 {
194 {
195 ring_node_to_send_swf_f0->coarseTime = waveform_picker_regs->f0_1_coarse_time;
195 ring_node_to_send_swf_f0->coarseTime = waveform_picker_regs->f0_1_coarse_time;
196 ring_node_to_send_swf_f0->fineTime = waveform_picker_regs->f0_1_fine_time;
196 ring_node_to_send_swf_f0->fineTime = waveform_picker_regs->f0_1_fine_time;
197 waveform_picker_regs->addr_data_f0_1 = current_ring_node_f0->buffer_address;
197 waveform_picker_regs->addr_data_f0_1 = current_ring_node_f0->buffer_address;
198 waveform_picker_regs->status = waveform_picker_regs->status & 0x00001102; // [0001 0001 0000 0010]
198 waveform_picker_regs->status = waveform_picker_regs->status & 0x00001102; // [0001 0001 0000 0010]
199 }
199 }
200 }
200 }
201
201
202 //***
202 //***
203 // F1
203 // F1
204 if ( (waveform_picker_regs->status & 0x0c) != 0x00 ) { // [0000 1100] check the f1 full bits
204 if ( (waveform_picker_regs->status & 0x0c) != 0x00 ) { // [0000 1100] check the f1 full bits
205 // (1) change the receiving buffer for the waveform picker
205 // (1) change the receiving buffer for the waveform picker
206 ring_node_to_send_cwf_f1 = current_ring_node_f1->previous;
206 ring_node_to_send_cwf_f1 = current_ring_node_f1->previous;
207 current_ring_node_f1 = current_ring_node_f1->next;
207 current_ring_node_f1 = current_ring_node_f1->next;
208 if ( (waveform_picker_regs->status & 0x04) == 0x04)
208 if ( (waveform_picker_regs->status & 0x04) == 0x04)
209 {
209 {
210 ring_node_to_send_cwf_f1->coarseTime = waveform_picker_regs->f1_0_coarse_time;
210 ring_node_to_send_cwf_f1->coarseTime = waveform_picker_regs->f1_0_coarse_time;
211 ring_node_to_send_cwf_f1->fineTime = waveform_picker_regs->f1_0_fine_time;
211 ring_node_to_send_cwf_f1->fineTime = waveform_picker_regs->f1_0_fine_time;
212 waveform_picker_regs->addr_data_f1_0 = current_ring_node_f1->buffer_address;
212 waveform_picker_regs->addr_data_f1_0 = current_ring_node_f1->buffer_address;
213 waveform_picker_regs->status = waveform_picker_regs->status & 0x00002204; // [0010 0010 0000 0100] f1 bits = 0
213 waveform_picker_regs->status = waveform_picker_regs->status & 0x00002204; // [0010 0010 0000 0100] f1 bits = 0
214 }
214 }
215 else if ( (waveform_picker_regs->status & 0x08) == 0x08)
215 else if ( (waveform_picker_regs->status & 0x08) == 0x08)
216 {
216 {
217 ring_node_to_send_cwf_f1->coarseTime = waveform_picker_regs->f1_1_coarse_time;
217 ring_node_to_send_cwf_f1->coarseTime = waveform_picker_regs->f1_1_coarse_time;
218 ring_node_to_send_cwf_f1->fineTime = waveform_picker_regs->f1_1_fine_time;
218 ring_node_to_send_cwf_f1->fineTime = waveform_picker_regs->f1_1_fine_time;
219 waveform_picker_regs->addr_data_f1_1 = current_ring_node_f1->buffer_address;
219 waveform_picker_regs->addr_data_f1_1 = current_ring_node_f1->buffer_address;
220 waveform_picker_regs->status = waveform_picker_regs->status & 0x00002208; // [0010 0010 0000 1000] f1 bits = 0
220 waveform_picker_regs->status = waveform_picker_regs->status & 0x00002208; // [0010 0010 0000 1000] f1 bits = 0
221 }
221 }
222 // (2) send an event for the the CWF1 task for transmission (and snapshot extraction if needed)
222 // (2) send an event for the the CWF1 task for transmission (and snapshot extraction if needed)
223 status = rtems_event_send( Task_id[TASKID_CWF1], RTEMS_EVENT_MODE_NORM_S1_S2 );
223 status = rtems_event_send( Task_id[TASKID_CWF1], RTEMS_EVENT_MODE_NORM_S1_S2 );
224 }
224 }
225
225
226 //***
226 //***
227 // F2
227 // F2
228 if ( (waveform_picker_regs->status & 0x30) != 0x00 ) { // [0011 0000] check the f2 full bit
228 if ( (waveform_picker_regs->status & 0x30) != 0x00 ) { // [0011 0000] check the f2 full bit
229 // (1) change the receiving buffer for the waveform picker
229 // (1) change the receiving buffer for the waveform picker
230 ring_node_to_send_cwf_f2 = current_ring_node_f2->previous;
230 ring_node_to_send_cwf_f2 = current_ring_node_f2->previous;
231 ring_node_to_send_cwf_f2->sid = SID_SBM2_CWF_F2;
231 ring_node_to_send_cwf_f2->sid = SID_SBM2_CWF_F2;
232 current_ring_node_f2 = current_ring_node_f2->next;
232 current_ring_node_f2 = current_ring_node_f2->next;
233 if ( (waveform_picker_regs->status & 0x10) == 0x10)
233 if ( (waveform_picker_regs->status & 0x10) == 0x10)
234 {
234 {
235 ring_node_to_send_cwf_f2->coarseTime = waveform_picker_regs->f2_0_coarse_time;
235 ring_node_to_send_cwf_f2->coarseTime = waveform_picker_regs->f2_0_coarse_time;
236 ring_node_to_send_cwf_f2->fineTime = waveform_picker_regs->f2_0_fine_time;
236 ring_node_to_send_cwf_f2->fineTime = waveform_picker_regs->f2_0_fine_time;
237 waveform_picker_regs->addr_data_f2_0 = current_ring_node_f2->buffer_address;
237 waveform_picker_regs->addr_data_f2_0 = current_ring_node_f2->buffer_address;
238 waveform_picker_regs->status = waveform_picker_regs->status & 0x00004410; // [0100 0100 0001 0000]
238 waveform_picker_regs->status = waveform_picker_regs->status & 0x00004410; // [0100 0100 0001 0000]
239 }
239 }
240 else if ( (waveform_picker_regs->status & 0x20) == 0x20)
240 else if ( (waveform_picker_regs->status & 0x20) == 0x20)
241 {
241 {
242 ring_node_to_send_cwf_f2->coarseTime = waveform_picker_regs->f2_1_coarse_time;
242 ring_node_to_send_cwf_f2->coarseTime = waveform_picker_regs->f2_1_coarse_time;
243 ring_node_to_send_cwf_f2->fineTime = waveform_picker_regs->f2_1_fine_time;
243 ring_node_to_send_cwf_f2->fineTime = waveform_picker_regs->f2_1_fine_time;
244 waveform_picker_regs->addr_data_f2_1 = current_ring_node_f2->buffer_address;
244 waveform_picker_regs->addr_data_f2_1 = current_ring_node_f2->buffer_address;
245 waveform_picker_regs->status = waveform_picker_regs->status & 0x00004420; // [0100 0100 0010 0000]
245 waveform_picker_regs->status = waveform_picker_regs->status & 0x00004420; // [0100 0100 0010 0000]
246 }
246 }
247 // (2) send an event for the waveforms transmission
247 // (2) send an event for the waveforms transmission
248 status = rtems_event_send( Task_id[TASKID_CWF2], RTEMS_EVENT_MODE_NORM_S1_S2 );
248 status = rtems_event_send( Task_id[TASKID_CWF2], RTEMS_EVENT_MODE_NORM_S1_S2 );
249 }
249 }
250 }
250 }
251
251
252 rtems_isr waveforms_isr( rtems_vector_number vector )
252 rtems_isr waveforms_isr( rtems_vector_number vector )
253 {
253 {
254 /** This is the interrupt sub routine called by the waveform picker core.
254 /** This is the interrupt sub routine called by the waveform picker core.
255 *
255 *
256 * This ISR launch different actions depending mainly on two pieces of information:
256 * This ISR launch different actions depending mainly on two pieces of information:
257 * 1. the values read in the registers of the waveform picker.
257 * 1. the values read in the registers of the waveform picker.
258 * 2. the current LFR mode.
258 * 2. the current LFR mode.
259 *
259 *
260 */
260 */
261
261
262 // STATUS
262 // STATUS
263 // new error error buffer full
263 // new error error buffer full
264 // 15 14 13 12 11 10 9 8
264 // 15 14 13 12 11 10 9 8
265 // f3 f2 f1 f0 f3 f2 f1 f0
265 // f3 f2 f1 f0 f3 f2 f1 f0
266 //
266 //
267 // ready buffer
267 // ready buffer
268 // 7 6 5 4 3 2 1 0
268 // 7 6 5 4 3 2 1 0
269 // f3_1 f3_0 f2_1 f2_0 f1_1 f1_0 f0_1 f0_0
269 // f3_1 f3_0 f2_1 f2_0 f1_1 f1_0 f0_1 f0_0
270
270
271 rtems_status_code spare_status;
271 rtems_status_code spare_status;
272
272
273 waveforms_isr_f3();
273 waveforms_isr_f3();
274
274
275 if ( (waveform_picker_regs->status & 0xff00) != 0x00) // [1111 1111 0000 0000] check the error bits
275 if ( (waveform_picker_regs->status & 0xff00) != 0x00) // [1111 1111 0000 0000] check the error bits
276 {
276 {
277 spare_status = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_10 );
277 spare_status = rtems_event_send( Task_id[TASKID_DUMB], RTEMS_EVENT_10 );
278 }
278 }
279
279
280 switch(lfrCurrentMode)
280 switch(lfrCurrentMode)
281 {
281 {
282 //********
282 //********
283 // STANDBY
283 // STANDBY
284 case LFR_MODE_STANDBY:
284 case LFR_MODE_STANDBY:
285 break;
285 break;
286 //**************************
286 //**************************
287 // LFR NORMAL, SBM1 and SBM2
287 // LFR NORMAL, SBM1 and SBM2
288 case LFR_MODE_NORMAL:
288 case LFR_MODE_NORMAL:
289 case LFR_MODE_SBM1:
289 case LFR_MODE_SBM1:
290 case LFR_MODE_SBM2:
290 case LFR_MODE_SBM2:
291 waveform_isr_normal_sbm1_sbm2();
291 waveform_isr_normal_sbm1_sbm2();
292 break;
292 break;
293 //******
293 //******
294 // BURST
294 // BURST
295 case LFR_MODE_BURST:
295 case LFR_MODE_BURST:
296 waveforms_isr_burst();
296 waveforms_isr_burst();
297 break;
297 break;
298 //********
298 //********
299 // DEFAULT
299 // DEFAULT
300 default:
300 default:
301 break;
301 break;
302 }
302 }
303 }
303 }
304
304
305 //************
305 //************
306 // RTEMS TASKS
306 // RTEMS TASKS
307
307
308 rtems_task wfrm_task(rtems_task_argument argument) //used with the waveform picker VHDL IP
308 rtems_task wfrm_task(rtems_task_argument argument) //used with the waveform picker VHDL IP
309 {
309 {
310 /** This RTEMS task is dedicated to the transmission of snapshots of the NORMAL mode.
310 /** This RTEMS task is dedicated to the transmission of snapshots of the NORMAL mode.
311 *
311 *
312 * @param unused is the starting argument of the RTEMS task
312 * @param unused is the starting argument of the RTEMS task
313 *
313 *
314 * The following data packets are sent by this task:
314 * The following data packets are sent by this task:
315 * - TM_LFR_SCIENCE_NORMAL_SWF_F0
315 * - TM_LFR_SCIENCE_NORMAL_SWF_F0
316 * - TM_LFR_SCIENCE_NORMAL_SWF_F1
316 * - TM_LFR_SCIENCE_NORMAL_SWF_F1
317 * - TM_LFR_SCIENCE_NORMAL_SWF_F2
317 * - TM_LFR_SCIENCE_NORMAL_SWF_F2
318 *
318 *
319 */
319 */
320
320
321 rtems_event_set event_out;
321 rtems_event_set event_out;
322 rtems_id queue_id;
322 rtems_id queue_id;
323 rtems_status_code status;
323 rtems_status_code status;
324 ring_node *ring_node_swf1_extracted_ptr;
324 ring_node *ring_node_swf1_extracted_ptr;
325 ring_node *ring_node_swf2_extracted_ptr;
325 ring_node *ring_node_swf2_extracted_ptr;
326
326
327 ring_node_swf1_extracted_ptr = (ring_node *) &ring_node_swf1_extracted;
327 ring_node_swf1_extracted_ptr = (ring_node *) &ring_node_swf1_extracted;
328 ring_node_swf2_extracted_ptr = (ring_node *) &ring_node_swf2_extracted;
328 ring_node_swf2_extracted_ptr = (ring_node *) &ring_node_swf2_extracted;
329
329
330 status = get_message_queue_id_send( &queue_id );
330 status = get_message_queue_id_send( &queue_id );
331 if (status != RTEMS_SUCCESSFUL)
331 if (status != RTEMS_SUCCESSFUL)
332 {
332 {
333 PRINTF1("in WFRM *** ERR get_message_queue_id_send %d\n", status);
333 PRINTF1("in WFRM *** ERR get_message_queue_id_send %d\n", status);
334 }
334 }
335
335
336 BOOT_PRINTF("in WFRM ***\n");
336 BOOT_PRINTF("in WFRM ***\n");
337
337
338 while(1){
338 while(1){
339 // wait for an RTEMS_EVENT
339 // wait for an RTEMS_EVENT
340 rtems_event_receive(RTEMS_EVENT_MODE_NORMAL,
340 rtems_event_receive(RTEMS_EVENT_MODE_NORMAL,
341 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
341 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
342
342
343 snapshot_resynchronization( (unsigned char *) &ring_node_to_send_swf_f0->coarseTime );
343 snapshot_resynchronization( (unsigned char *) &ring_node_to_send_swf_f0->coarseTime );
344
344
345 if (event_out == RTEMS_EVENT_MODE_NORMAL)
345 if (event_out == RTEMS_EVENT_MODE_NORMAL)
346 {
346 {
347 DEBUG_PRINTF("WFRM received RTEMS_EVENT_MODE_SBM2\n");
347 DEBUG_PRINTF("WFRM received RTEMS_EVENT_MODE_SBM2\n");
348 ring_node_to_send_swf_f0->sid = SID_NORM_SWF_F0;
348 ring_node_to_send_swf_f0->sid = SID_NORM_SWF_F0;
349 ring_node_swf1_extracted_ptr->sid = SID_NORM_SWF_F1;
349 ring_node_swf1_extracted_ptr->sid = SID_NORM_SWF_F1;
350 ring_node_swf2_extracted_ptr->sid = SID_NORM_SWF_F2;
350 ring_node_swf2_extracted_ptr->sid = SID_NORM_SWF_F2;
351 status = rtems_message_queue_send( queue_id, &ring_node_to_send_swf_f0, sizeof( ring_node* ) );
351 status = rtems_message_queue_send( queue_id, &ring_node_to_send_swf_f0, sizeof( ring_node* ) );
352 status = rtems_message_queue_send( queue_id, &ring_node_swf1_extracted_ptr, sizeof( ring_node* ) );
352 status = rtems_message_queue_send( queue_id, &ring_node_swf1_extracted_ptr, sizeof( ring_node* ) );
353 status = rtems_message_queue_send( queue_id, &ring_node_swf2_extracted_ptr, sizeof( ring_node* ) );
353 status = rtems_message_queue_send( queue_id, &ring_node_swf2_extracted_ptr, sizeof( ring_node* ) );
354 }
354 }
355 }
355 }
356 }
356 }
357
357
358 rtems_task cwf3_task(rtems_task_argument argument) //used with the waveform picker VHDL IP
358 rtems_task cwf3_task(rtems_task_argument argument) //used with the waveform picker VHDL IP
359 {
359 {
360 /** This RTEMS task is dedicated to the transmission of continuous waveforms at f3.
360 /** This RTEMS task is dedicated to the transmission of continuous waveforms at f3.
361 *
361 *
362 * @param unused is the starting argument of the RTEMS task
362 * @param unused is the starting argument of the RTEMS task
363 *
363 *
364 * The following data packet is sent by this task:
364 * The following data packet is sent by this task:
365 * - TM_LFR_SCIENCE_NORMAL_CWF_F3
365 * - TM_LFR_SCIENCE_NORMAL_CWF_F3
366 *
366 *
367 */
367 */
368
368
369 rtems_event_set event_out;
369 rtems_event_set event_out;
370 rtems_id queue_id;
370 rtems_id queue_id;
371 rtems_status_code status;
371 rtems_status_code status;
372 ring_node ring_node_cwf3_light;
372 ring_node ring_node_cwf3_light;
373 ring_node *ring_node_to_send_cwf;
373 ring_node *ring_node_to_send_cwf;
374
374
375 status = get_message_queue_id_send( &queue_id );
375 status = get_message_queue_id_send( &queue_id );
376 if (status != RTEMS_SUCCESSFUL)
376 if (status != RTEMS_SUCCESSFUL)
377 {
377 {
378 PRINTF1("in CWF3 *** ERR get_message_queue_id_send %d\n", status)
378 PRINTF1("in CWF3 *** ERR get_message_queue_id_send %d\n", status)
379 }
379 }
380
380
381 ring_node_to_send_cwf_f3->sid = SID_NORM_CWF_LONG_F3;
381 ring_node_to_send_cwf_f3->sid = SID_NORM_CWF_LONG_F3;
382
382
383 // init the ring_node_cwf3_light structure
383 // init the ring_node_cwf3_light structure
384 ring_node_cwf3_light.buffer_address = (int) wf_cont_f3_light;
384 ring_node_cwf3_light.buffer_address = (int) wf_cont_f3_light;
385 ring_node_cwf3_light.coarseTime = 0x00;
385 ring_node_cwf3_light.coarseTime = 0x00;
386 ring_node_cwf3_light.fineTime = 0x00;
386 ring_node_cwf3_light.fineTime = 0x00;
387 ring_node_cwf3_light.next = NULL;
387 ring_node_cwf3_light.next = NULL;
388 ring_node_cwf3_light.previous = NULL;
388 ring_node_cwf3_light.previous = NULL;
389 ring_node_cwf3_light.sid = SID_NORM_CWF_F3;
389 ring_node_cwf3_light.sid = SID_NORM_CWF_F3;
390 ring_node_cwf3_light.status = 0x00;
390 ring_node_cwf3_light.status = 0x00;
391
391
392 BOOT_PRINTF("in CWF3 ***\n")
392 BOOT_PRINTF("in CWF3 ***\n")
393
393
394 while(1){
394 while(1){
395 // wait for an RTEMS_EVENT
395 // wait for an RTEMS_EVENT
396 rtems_event_receive( RTEMS_EVENT_0,
396 rtems_event_receive( RTEMS_EVENT_0,
397 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
397 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
398 if ( (lfrCurrentMode == LFR_MODE_NORMAL)
398 if ( (lfrCurrentMode == LFR_MODE_NORMAL)
399 || (lfrCurrentMode == LFR_MODE_SBM1) || (lfrCurrentMode==LFR_MODE_SBM2) )
399 || (lfrCurrentMode == LFR_MODE_SBM1) || (lfrCurrentMode==LFR_MODE_SBM2) )
400 {
400 {
401 ring_node_to_send_cwf = getRingNodeToSendCWF( 3 );
401 ring_node_to_send_cwf = getRingNodeToSendCWF( 3 );
402 if ( (parameter_dump_packet.sy_lfr_n_cwf_long_f3 & 0x01) == 0x01)
402 if ( (parameter_dump_packet.sy_lfr_n_cwf_long_f3 & 0x01) == 0x01)
403 {
403 {
404 PRINTF("send CWF_LONG_F3\n")
404 PRINTF("send CWF_LONG_F3\n")
405 ring_node_to_send_cwf_f3->sid = SID_NORM_CWF_LONG_F3;
405 ring_node_to_send_cwf_f3->sid = SID_NORM_CWF_LONG_F3;
406 status = rtems_message_queue_send( queue_id, &ring_node_to_send_cwf, sizeof( ring_node* ) );
406 status = rtems_message_queue_send( queue_id, &ring_node_to_send_cwf, sizeof( ring_node* ) );
407 }
407 }
408 else
408 else
409 {
409 {
410 PRINTF("send CWF_F3 (light)\n")
410 PRINTF("send CWF_F3 (light)\n")
411 send_waveform_CWF3_light( ring_node_to_send_cwf, &ring_node_cwf3_light, queue_id );
411 send_waveform_CWF3_light( ring_node_to_send_cwf, &ring_node_cwf3_light, queue_id );
412 }
412 }
413
413
414 }
414 }
415 else
415 else
416 {
416 {
417 PRINTF1("in CWF3 *** lfrCurrentMode is %d, no data will be sent\n", lfrCurrentMode)
417 PRINTF1("in CWF3 *** lfrCurrentMode is %d, no data will be sent\n", lfrCurrentMode)
418 }
418 }
419 }
419 }
420 }
420 }
421
421
422 rtems_task cwf2_task(rtems_task_argument argument) // ONLY USED IN BURST AND SBM2
422 rtems_task cwf2_task(rtems_task_argument argument) // ONLY USED IN BURST AND SBM2
423 {
423 {
424 /** This RTEMS task is dedicated to the transmission of continuous waveforms at f2.
424 /** This RTEMS task is dedicated to the transmission of continuous waveforms at f2.
425 *
425 *
426 * @param unused is the starting argument of the RTEMS task
426 * @param unused is the starting argument of the RTEMS task
427 *
427 *
428 * The following data packet is sent by this function:
428 * The following data packet is sent by this function:
429 * - TM_LFR_SCIENCE_BURST_CWF_F2
429 * - TM_LFR_SCIENCE_BURST_CWF_F2
430 * - TM_LFR_SCIENCE_SBM2_CWF_F2
430 * - TM_LFR_SCIENCE_SBM2_CWF_F2
431 *
431 *
432 */
432 */
433
433
434 rtems_event_set event_out;
434 rtems_event_set event_out;
435 rtems_id queue_id;
435 rtems_id queue_id;
436 rtems_status_code status;
436 rtems_status_code status;
437 ring_node *ring_node_to_send;
437 ring_node *ring_node_to_send;
438 unsigned long long int acquisitionTimeF0_asLong;
438 unsigned long long int acquisitionTimeF0_asLong;
439
439
440 acquisitionTimeF0_asLong = 0x00;
440 acquisitionTimeF0_asLong = 0x00;
441
441
442 status = get_message_queue_id_send( &queue_id );
442 status = get_message_queue_id_send( &queue_id );
443 if (status != RTEMS_SUCCESSFUL)
443 if (status != RTEMS_SUCCESSFUL)
444 {
444 {
445 PRINTF1("in CWF2 *** ERR get_message_queue_id_send %d\n", status)
445 PRINTF1("in CWF2 *** ERR get_message_queue_id_send %d\n", status)
446 }
446 }
447
447
448 BOOT_PRINTF("in CWF2 ***\n")
448 BOOT_PRINTF("in CWF2 ***\n")
449
449
450 while(1){
450 while(1){
451 // wait for an RTEMS_EVENT
451 // wait for an RTEMS_EVENT
452 rtems_event_receive( RTEMS_EVENT_MODE_NORM_S1_S2 | RTEMS_EVENT_MODE_BURST,
452 rtems_event_receive( RTEMS_EVENT_MODE_NORM_S1_S2 | RTEMS_EVENT_MODE_BURST,
453 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
453 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
454 ring_node_to_send = getRingNodeToSendCWF( 2 );
454 ring_node_to_send = getRingNodeToSendCWF( 2 );
455 if (event_out == RTEMS_EVENT_MODE_BURST)
455 if (event_out == RTEMS_EVENT_MODE_BURST)
456 {
456 {
457 status = rtems_message_queue_send( queue_id, &ring_node_to_send, sizeof( ring_node* ) );
457 status = rtems_message_queue_send( queue_id, &ring_node_to_send, sizeof( ring_node* ) );
458 }
458 }
459 else if (event_out == RTEMS_EVENT_MODE_NORM_S1_S2)
459 else if (event_out == RTEMS_EVENT_MODE_NORM_S1_S2)
460 {
460 {
461 if ( lfrCurrentMode == LFR_MODE_SBM2 )
461 if ( lfrCurrentMode == LFR_MODE_SBM2 )
462 {
462 {
463 status = rtems_message_queue_send( queue_id, &ring_node_to_send, sizeof( ring_node* ) );
463 status = rtems_message_queue_send( queue_id, &ring_node_to_send, sizeof( ring_node* ) );
464 }
464 }
465 // launch snapshot extraction if needed
465 // launch snapshot extraction if needed
466 if (extractSWF2 == true)
466 if (extractSWF2 == true)
467 {
467 {
468 ring_node_to_send_swf_f2 = ring_node_to_send_cwf_f2;
468 ring_node_to_send_swf_f2 = ring_node_to_send_cwf_f2;
469 // extract the snapshot
469 // extract the snapshot
470 build_snapshot_from_ring( ring_node_to_send_swf_f2, 2, acquisitionTimeF0_asLong,
470 build_snapshot_from_ring( ring_node_to_send_swf_f2, 2, acquisitionTimeF0_asLong,
471 &ring_node_swf2_extracted, swf2_extracted );
471 &ring_node_swf2_extracted, swf2_extracted );
472 // send the snapshot when built
472 // send the snapshot when built
473 status = rtems_event_send( Task_id[TASKID_WFRM], RTEMS_EVENT_MODE_SBM2 );
473 status = rtems_event_send( Task_id[TASKID_WFRM], RTEMS_EVENT_MODE_SBM2 );
474 extractSWF2 = false;
474 extractSWF2 = false;
475 swf2_ready = true;
475 swf2_ready = true;
476 }
476 }
477 if (swf0_ready_flag_f2 == true)
477 if (swf0_ready_flag_f2 == true)
478 {
478 {
479 extractSWF2 = true;
479 extractSWF2 = true;
480 // record the acquition time of the f0 snapshot to use to build the snapshot at f2
480 // record the acquition time of the f0 snapshot to use to build the snapshot at f2
481 acquisitionTimeF0_asLong = get_acquisition_time( (unsigned char *) &ring_node_to_send_swf_f0->coarseTime );
481 acquisitionTimeF0_asLong = get_acquisition_time( (unsigned char *) &ring_node_to_send_swf_f0->coarseTime );
482 swf0_ready_flag_f2 = false;
482 swf0_ready_flag_f2 = false;
483 }
483 }
484 }
484 }
485 }
485 }
486 }
486 }
487
487
488 rtems_task cwf1_task(rtems_task_argument argument) // ONLY USED IN SBM1
488 rtems_task cwf1_task(rtems_task_argument argument) // ONLY USED IN SBM1
489 {
489 {
490 /** This RTEMS task is dedicated to the transmission of continuous waveforms at f1.
490 /** This RTEMS task is dedicated to the transmission of continuous waveforms at f1.
491 *
491 *
492 * @param unused is the starting argument of the RTEMS task
492 * @param unused is the starting argument of the RTEMS task
493 *
493 *
494 * The following data packet is sent by this function:
494 * The following data packet is sent by this function:
495 * - TM_LFR_SCIENCE_SBM1_CWF_F1
495 * - TM_LFR_SCIENCE_SBM1_CWF_F1
496 *
496 *
497 */
497 */
498
498
499 rtems_event_set event_out;
499 rtems_event_set event_out;
500 rtems_id queue_id;
500 rtems_id queue_id;
501 rtems_status_code status;
501 rtems_status_code status;
502
502
503 ring_node *ring_node_to_send_cwf;
503 ring_node *ring_node_to_send_cwf;
504
504
505 status = get_message_queue_id_send( &queue_id );
505 status = get_message_queue_id_send( &queue_id );
506 if (status != RTEMS_SUCCESSFUL)
506 if (status != RTEMS_SUCCESSFUL)
507 {
507 {
508 PRINTF1("in CWF1 *** ERR get_message_queue_id_send %d\n", status)
508 PRINTF1("in CWF1 *** ERR get_message_queue_id_send %d\n", status)
509 }
509 }
510
510
511 BOOT_PRINTF("in CWF1 ***\n");
511 BOOT_PRINTF("in CWF1 ***\n");
512
512
513 while(1){
513 while(1){
514 // wait for an RTEMS_EVENT
514 // wait for an RTEMS_EVENT
515 rtems_event_receive( RTEMS_EVENT_MODE_NORM_S1_S2,
515 rtems_event_receive( RTEMS_EVENT_MODE_NORM_S1_S2,
516 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
516 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
517 ring_node_to_send_cwf = getRingNodeToSendCWF( 1 );
517 ring_node_to_send_cwf = getRingNodeToSendCWF( 1 );
518 ring_node_to_send_cwf_f1->sid = SID_SBM1_CWF_F1;
518 ring_node_to_send_cwf_f1->sid = SID_SBM1_CWF_F1;
519 if (lfrCurrentMode == LFR_MODE_SBM1)
519 if (lfrCurrentMode == LFR_MODE_SBM1)
520 {
520 {
521 status = rtems_message_queue_send( queue_id, &ring_node_to_send_cwf, sizeof( ring_node* ) );
521 status = rtems_message_queue_send( queue_id, &ring_node_to_send_cwf, sizeof( ring_node* ) );
522 if (status != 0)
522 if (status != 0)
523 {
523 {
524 PRINTF("cwf sending failed\n")
524 PRINTF("cwf sending failed\n")
525 }
525 }
526 }
526 }
527 // launch snapshot extraction if needed
527 // launch snapshot extraction if needed
528 if (extractSWF1 == true)
528 if (extractSWF1 == true)
529 {
529 {
530 ring_node_to_send_swf_f1 = ring_node_to_send_cwf;
530 ring_node_to_send_swf_f1 = ring_node_to_send_cwf;
531 // launch the snapshot extraction
531 // launch the snapshot extraction
532 status = rtems_event_send( Task_id[TASKID_SWBD], RTEMS_EVENT_MODE_NORM_S1_S2 );
532 status = rtems_event_send( Task_id[TASKID_SWBD], RTEMS_EVENT_MODE_NORM_S1_S2 );
533 extractSWF1 = false;
533 extractSWF1 = false;
534 }
534 }
535 if (swf0_ready_flag_f1 == true)
535 if (swf0_ready_flag_f1 == true)
536 {
536 {
537 extractSWF1 = true;
537 extractSWF1 = true;
538 swf0_ready_flag_f1 = false; // this step shall be executed only one time
538 swf0_ready_flag_f1 = false; // this step shall be executed only one time
539 }
539 }
540 if ((swf1_ready == true) && (swf2_ready == true)) // swf_f1 is ready after the extraction
540 if ((swf1_ready == true) && (swf2_ready == true)) // swf_f1 is ready after the extraction
541 {
541 {
542 status = rtems_event_send( Task_id[TASKID_WFRM], RTEMS_EVENT_MODE_NORMAL );
542 status = rtems_event_send( Task_id[TASKID_WFRM], RTEMS_EVENT_MODE_NORMAL );
543 swf1_ready = false;
543 swf1_ready = false;
544 swf2_ready = false;
544 swf2_ready = false;
545 }
545 }
546 }
546 }
547 }
547 }
548
548
549 rtems_task swbd_task(rtems_task_argument argument)
549 rtems_task swbd_task(rtems_task_argument argument)
550 {
550 {
551 /** This RTEMS task is dedicated to the building of snapshots from different continuous waveforms buffers.
551 /** This RTEMS task is dedicated to the building of snapshots from different continuous waveforms buffers.
552 *
552 *
553 * @param unused is the starting argument of the RTEMS task
553 * @param unused is the starting argument of the RTEMS task
554 *
554 *
555 */
555 */
556
556
557 rtems_event_set event_out;
557 rtems_event_set event_out;
558 unsigned long long int acquisitionTimeF0_asLong;
558 unsigned long long int acquisitionTimeF0_asLong;
559
559
560 acquisitionTimeF0_asLong = 0x00;
560 acquisitionTimeF0_asLong = 0x00;
561
561
562 BOOT_PRINTF("in SWBD ***\n")
562 BOOT_PRINTF("in SWBD ***\n")
563
563
564 while(1){
564 while(1){
565 // wait for an RTEMS_EVENT
565 // wait for an RTEMS_EVENT
566 rtems_event_receive( RTEMS_EVENT_MODE_NORM_S1_S2,
566 rtems_event_receive( RTEMS_EVENT_MODE_NORM_S1_S2,
567 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
567 RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &event_out);
568 if (event_out == RTEMS_EVENT_MODE_NORM_S1_S2)
568 if (event_out == RTEMS_EVENT_MODE_NORM_S1_S2)
569 {
569 {
570 acquisitionTimeF0_asLong = get_acquisition_time( (unsigned char *) &ring_node_to_send_swf_f0->coarseTime );
570 acquisitionTimeF0_asLong = get_acquisition_time( (unsigned char *) &ring_node_to_send_swf_f0->coarseTime );
571 build_snapshot_from_ring( ring_node_to_send_swf_f1, 1, acquisitionTimeF0_asLong,
571 build_snapshot_from_ring( ring_node_to_send_swf_f1, 1, acquisitionTimeF0_asLong,
572 &ring_node_swf1_extracted, swf1_extracted );
572 &ring_node_swf1_extracted, swf1_extracted );
573 swf1_ready = true; // the snapshot has been extracted and is ready to be sent
573 swf1_ready = true; // the snapshot has been extracted and is ready to be sent
574 }
574 }
575 else
575 else
576 {
576 {
577 PRINTF1("in SWBD *** unexpected rtems event received %x\n", (int) event_out)
577 PRINTF1("in SWBD *** unexpected rtems event received %x\n", (int) event_out)
578 }
578 }
579 }
579 }
580 }
580 }
581
581
582 //******************
582 //******************
583 // general functions
583 // general functions
584
584
585 void WFP_init_rings( void )
585 void WFP_init_rings( void )
586 {
586 {
587 // F0 RING
587 // F0 RING
588 init_ring( waveform_ring_f0, NB_RING_NODES_F0, wf_buffer_f0, WFRM_BUFFER );
588 init_ring( waveform_ring_f0, NB_RING_NODES_F0, wf_buffer_f0, WFRM_BUFFER );
589 // F1 RING
589 // F1 RING
590 init_ring( waveform_ring_f1, NB_RING_NODES_F1, wf_buffer_f1, WFRM_BUFFER );
590 init_ring( waveform_ring_f1, NB_RING_NODES_F1, wf_buffer_f1, WFRM_BUFFER );
591 // F2 RING
591 // F2 RING
592 init_ring( waveform_ring_f2, NB_RING_NODES_F2, wf_buffer_f2, WFRM_BUFFER );
592 init_ring( waveform_ring_f2, NB_RING_NODES_F2, wf_buffer_f2, WFRM_BUFFER );
593 // F3 RING
593 // F3 RING
594 init_ring( waveform_ring_f3, NB_RING_NODES_F3, wf_buffer_f3, WFRM_BUFFER );
594 init_ring( waveform_ring_f3, NB_RING_NODES_F3, wf_buffer_f3, WFRM_BUFFER );
595
595
596 ring_node_swf1_extracted.buffer_address = (int) swf1_extracted;
596 ring_node_swf1_extracted.buffer_address = (int) swf1_extracted;
597 ring_node_swf2_extracted.buffer_address = (int) swf2_extracted;
597 ring_node_swf2_extracted.buffer_address = (int) swf2_extracted;
598
598
599 DEBUG_PRINTF1("waveform_ring_f0 @%x\n", (unsigned int) waveform_ring_f0)
599 DEBUG_PRINTF1("waveform_ring_f0 @%x\n", (unsigned int) waveform_ring_f0)
600 DEBUG_PRINTF1("waveform_ring_f1 @%x\n", (unsigned int) waveform_ring_f1)
600 DEBUG_PRINTF1("waveform_ring_f1 @%x\n", (unsigned int) waveform_ring_f1)
601 DEBUG_PRINTF1("waveform_ring_f2 @%x\n", (unsigned int) waveform_ring_f2)
601 DEBUG_PRINTF1("waveform_ring_f2 @%x\n", (unsigned int) waveform_ring_f2)
602 DEBUG_PRINTF1("waveform_ring_f3 @%x\n", (unsigned int) waveform_ring_f3)
602 DEBUG_PRINTF1("waveform_ring_f3 @%x\n", (unsigned int) waveform_ring_f3)
603 DEBUG_PRINTF1("wf_buffer_f0 @%x\n", (unsigned int) wf_buffer_f0)
603 DEBUG_PRINTF1("wf_buffer_f0 @%x\n", (unsigned int) wf_buffer_f0)
604 DEBUG_PRINTF1("wf_buffer_f1 @%x\n", (unsigned int) wf_buffer_f1)
604 DEBUG_PRINTF1("wf_buffer_f1 @%x\n", (unsigned int) wf_buffer_f1)
605 DEBUG_PRINTF1("wf_buffer_f2 @%x\n", (unsigned int) wf_buffer_f2)
605 DEBUG_PRINTF1("wf_buffer_f2 @%x\n", (unsigned int) wf_buffer_f2)
606 DEBUG_PRINTF1("wf_buffer_f3 @%x\n", (unsigned int) wf_buffer_f3)
606 DEBUG_PRINTF1("wf_buffer_f3 @%x\n", (unsigned int) wf_buffer_f3)
607
607
608 }
608 }
609
609
610 void WFP_reset_current_ring_nodes( void )
610 void WFP_reset_current_ring_nodes( void )
611 {
611 {
612 current_ring_node_f0 = waveform_ring_f0[0].next;
612 current_ring_node_f0 = waveform_ring_f0[0].next;
613 current_ring_node_f1 = waveform_ring_f1[0].next;
613 current_ring_node_f1 = waveform_ring_f1[0].next;
614 current_ring_node_f2 = waveform_ring_f2[0].next;
614 current_ring_node_f2 = waveform_ring_f2[0].next;
615 current_ring_node_f3 = waveform_ring_f3[0].next;
615 current_ring_node_f3 = waveform_ring_f3[0].next;
616
616
617 ring_node_to_send_swf_f0 = waveform_ring_f0;
617 ring_node_to_send_swf_f0 = waveform_ring_f0;
618 ring_node_to_send_swf_f1 = waveform_ring_f1;
618 ring_node_to_send_swf_f1 = waveform_ring_f1;
619 ring_node_to_send_swf_f2 = waveform_ring_f2;
619 ring_node_to_send_swf_f2 = waveform_ring_f2;
620
620
621 ring_node_to_send_cwf_f1 = waveform_ring_f1;
621 ring_node_to_send_cwf_f1 = waveform_ring_f1;
622 ring_node_to_send_cwf_f2 = waveform_ring_f2;
622 ring_node_to_send_cwf_f2 = waveform_ring_f2;
623 ring_node_to_send_cwf_f3 = waveform_ring_f3;
623 ring_node_to_send_cwf_f3 = waveform_ring_f3;
624 }
624 }
625
625
626 int send_waveform_CWF3_light( ring_node *ring_node_to_send, ring_node *ring_node_cwf3_light, rtems_id queue_id )
626 int send_waveform_CWF3_light( ring_node *ring_node_to_send, ring_node *ring_node_cwf3_light, rtems_id queue_id )
627 {
627 {
628 /** This function sends CWF_F3 CCSDS packets without the b1, b2 and b3 data.
628 /** This function sends CWF_F3 CCSDS packets without the b1, b2 and b3 data.
629 *
629 *
630 * @param waveform points to the buffer containing the data that will be send.
630 * @param waveform points to the buffer containing the data that will be send.
631 * @param headerCWF points to a table of headers that have been prepared for the data transmission.
631 * @param headerCWF points to a table of headers that have been prepared for the data transmission.
632 * @param queue_id is the id of the rtems queue to which spw_ioctl_pkt_send structures will be send. The structures
632 * @param queue_id is the id of the rtems queue to which spw_ioctl_pkt_send structures will be send. The structures
633 * contain information to setup the transmission of the data packets.
633 * contain information to setup the transmission of the data packets.
634 *
634 *
635 * By default, CWF_F3 packet are send without the b1, b2 and b3 data. This function rebuilds a data buffer
635 * By default, CWF_F3 packet are send without the b1, b2 and b3 data. This function rebuilds a data buffer
636 * from the incoming data and sends it in 7 packets, 6 containing 340 blocks and 1 one containing 8 blocks.
636 * from the incoming data and sends it in 7 packets, 6 containing 340 blocks and 1 one containing 8 blocks.
637 *
637 *
638 */
638 */
639
639
640 unsigned int i;
640 unsigned int i;
641 int ret;
641 int ret;
642 rtems_status_code status;
642 rtems_status_code status;
643
643
644 char *sample;
644 char *sample;
645 int *dataPtr;
645 int *dataPtr;
646
646
647 ret = LFR_DEFAULT;
647 ret = LFR_DEFAULT;
648
648
649 dataPtr = (int*) ring_node_to_send->buffer_address;
649 dataPtr = (int*) ring_node_to_send->buffer_address;
650
650
651 ring_node_cwf3_light->coarseTime = ring_node_to_send->coarseTime;
651 ring_node_cwf3_light->coarseTime = ring_node_to_send->coarseTime;
652 ring_node_cwf3_light->fineTime = ring_node_to_send->fineTime;
652 ring_node_cwf3_light->fineTime = ring_node_to_send->fineTime;
653
653
654 //**********************
654 //**********************
655 // BUILD CWF3_light DATA
655 // BUILD CWF3_light DATA
656 for ( i=0; i< NB_SAMPLES_PER_SNAPSHOT; i++)
656 for ( i=0; i< NB_SAMPLES_PER_SNAPSHOT; i++)
657 {
657 {
658 sample = (char*) &dataPtr[ (i * NB_WORDS_SWF_BLK) ];
658 sample = (char*) &dataPtr[ (i * NB_WORDS_SWF_BLK) ];
659 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) ] = sample[ 0 ];
659 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) ] = sample[ 0 ];
660 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) + 1 ] = sample[ 1 ];
660 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) + 1 ] = sample[ 1 ];
661 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) + 2 ] = sample[ 2 ];
661 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) + 2 ] = sample[ 2 ];
662 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) + 3 ] = sample[ 3 ];
662 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) + 3 ] = sample[ 3 ];
663 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) + 4 ] = sample[ 4 ];
663 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) + 4 ] = sample[ 4 ];
664 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) + 5 ] = sample[ 5 ];
664 wf_cont_f3_light[ (i * NB_BYTES_CWF3_LIGHT_BLK) + 5 ] = sample[ 5 ];
665 }
665 }
666
666
667 // SEND PACKET
667 // SEND PACKET
668 status = rtems_message_queue_send( queue_id, &ring_node_cwf3_light, sizeof( ring_node* ) );
668 status = rtems_message_queue_send( queue_id, &ring_node_cwf3_light, sizeof( ring_node* ) );
669 if (status != RTEMS_SUCCESSFUL) {
669 if (status != RTEMS_SUCCESSFUL) {
670 ret = LFR_DEFAULT;
670 ret = LFR_DEFAULT;
671 }
671 }
672
672
673 return ret;
673 return ret;
674 }
674 }
675
675
676 void compute_acquisition_time( unsigned int coarseTime, unsigned int fineTime,
676 void compute_acquisition_time( unsigned int coarseTime, unsigned int fineTime,
677 unsigned int sid, unsigned char pa_lfr_pkt_nr, unsigned char * acquisitionTime )
677 unsigned int sid, unsigned char pa_lfr_pkt_nr, unsigned char * acquisitionTime )
678 {
678 {
679 unsigned long long int acquisitionTimeAsLong;
679 unsigned long long int acquisitionTimeAsLong;
680 unsigned char localAcquisitionTime[6];
680 unsigned char localAcquisitionTime[6];
681 double deltaT;
681 double deltaT;
682
682
683 deltaT = 0.;
683 deltaT = 0.;
684
684
685 localAcquisitionTime[0] = (unsigned char) ( coarseTime >> 24 );
685 localAcquisitionTime[0] = (unsigned char) ( coarseTime >> 24 );
686 localAcquisitionTime[1] = (unsigned char) ( coarseTime >> 16 );
686 localAcquisitionTime[1] = (unsigned char) ( coarseTime >> 16 );
687 localAcquisitionTime[2] = (unsigned char) ( coarseTime >> 8 );
687 localAcquisitionTime[2] = (unsigned char) ( coarseTime >> 8 );
688 localAcquisitionTime[3] = (unsigned char) ( coarseTime );
688 localAcquisitionTime[3] = (unsigned char) ( coarseTime );
689 localAcquisitionTime[4] = (unsigned char) ( fineTime >> 8 );
689 localAcquisitionTime[4] = (unsigned char) ( fineTime >> 8 );
690 localAcquisitionTime[5] = (unsigned char) ( fineTime );
690 localAcquisitionTime[5] = (unsigned char) ( fineTime );
691
691
692 acquisitionTimeAsLong = ( (unsigned long long int) localAcquisitionTime[0] << 40 )
692 acquisitionTimeAsLong = ( (unsigned long long int) localAcquisitionTime[0] << 40 )
693 + ( (unsigned long long int) localAcquisitionTime[1] << 32 )
693 + ( (unsigned long long int) localAcquisitionTime[1] << 32 )
694 + ( (unsigned long long int) localAcquisitionTime[2] << 24 )
694 + ( (unsigned long long int) localAcquisitionTime[2] << 24 )
695 + ( (unsigned long long int) localAcquisitionTime[3] << 16 )
695 + ( (unsigned long long int) localAcquisitionTime[3] << 16 )
696 + ( (unsigned long long int) localAcquisitionTime[4] << 8 )
696 + ( (unsigned long long int) localAcquisitionTime[4] << 8 )
697 + ( (unsigned long long int) localAcquisitionTime[5] );
697 + ( (unsigned long long int) localAcquisitionTime[5] );
698
698
699 switch( sid )
699 switch( sid )
700 {
700 {
701 case SID_NORM_SWF_F0:
701 case SID_NORM_SWF_F0:
702 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_304 * 65536. / 24576. ;
702 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_304 * 65536. / 24576. ;
703 break;
703 break;
704
704
705 case SID_NORM_SWF_F1:
705 case SID_NORM_SWF_F1:
706 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_304 * 65536. / 4096. ;
706 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_304 * 65536. / 4096. ;
707 break;
707 break;
708
708
709 case SID_NORM_SWF_F2:
709 case SID_NORM_SWF_F2:
710 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_304 * 65536. / 256. ;
710 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_304 * 65536. / 256. ;
711 break;
711 break;
712
712
713 case SID_SBM1_CWF_F1:
713 case SID_SBM1_CWF_F1:
714 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_CWF * 65536. / 4096. ;
714 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_CWF * 65536. / 4096. ;
715 break;
715 break;
716
716
717 case SID_SBM2_CWF_F2:
717 case SID_SBM2_CWF_F2:
718 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_CWF * 65536. / 256. ;
718 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_CWF * 65536. / 256. ;
719 break;
719 break;
720
720
721 case SID_BURST_CWF_F2:
721 case SID_BURST_CWF_F2:
722 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_CWF * 65536. / 256. ;
722 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_CWF * 65536. / 256. ;
723 break;
723 break;
724
724
725 case SID_NORM_CWF_F3:
725 case SID_NORM_CWF_F3:
726 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_CWF_SHORT_F3 * 65536. / 16. ;
726 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_CWF_SHORT_F3 * 65536. / 16. ;
727 break;
727 break;
728
728
729 case SID_NORM_CWF_LONG_F3:
729 case SID_NORM_CWF_LONG_F3:
730 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_CWF * 65536. / 16. ;
730 deltaT = ( (double ) (pa_lfr_pkt_nr) ) * BLK_NR_CWF * 65536. / 16. ;
731 break;
731 break;
732
732
733 default:
733 default:
734 PRINTF1("in compute_acquisition_time *** ERR unexpected sid %d\n", sid)
734 PRINTF1("in compute_acquisition_time *** ERR unexpected sid %d\n", sid)
735 deltaT = 0.;
735 deltaT = 0.;
736 break;
736 break;
737 }
737 }
738
738
739 acquisitionTimeAsLong = acquisitionTimeAsLong + (unsigned long long int) deltaT;
739 acquisitionTimeAsLong = acquisitionTimeAsLong + (unsigned long long int) deltaT;
740 //
740 //
741 acquisitionTime[0] = (unsigned char) (acquisitionTimeAsLong >> 40);
741 acquisitionTime[0] = (unsigned char) (acquisitionTimeAsLong >> 40);
742 acquisitionTime[1] = (unsigned char) (acquisitionTimeAsLong >> 32);
742 acquisitionTime[1] = (unsigned char) (acquisitionTimeAsLong >> 32);
743 acquisitionTime[2] = (unsigned char) (acquisitionTimeAsLong >> 24);
743 acquisitionTime[2] = (unsigned char) (acquisitionTimeAsLong >> 24);
744 acquisitionTime[3] = (unsigned char) (acquisitionTimeAsLong >> 16);
744 acquisitionTime[3] = (unsigned char) (acquisitionTimeAsLong >> 16);
745 acquisitionTime[4] = (unsigned char) (acquisitionTimeAsLong >> 8 );
745 acquisitionTime[4] = (unsigned char) (acquisitionTimeAsLong >> 8 );
746 acquisitionTime[5] = (unsigned char) (acquisitionTimeAsLong );
746 acquisitionTime[5] = (unsigned char) (acquisitionTimeAsLong );
747
747
748 }
748 }
749
749
750 void build_snapshot_from_ring( ring_node *ring_node_to_send,
750 void build_snapshot_from_ring( ring_node *ring_node_to_send,
751 unsigned char frequencyChannel,
751 unsigned char frequencyChannel,
752 unsigned long long int acquisitionTimeF0_asLong,
752 unsigned long long int acquisitionTimeF0_asLong,
753 ring_node *ring_node_swf_extracted,
753 ring_node *ring_node_swf_extracted,
754 int *swf_extracted)
754 int *swf_extracted)
755 {
755 {
756 unsigned int i;
756 unsigned int i;
757 unsigned long long int centerTime_asLong;
757 unsigned long long int centerTime_asLong;
758 unsigned long long int acquisitionTime_asLong;
758 unsigned long long int acquisitionTime_asLong;
759 unsigned long long int bufferAcquisitionTime_asLong;
759 unsigned long long int bufferAcquisitionTime_asLong;
760 unsigned char *ptr1;
760 unsigned char *ptr1;
761 unsigned char *ptr2;
761 unsigned char *ptr2;
762 unsigned char *timeCharPtr;
762 unsigned char *timeCharPtr;
763 unsigned char nb_ring_nodes;
763 unsigned char nb_ring_nodes;
764 unsigned long long int frequency_asLong;
764 unsigned long long int frequency_asLong;
765 unsigned long long int nbTicksPerSample_asLong;
765 unsigned long long int nbTicksPerSample_asLong;
766 unsigned long long int nbSamplesPart1_asLong;
766 unsigned long long int nbSamplesPart1_asLong;
767 unsigned long long int sampleOffset_asLong;
767 unsigned long long int sampleOffset_asLong;
768
768
769 unsigned int deltaT_F0;
769 unsigned int deltaT_F0;
770 unsigned int deltaT_F1;
770 unsigned int deltaT_F1;
771 unsigned long long int deltaT_F2;
771 unsigned long long int deltaT_F2;
772
772
773 deltaT_F0 = 2731; // (2048. / 24576. / 2.) * 65536. = 2730.667;
773 deltaT_F0 = 2731; // (2048. / 24576. / 2.) * 65536. = 2730.667;
774 deltaT_F1 = 16384; // (2048. / 4096. / 2.) * 65536. = 16384;
774 deltaT_F1 = 16384; // (2048. / 4096. / 2.) * 65536. = 16384;
775 deltaT_F2 = 262144; // (2048. / 256. / 2.) * 65536. = 262144;
775 deltaT_F2 = 262144; // (2048. / 256. / 2.) * 65536. = 262144;
776 sampleOffset_asLong = 0x00;
776 sampleOffset_asLong = 0x00;
777
777
778 // (1) get the f0 acquisition time => the value is passed in argument
778 // (1) get the f0 acquisition time => the value is passed in argument
779
779
780 // (2) compute the central reference time
780 // (2) compute the central reference time
781 centerTime_asLong = acquisitionTimeF0_asLong + deltaT_F0;
781 centerTime_asLong = acquisitionTimeF0_asLong + deltaT_F0;
782
782
783 // (3) compute the acquisition time of the current snapshot
783 // (3) compute the acquisition time of the current snapshot
784 switch(frequencyChannel)
784 switch(frequencyChannel)
785 {
785 {
786 case 1: // 1 is for F1 = 4096 Hz
786 case 1: // 1 is for F1 = 4096 Hz
787 acquisitionTime_asLong = centerTime_asLong - deltaT_F1;
787 acquisitionTime_asLong = centerTime_asLong - deltaT_F1;
788 nb_ring_nodes = NB_RING_NODES_F1;
788 nb_ring_nodes = NB_RING_NODES_F1;
789 frequency_asLong = 4096;
789 frequency_asLong = 4096;
790 nbTicksPerSample_asLong = 16; // 65536 / 4096;
790 nbTicksPerSample_asLong = 16; // 65536 / 4096;
791 break;
791 break;
792 case 2: // 2 is for F2 = 256 Hz
792 case 2: // 2 is for F2 = 256 Hz
793 acquisitionTime_asLong = centerTime_asLong - deltaT_F2;
793 acquisitionTime_asLong = centerTime_asLong - deltaT_F2;
794 nb_ring_nodes = NB_RING_NODES_F2;
794 nb_ring_nodes = NB_RING_NODES_F2;
795 frequency_asLong = 256;
795 frequency_asLong = 256;
796 nbTicksPerSample_asLong = 256; // 65536 / 256;
796 nbTicksPerSample_asLong = 256; // 65536 / 256;
797 break;
797 break;
798 default:
798 default:
799 acquisitionTime_asLong = centerTime_asLong;
799 acquisitionTime_asLong = centerTime_asLong;
800 frequency_asLong = 256;
800 frequency_asLong = 256;
801 nbTicksPerSample_asLong = 256;
801 nbTicksPerSample_asLong = 256;
802 break;
802 break;
803 }
803 }
804
804
805 //****************************************************************************
805 //****************************************************************************
806 // (4) search the ring_node with the acquisition time <= acquisitionTime_asLong
806 // (4) search the ring_node with the acquisition time <= acquisitionTime_asLong
807 for (i=0; i<nb_ring_nodes; i++)
807 for (i=0; i<nb_ring_nodes; i++)
808 {
808 {
809 //PRINTF1("%d ... ", i);
809 //PRINTF1("%d ... ", i);
810 bufferAcquisitionTime_asLong = get_acquisition_time( (unsigned char *) &ring_node_to_send->coarseTime );
810 bufferAcquisitionTime_asLong = get_acquisition_time( (unsigned char *) &ring_node_to_send->coarseTime );
811 if (bufferAcquisitionTime_asLong <= acquisitionTime_asLong)
811 if (bufferAcquisitionTime_asLong <= acquisitionTime_asLong)
812 {
812 {
813 //PRINTF1("buffer found with acquisition time = %llx\n", bufferAcquisitionTime_asLong);
813 //PRINTF1("buffer found with acquisition time = %llx\n", bufferAcquisitionTime_asLong);
814 break;
814 break;
815 }
815 }
816 ring_node_to_send = ring_node_to_send->previous;
816 ring_node_to_send = ring_node_to_send->previous;
817 }
817 }
818
818
819 // (5) compute the number of samples to take in the current buffer
819 // (5) compute the number of samples to take in the current buffer
820 sampleOffset_asLong = ((acquisitionTime_asLong - bufferAcquisitionTime_asLong) * frequency_asLong ) >> 16;
820 sampleOffset_asLong = ((acquisitionTime_asLong - bufferAcquisitionTime_asLong) * frequency_asLong ) >> 16;
821 nbSamplesPart1_asLong = NB_SAMPLES_PER_SNAPSHOT - sampleOffset_asLong;
821 nbSamplesPart1_asLong = NB_SAMPLES_PER_SNAPSHOT - sampleOffset_asLong;
822 //PRINTF2("sampleOffset_asLong = %lld, nbSamplesPart1_asLong = %lld\n", sampleOffset_asLong, nbSamplesPart1_asLong);
822 //PRINTF2("sampleOffset_asLong = %lld, nbSamplesPart1_asLong = %lld\n", sampleOffset_asLong, nbSamplesPart1_asLong);
823
823
824 // (6) compute the final acquisition time
824 // (6) compute the final acquisition time
825 acquisitionTime_asLong = bufferAcquisitionTime_asLong +
825 acquisitionTime_asLong = bufferAcquisitionTime_asLong +
826 sampleOffset_asLong * nbTicksPerSample_asLong;
826 sampleOffset_asLong * nbTicksPerSample_asLong;
827
827
828 // (7) copy the acquisition time at the beginning of the extrated snapshot
828 // (7) copy the acquisition time at the beginning of the extrated snapshot
829 ptr1 = (unsigned char*) &acquisitionTime_asLong;
829 ptr1 = (unsigned char*) &acquisitionTime_asLong;
830 // fine time
830 // fine time
831 ptr2 = (unsigned char*) &ring_node_swf_extracted->fineTime;
831 ptr2 = (unsigned char*) &ring_node_swf_extracted->fineTime;
832 ptr2[2] = ptr1[ 4 + 2 ];
832 ptr2[2] = ptr1[ 4 + 2 ];
833 ptr2[3] = ptr1[ 5 + 2 ];
833 ptr2[3] = ptr1[ 5 + 2 ];
834 // coarse time
834 // coarse time
835 ptr2 = (unsigned char*) &ring_node_swf_extracted->coarseTime;
835 ptr2 = (unsigned char*) &ring_node_swf_extracted->coarseTime;
836 ptr2[0] = ptr1[ 0 + 2 ];
836 ptr2[0] = ptr1[ 0 + 2 ];
837 ptr2[1] = ptr1[ 1 + 2 ];
837 ptr2[1] = ptr1[ 1 + 2 ];
838 ptr2[2] = ptr1[ 2 + 2 ];
838 ptr2[2] = ptr1[ 2 + 2 ];
839 ptr2[3] = ptr1[ 3 + 2 ];
839 ptr2[3] = ptr1[ 3 + 2 ];
840
840
841 // re set the synchronization bit
841 // re set the synchronization bit
842 timeCharPtr = (unsigned char*) &ring_node_to_send->coarseTime;
842 timeCharPtr = (unsigned char*) &ring_node_to_send->coarseTime;
843 ptr2[0] = ptr2[0] | (timeCharPtr[0] & 0x80); // [1000 0000]
843 ptr2[0] = ptr2[0] | (timeCharPtr[0] & 0x80); // [1000 0000]
844
844
845 if ( (nbSamplesPart1_asLong >= NB_SAMPLES_PER_SNAPSHOT) | (nbSamplesPart1_asLong < 0) )
845 if ( (nbSamplesPart1_asLong >= NB_SAMPLES_PER_SNAPSHOT) | (nbSamplesPart1_asLong < 0) )
846 {
846 {
847 nbSamplesPart1_asLong = 0;
847 nbSamplesPart1_asLong = 0;
848 }
848 }
849 // copy the part 1 of the snapshot in the extracted buffer
849 // copy the part 1 of the snapshot in the extracted buffer
850 for ( i = 0; i < (nbSamplesPart1_asLong * NB_WORDS_SWF_BLK); i++ )
850 for ( i = 0; i < (nbSamplesPart1_asLong * NB_WORDS_SWF_BLK); i++ )
851 {
851 {
852 swf_extracted[i] =
852 swf_extracted[i] =
853 ((int*) ring_node_to_send->buffer_address)[ i + (sampleOffset_asLong * NB_WORDS_SWF_BLK) ];
853 ((int*) ring_node_to_send->buffer_address)[ i + (sampleOffset_asLong * NB_WORDS_SWF_BLK) ];
854 }
854 }
855 // copy the part 2 of the snapshot in the extracted buffer
855 // copy the part 2 of the snapshot in the extracted buffer
856 ring_node_to_send = ring_node_to_send->next;
856 ring_node_to_send = ring_node_to_send->next;
857 for ( i = (nbSamplesPart1_asLong * NB_WORDS_SWF_BLK); i < (NB_SAMPLES_PER_SNAPSHOT * NB_WORDS_SWF_BLK); i++ )
857 for ( i = (nbSamplesPart1_asLong * NB_WORDS_SWF_BLK); i < (NB_SAMPLES_PER_SNAPSHOT * NB_WORDS_SWF_BLK); i++ )
858 {
858 {
859 swf_extracted[i] =
859 swf_extracted[i] =
860 ((int*) ring_node_to_send->buffer_address)[ (i-(nbSamplesPart1_asLong * NB_WORDS_SWF_BLK)) ];
860 ((int*) ring_node_to_send->buffer_address)[ (i-(nbSamplesPart1_asLong * NB_WORDS_SWF_BLK)) ];
861 }
861 }
862 }
862 }
863
863
864 void snapshot_resynchronization( unsigned char *timePtr )
864 void snapshot_resynchronization( unsigned char *timePtr )
865 {
865 {
866 unsigned long long int acquisitionTime;
866 unsigned long long int acquisitionTime;
867 unsigned long long int centerTime;
867 unsigned long long int centerTime;
868 unsigned long long int previousTick;
868 unsigned long long int previousTick;
869 unsigned long long int nextTick;
869 unsigned long long int nextTick;
870 unsigned long long int deltaPreviousTick;
870 unsigned long long int deltaPreviousTick;
871 unsigned long long int deltaNextTick;
871 unsigned long long int deltaNextTick;
872 unsigned int deltaTickInF2;
872 int deltaTickInF2;
873 double deltaPrevious_ms;
873 double deltaPrevious_ms;
874 double deltaNext_ms;
874 double deltaNext_ms;
875 double correctionInF2;
876 static unsigned char resynchroEngaged = 0;
875
877
876 // get acquisition time in fine time ticks
878 if (resynchroEngaged == 0)
877 acquisitionTime = get_acquisition_time( timePtr );
879 {
880 resynchroEngaged = 1;
881 // get acquisition time in fine time ticks
882 acquisitionTime = get_acquisition_time( timePtr );
878
883
879 // compute center time
884 // compute center time
880 centerTime = acquisitionTime + 2731; // (2048. / 24576. / 2.) * 65536. = 2730.667;
885 centerTime = acquisitionTime + 2731; // (2048. / 24576. / 2.) * 65536. = 2730.667;
881 previousTick = centerTime - (centerTime & 0xffff);
886 previousTick = centerTime - (centerTime & 0xffff);
882 nextTick = previousTick + 65536;
887 nextTick = previousTick + 65536;
883
888
884 deltaPreviousTick = centerTime - previousTick;
889 deltaPreviousTick = centerTime - previousTick;
885 deltaNextTick = nextTick - centerTime;
890 deltaNextTick = nextTick - centerTime;
891
892 deltaPrevious_ms = ((double) deltaPreviousTick) / 65536. * 1000.;
893 deltaNext_ms = ((double) deltaNextTick) / 65536. * 1000.;
894
895 PRINTF2("delta previous = %f ms, delta next = %f ms\n", deltaPrevious_ms, deltaNext_ms);
896 PRINTF2("delta previous = %llu fine time ticks, delta next = %llu fine time ticks\n", deltaPreviousTick, deltaNextTick);
886
897
887 deltaPrevious_ms = ((double) deltaPreviousTick) / 65536. * 1000.;
898 // which tick is the closest?
888 deltaNext_ms = ((double) deltaNextTick) / 65536. * 1000.;
899 if (deltaPreviousTick > deltaNextTick)
889
900 {
890 PRINTF2("delta previous = %f ms, delta next = %f ms\n", deltaPrevious_ms, deltaNext_ms);
901 // the snapshot center is just before the second => increase delta_snapshot
891 PRINTF2("delta previous = %llu fine time ticks, delta next = %llu fine time ticks\n", deltaPreviousTick, deltaNextTick);
902 correctionInF2 = + (deltaNext_ms * 256. / 1000. );
903 }
904 else
905 {
906 // the snapshot center is just after the second => decrease delta_snapshot
907 correctionInF2 = - (deltaPrevious_ms * 256. / 1000. );
908 }
892
909
893 // which tick is the closest
910 if (correctionInF2 >=0 )
894 if (deltaPreviousTick > deltaNextTick)
911 {
895 {
912 deltaTickInF2 = floor( correctionInF2 );
896 // the snapshot center is just before the second => increase delta_snapshot
913 }
897 deltaTickInF2 = ceil( (deltaNext_ms * 256. / 1000.) );
914 else
898 waveform_picker_regs->delta_snapshot = waveform_picker_regs->delta_snapshot + 1 * deltaTickInF2;
915 {
899 PRINTF2("correction of = + %u, delta_snapshot = %d\n", deltaTickInF2, waveform_picker_regs->delta_snapshot);
916 deltaTickInF2 = ceil( correctionInF2 );
917 }
918 waveform_picker_regs->delta_snapshot = waveform_picker_regs->delta_snapshot + deltaTickInF2;
919 PRINTF2("Correction of = %d, delta_snapshot = %d\n\n", deltaTickInF2, waveform_picker_regs->delta_snapshot);
900 }
920 }
901 else
921 else
902 {
922 {
903 // the snapshot center is just after the second => decrease delat_snapshot
923 PRINTF1("No resynchro, delta_snapshot = %d\n\n", waveform_picker_regs->delta_snapshot);
904 deltaTickInF2 = ceil( (deltaPrevious_ms * 256. / 1000.) );
924 resynchroEngaged = 0;
905 waveform_picker_regs->delta_snapshot = waveform_picker_regs->delta_snapshot - 1 * deltaTickInF2;
906 PRINTF2("correction of = - %u, delta_snapshot = %d\n", deltaTickInF2, waveform_picker_regs->delta_snapshot);
907 }
925 }
908 }
926 }
909
927
910 //**************
928 //**************
911 // wfp registers
929 // wfp registers
912 void reset_wfp_burst_enable( void )
930 void reset_wfp_burst_enable( void )
913 {
931 {
914 /** This function resets the waveform picker burst_enable register.
932 /** This function resets the waveform picker burst_enable register.
915 *
933 *
916 * The burst bits [f2 f1 f0] and the enable bits [f3 f2 f1 f0] are set to 0.
934 * The burst bits [f2 f1 f0] and the enable bits [f3 f2 f1 f0] are set to 0.
917 *
935 *
918 */
936 */
919
937
920 // [1000 000] burst f2, f1, f0 enable f3, f2, f1, f0
938 // [1000 000] burst f2, f1, f0 enable f3, f2, f1, f0
921 waveform_picker_regs->run_burst_enable = waveform_picker_regs->run_burst_enable & 0x80;
939 waveform_picker_regs->run_burst_enable = waveform_picker_regs->run_burst_enable & 0x80;
922 }
940 }
923
941
924 void reset_wfp_status( void )
942 void reset_wfp_status( void )
925 {
943 {
926 /** This function resets the waveform picker status register.
944 /** This function resets the waveform picker status register.
927 *
945 *
928 * All status bits are set to 0 [new_err full_err full].
946 * All status bits are set to 0 [new_err full_err full].
929 *
947 *
930 */
948 */
931
949
932 waveform_picker_regs->status = 0xffff;
950 waveform_picker_regs->status = 0xffff;
933 }
951 }
934
952
935 void reset_wfp_buffer_addresses( void )
953 void reset_wfp_buffer_addresses( void )
936 {
954 {
937 // F0
955 // F0
938 waveform_picker_regs->addr_data_f0_0 = current_ring_node_f0->previous->buffer_address; // 0x08
956 waveform_picker_regs->addr_data_f0_0 = current_ring_node_f0->previous->buffer_address; // 0x08
939 waveform_picker_regs->addr_data_f0_1 = current_ring_node_f0->buffer_address; // 0x0c
957 waveform_picker_regs->addr_data_f0_1 = current_ring_node_f0->buffer_address; // 0x0c
940 // F1
958 // F1
941 waveform_picker_regs->addr_data_f1_0 = current_ring_node_f1->previous->buffer_address; // 0x10
959 waveform_picker_regs->addr_data_f1_0 = current_ring_node_f1->previous->buffer_address; // 0x10
942 waveform_picker_regs->addr_data_f1_1 = current_ring_node_f1->buffer_address; // 0x14
960 waveform_picker_regs->addr_data_f1_1 = current_ring_node_f1->buffer_address; // 0x14
943 // F2
961 // F2
944 waveform_picker_regs->addr_data_f2_0 = current_ring_node_f2->previous->buffer_address; // 0x18
962 waveform_picker_regs->addr_data_f2_0 = current_ring_node_f2->previous->buffer_address; // 0x18
945 waveform_picker_regs->addr_data_f2_1 = current_ring_node_f2->buffer_address; // 0x1c
963 waveform_picker_regs->addr_data_f2_1 = current_ring_node_f2->buffer_address; // 0x1c
946 // F3
964 // F3
947 waveform_picker_regs->addr_data_f3_0 = current_ring_node_f3->previous->buffer_address; // 0x20
965 waveform_picker_regs->addr_data_f3_0 = current_ring_node_f3->previous->buffer_address; // 0x20
948 waveform_picker_regs->addr_data_f3_1 = current_ring_node_f3->buffer_address; // 0x24
966 waveform_picker_regs->addr_data_f3_1 = current_ring_node_f3->buffer_address; // 0x24
949 }
967 }
950
968
951 void reset_waveform_picker_regs( void )
969 void reset_waveform_picker_regs( void )
952 {
970 {
953 /** This function resets the waveform picker module registers.
971 /** This function resets the waveform picker module registers.
954 *
972 *
955 * The registers affected by this function are located at the following offset addresses:
973 * The registers affected by this function are located at the following offset addresses:
956 * - 0x00 data_shaping
974 * - 0x00 data_shaping
957 * - 0x04 run_burst_enable
975 * - 0x04 run_burst_enable
958 * - 0x08 addr_data_f0
976 * - 0x08 addr_data_f0
959 * - 0x0C addr_data_f1
977 * - 0x0C addr_data_f1
960 * - 0x10 addr_data_f2
978 * - 0x10 addr_data_f2
961 * - 0x14 addr_data_f3
979 * - 0x14 addr_data_f3
962 * - 0x18 status
980 * - 0x18 status
963 * - 0x1C delta_snapshot
981 * - 0x1C delta_snapshot
964 * - 0x20 delta_f0
982 * - 0x20 delta_f0
965 * - 0x24 delta_f0_2
983 * - 0x24 delta_f0_2
966 * - 0x28 delta_f1
984 * - 0x28 delta_f1
967 * - 0x2c delta_f2
985 * - 0x2c delta_f2
968 * - 0x30 nb_data_by_buffer
986 * - 0x30 nb_data_by_buffer
969 * - 0x34 nb_snapshot_param
987 * - 0x34 nb_snapshot_param
970 * - 0x38 start_date
988 * - 0x38 start_date
971 * - 0x3c nb_word_in_buffer
989 * - 0x3c nb_word_in_buffer
972 *
990 *
973 */
991 */
974
992
975 set_wfp_data_shaping(); // 0x00 *** R1 R0 SP1 SP0 BW
993 set_wfp_data_shaping(); // 0x00 *** R1 R0 SP1 SP0 BW
976
994
977 reset_wfp_burst_enable(); // 0x04 *** [run *** burst f2, f1, f0 *** enable f3, f2, f1, f0 ]
995 reset_wfp_burst_enable(); // 0x04 *** [run *** burst f2, f1, f0 *** enable f3, f2, f1, f0 ]
978
996
979 reset_wfp_buffer_addresses();
997 reset_wfp_buffer_addresses();
980
998
981 reset_wfp_status(); // 0x18
999 reset_wfp_status(); // 0x18
982
1000
983 set_wfp_delta_snapshot(); // 0x1c *** 300 s => 0x12bff
1001 set_wfp_delta_snapshot(); // 0x1c *** 300 s => 0x12bff
984
1002
985 set_wfp_delta_f0_f0_2(); // 0x20, 0x24
1003 set_wfp_delta_f0_f0_2(); // 0x20, 0x24
986
1004
987 set_wfp_delta_f1(); // 0x28
1005 set_wfp_delta_f1(); // 0x28
988
1006
989 set_wfp_delta_f2(); // 0x2c
1007 set_wfp_delta_f2(); // 0x2c
990
1008
991 DEBUG_PRINTF1("delta_snapshot %x\n", waveform_picker_regs->delta_snapshot)
1009 DEBUG_PRINTF1("delta_snapshot %x\n", waveform_picker_regs->delta_snapshot)
992 DEBUG_PRINTF1("delta_f0 %x\n", waveform_picker_regs->delta_f0)
1010 DEBUG_PRINTF1("delta_f0 %x\n", waveform_picker_regs->delta_f0)
993 DEBUG_PRINTF1("delta_f0_2 %x\n", waveform_picker_regs->delta_f0_2)
1011 DEBUG_PRINTF1("delta_f0_2 %x\n", waveform_picker_regs->delta_f0_2)
994 DEBUG_PRINTF1("delta_f1 %x\n", waveform_picker_regs->delta_f1)
1012 DEBUG_PRINTF1("delta_f1 %x\n", waveform_picker_regs->delta_f1)
995 DEBUG_PRINTF1("delta_f2 %x\n", waveform_picker_regs->delta_f2)
1013 DEBUG_PRINTF1("delta_f2 %x\n", waveform_picker_regs->delta_f2)
996 // 2688 = 8 * 336
1014 // 2688 = 8 * 336
997 waveform_picker_regs->nb_data_by_buffer = 0xa7f; // 0x30 *** 2688 - 1 => nb samples -1
1015 waveform_picker_regs->nb_data_by_buffer = 0xa7f; // 0x30 *** 2688 - 1 => nb samples -1
998 waveform_picker_regs->snapshot_param = 0xa80; // 0x34 *** 2688 => nb samples
1016 waveform_picker_regs->snapshot_param = 0xa80; // 0x34 *** 2688 => nb samples
999 waveform_picker_regs->start_date = 0x7fffffff; // 0x38
1017 waveform_picker_regs->start_date = 0x7fffffff; // 0x38
1000 //
1018 //
1001 // coarse time and fine time registers are not initialized, they are volatile
1019 // coarse time and fine time registers are not initialized, they are volatile
1002 //
1020 //
1003 waveform_picker_regs->buffer_length = 0x1f8;// buffer length in burst = 3 * 2688 / 16 = 504 = 0x1f8
1021 waveform_picker_regs->buffer_length = 0x1f8;// buffer length in burst = 3 * 2688 / 16 = 504 = 0x1f8
1004 }
1022 }
1005
1023
1006 void set_wfp_data_shaping( void )
1024 void set_wfp_data_shaping( void )
1007 {
1025 {
1008 /** This function sets the data_shaping register of the waveform picker module.
1026 /** This function sets the data_shaping register of the waveform picker module.
1009 *
1027 *
1010 * The value is read from one field of the parameter_dump_packet structure:\n
1028 * The value is read from one field of the parameter_dump_packet structure:\n
1011 * bw_sp0_sp1_r0_r1
1029 * bw_sp0_sp1_r0_r1
1012 *
1030 *
1013 */
1031 */
1014
1032
1015 unsigned char data_shaping;
1033 unsigned char data_shaping;
1016
1034
1017 // get the parameters for the data shaping [BW SP0 SP1 R0 R1] in sy_lfr_common1 and configure the register
1035 // get the parameters for the data shaping [BW SP0 SP1 R0 R1] in sy_lfr_common1 and configure the register
1018 // waveform picker : [R1 R0 SP1 SP0 BW]
1036 // waveform picker : [R1 R0 SP1 SP0 BW]
1019
1037
1020 data_shaping = parameter_dump_packet.sy_lfr_common_parameters;
1038 data_shaping = parameter_dump_packet.sy_lfr_common_parameters;
1021
1039
1022 waveform_picker_regs->data_shaping =
1040 waveform_picker_regs->data_shaping =
1023 ( (data_shaping & 0x20) >> 5 ) // BW
1041 ( (data_shaping & 0x20) >> 5 ) // BW
1024 + ( (data_shaping & 0x10) >> 3 ) // SP0
1042 + ( (data_shaping & 0x10) >> 3 ) // SP0
1025 + ( (data_shaping & 0x08) >> 1 ) // SP1
1043 + ( (data_shaping & 0x08) >> 1 ) // SP1
1026 + ( (data_shaping & 0x04) << 1 ) // R0
1044 + ( (data_shaping & 0x04) << 1 ) // R0
1027 + ( (data_shaping & 0x02) << 3 ) // R1
1045 + ( (data_shaping & 0x02) << 3 ) // R1
1028 + ( (data_shaping & 0x01) << 5 ); // R2
1046 + ( (data_shaping & 0x01) << 5 ); // R2
1029 }
1047 }
1030
1048
1031 void set_wfp_burst_enable_register( unsigned char mode )
1049 void set_wfp_burst_enable_register( unsigned char mode )
1032 {
1050 {
1033 /** This function sets the waveform picker burst_enable register depending on the mode.
1051 /** This function sets the waveform picker burst_enable register depending on the mode.
1034 *
1052 *
1035 * @param mode is the LFR mode to launch.
1053 * @param mode is the LFR mode to launch.
1036 *
1054 *
1037 * The burst bits shall be before the enable bits.
1055 * The burst bits shall be before the enable bits.
1038 *
1056 *
1039 */
1057 */
1040
1058
1041 // [0000 0000] burst f2, f1, f0 enable f3 f2 f1 f0
1059 // [0000 0000] burst f2, f1, f0 enable f3 f2 f1 f0
1042 // the burst bits shall be set first, before the enable bits
1060 // the burst bits shall be set first, before the enable bits
1043 switch(mode) {
1061 switch(mode) {
1044 case LFR_MODE_NORMAL:
1062 case LFR_MODE_NORMAL:
1045 case LFR_MODE_SBM1:
1063 case LFR_MODE_SBM1:
1046 case LFR_MODE_SBM2:
1064 case LFR_MODE_SBM2:
1047 waveform_picker_regs->run_burst_enable = 0x60; // [0110 0000] enable f2 and f1 burst
1065 waveform_picker_regs->run_burst_enable = 0x60; // [0110 0000] enable f2 and f1 burst
1048 waveform_picker_regs->run_burst_enable = waveform_picker_regs->run_burst_enable | 0x0f; // [1111] enable f3 f2 f1 f0
1066 waveform_picker_regs->run_burst_enable = waveform_picker_regs->run_burst_enable | 0x0f; // [1111] enable f3 f2 f1 f0
1049 break;
1067 break;
1050 case LFR_MODE_BURST:
1068 case LFR_MODE_BURST:
1051 waveform_picker_regs->run_burst_enable = 0x40; // [0100 0000] f2 burst enabled
1069 waveform_picker_regs->run_burst_enable = 0x40; // [0100 0000] f2 burst enabled
1052 waveform_picker_regs->run_burst_enable = waveform_picker_regs->run_burst_enable | 0x0c; // [1100] enable f3 and f2
1070 waveform_picker_regs->run_burst_enable = waveform_picker_regs->run_burst_enable | 0x0c; // [1100] enable f3 and f2
1053 break;
1071 break;
1054 default:
1072 default:
1055 waveform_picker_regs->run_burst_enable = 0x00; // [0000 0000] no burst enabled, no waveform enabled
1073 waveform_picker_regs->run_burst_enable = 0x00; // [0000 0000] no burst enabled, no waveform enabled
1056 break;
1074 break;
1057 }
1075 }
1058 }
1076 }
1059
1077
1060 void set_wfp_delta_snapshot( void )
1078 void set_wfp_delta_snapshot( void )
1061 {
1079 {
1062 /** This function sets the delta_snapshot register of the waveform picker module.
1080 /** This function sets the delta_snapshot register of the waveform picker module.
1063 *
1081 *
1064 * The value is read from two (unsigned char) of the parameter_dump_packet structure:
1082 * The value is read from two (unsigned char) of the parameter_dump_packet structure:
1065 * - sy_lfr_n_swf_p[0]
1083 * - sy_lfr_n_swf_p[0]
1066 * - sy_lfr_n_swf_p[1]
1084 * - sy_lfr_n_swf_p[1]
1067 *
1085 *
1068 */
1086 */
1069
1087
1070 unsigned int delta_snapshot;
1088 unsigned int delta_snapshot;
1071 unsigned int delta_snapshot_in_T2;
1089 unsigned int delta_snapshot_in_T2;
1072
1090
1073 delta_snapshot = parameter_dump_packet.sy_lfr_n_swf_p[0]*256
1091 delta_snapshot = parameter_dump_packet.sy_lfr_n_swf_p[0]*256
1074 + parameter_dump_packet.sy_lfr_n_swf_p[1];
1092 + parameter_dump_packet.sy_lfr_n_swf_p[1];
1075
1093
1076 delta_snapshot_in_T2 = delta_snapshot * 256;
1094 delta_snapshot_in_T2 = delta_snapshot * 256;
1077 waveform_picker_regs->delta_snapshot = delta_snapshot_in_T2 - 1; // max 4 bytes
1095 waveform_picker_regs->delta_snapshot = delta_snapshot_in_T2 - 1; // max 4 bytes
1078 }
1096 }
1079
1097
1080 void set_wfp_delta_f0_f0_2( void )
1098 void set_wfp_delta_f0_f0_2( void )
1081 {
1099 {
1082 unsigned int delta_snapshot;
1100 unsigned int delta_snapshot;
1083 unsigned int nb_samples_per_snapshot;
1101 unsigned int nb_samples_per_snapshot;
1084 float delta_f0_in_float;
1102 float delta_f0_in_float;
1085
1103
1086 delta_snapshot = waveform_picker_regs->delta_snapshot;
1104 delta_snapshot = waveform_picker_regs->delta_snapshot;
1087 nb_samples_per_snapshot = parameter_dump_packet.sy_lfr_n_swf_l[0] * 256 + parameter_dump_packet.sy_lfr_n_swf_l[1];
1105 nb_samples_per_snapshot = parameter_dump_packet.sy_lfr_n_swf_l[0] * 256 + parameter_dump_packet.sy_lfr_n_swf_l[1];
1088 delta_f0_in_float =nb_samples_per_snapshot / 2. * ( 1. / 256. - 1. / 24576.) * 256.;
1106 delta_f0_in_float =nb_samples_per_snapshot / 2. * ( 1. / 256. - 1. / 24576.) * 256.;
1089
1107
1090 waveform_picker_regs->delta_f0 = delta_snapshot - floor( delta_f0_in_float );
1108 waveform_picker_regs->delta_f0 = delta_snapshot - floor( delta_f0_in_float );
1091 waveform_picker_regs->delta_f0_2 = 0x30; // 48 = 11 0000, max 7 bits
1109 waveform_picker_regs->delta_f0_2 = 0x30; // 48 = 11 0000, max 7 bits
1092 }
1110 }
1093
1111
1094 void set_wfp_delta_f1( void )
1112 void set_wfp_delta_f1( void )
1095 {
1113 {
1096 unsigned int delta_snapshot;
1114 unsigned int delta_snapshot;
1097 unsigned int nb_samples_per_snapshot;
1115 unsigned int nb_samples_per_snapshot;
1098 float delta_f1_in_float;
1116 float delta_f1_in_float;
1099
1117
1100 delta_snapshot = waveform_picker_regs->delta_snapshot;
1118 delta_snapshot = waveform_picker_regs->delta_snapshot;
1101 nb_samples_per_snapshot = parameter_dump_packet.sy_lfr_n_swf_l[0] * 256 + parameter_dump_packet.sy_lfr_n_swf_l[1];
1119 nb_samples_per_snapshot = parameter_dump_packet.sy_lfr_n_swf_l[0] * 256 + parameter_dump_packet.sy_lfr_n_swf_l[1];
1102 delta_f1_in_float = nb_samples_per_snapshot / 2. * ( 1. / 256. - 1. / 4096.) * 256.;
1120 delta_f1_in_float = nb_samples_per_snapshot / 2. * ( 1. / 256. - 1. / 4096.) * 256.;
1103
1121
1104 waveform_picker_regs->delta_f1 = delta_snapshot - floor( delta_f1_in_float );
1122 waveform_picker_regs->delta_f1 = delta_snapshot - floor( delta_f1_in_float );
1105 }
1123 }
1106
1124
1107 void set_wfp_delta_f2()
1125 void set_wfp_delta_f2()
1108 {
1126 {
1109 unsigned int delta_snapshot;
1127 unsigned int delta_snapshot;
1110 unsigned int nb_samples_per_snapshot;
1128 unsigned int nb_samples_per_snapshot;
1111
1129
1112 delta_snapshot = waveform_picker_regs->delta_snapshot;
1130 delta_snapshot = waveform_picker_regs->delta_snapshot;
1113 nb_samples_per_snapshot = parameter_dump_packet.sy_lfr_n_swf_l[0] * 256 + parameter_dump_packet.sy_lfr_n_swf_l[1];
1131 nb_samples_per_snapshot = parameter_dump_packet.sy_lfr_n_swf_l[0] * 256 + parameter_dump_packet.sy_lfr_n_swf_l[1];
1114
1132
1115 waveform_picker_regs->delta_f2 = delta_snapshot - nb_samples_per_snapshot / 2;
1133 waveform_picker_regs->delta_f2 = delta_snapshot - nb_samples_per_snapshot / 2;
1116 }
1134 }
1117
1135
1118 //*****************
1136 //*****************
1119 // local parameters
1137 // local parameters
1120
1138
1121 void increment_seq_counter_source_id( unsigned char *packet_sequence_control, unsigned int sid )
1139 void increment_seq_counter_source_id( unsigned char *packet_sequence_control, unsigned int sid )
1122 {
1140 {
1123 /** This function increments the parameter "sequence_cnt" depending on the sid passed in argument.
1141 /** This function increments the parameter "sequence_cnt" depending on the sid passed in argument.
1124 *
1142 *
1125 * @param packet_sequence_control is a pointer toward the parameter sequence_cnt to update.
1143 * @param packet_sequence_control is a pointer toward the parameter sequence_cnt to update.
1126 * @param sid is the source identifier of the packet being updated.
1144 * @param sid is the source identifier of the packet being updated.
1127 *
1145 *
1128 * REQ-LFR-SRS-5240 / SSS-CP-FS-590
1146 * REQ-LFR-SRS-5240 / SSS-CP-FS-590
1129 * The sequence counters shall wrap around from 2^14 to zero.
1147 * The sequence counters shall wrap around from 2^14 to zero.
1130 * The sequence counter shall start at zero at startup.
1148 * The sequence counter shall start at zero at startup.
1131 *
1149 *
1132 * REQ-LFR-SRS-5239 / SSS-CP-FS-580
1150 * REQ-LFR-SRS-5239 / SSS-CP-FS-580
1133 * All TM_LFR_SCIENCE_ packets are sent to ground, i.e. destination id = 0
1151 * All TM_LFR_SCIENCE_ packets are sent to ground, i.e. destination id = 0
1134 *
1152 *
1135 */
1153 */
1136
1154
1137 unsigned short *sequence_cnt;
1155 unsigned short *sequence_cnt;
1138 unsigned short segmentation_grouping_flag;
1156 unsigned short segmentation_grouping_flag;
1139 unsigned short new_packet_sequence_control;
1157 unsigned short new_packet_sequence_control;
1140 rtems_mode initial_mode_set;
1158 rtems_mode initial_mode_set;
1141 rtems_mode current_mode_set;
1159 rtems_mode current_mode_set;
1142 rtems_status_code status;
1160 rtems_status_code status;
1143
1161
1144 //******************************************
1162 //******************************************
1145 // CHANGE THE MODE OF THE CALLING RTEMS TASK
1163 // CHANGE THE MODE OF THE CALLING RTEMS TASK
1146 status = rtems_task_mode( RTEMS_NO_PREEMPT, RTEMS_PREEMPT_MASK, &initial_mode_set );
1164 status = rtems_task_mode( RTEMS_NO_PREEMPT, RTEMS_PREEMPT_MASK, &initial_mode_set );
1147
1165
1148 if ( (sid == SID_NORM_SWF_F0) || (sid == SID_NORM_SWF_F1) || (sid == SID_NORM_SWF_F2)
1166 if ( (sid == SID_NORM_SWF_F0) || (sid == SID_NORM_SWF_F1) || (sid == SID_NORM_SWF_F2)
1149 || (sid == SID_NORM_CWF_F3) || (sid == SID_NORM_CWF_LONG_F3)
1167 || (sid == SID_NORM_CWF_F3) || (sid == SID_NORM_CWF_LONG_F3)
1150 || (sid == SID_BURST_CWF_F2)
1168 || (sid == SID_BURST_CWF_F2)
1151 || (sid == SID_NORM_ASM_F0) || (sid == SID_NORM_ASM_F1) || (sid == SID_NORM_ASM_F2)
1169 || (sid == SID_NORM_ASM_F0) || (sid == SID_NORM_ASM_F1) || (sid == SID_NORM_ASM_F2)
1152 || (sid == SID_NORM_BP1_F0) || (sid == SID_NORM_BP1_F1) || (sid == SID_NORM_BP1_F2)
1170 || (sid == SID_NORM_BP1_F0) || (sid == SID_NORM_BP1_F1) || (sid == SID_NORM_BP1_F2)
1153 || (sid == SID_NORM_BP2_F0) || (sid == SID_NORM_BP2_F1) || (sid == SID_NORM_BP2_F2)
1171 || (sid == SID_NORM_BP2_F0) || (sid == SID_NORM_BP2_F1) || (sid == SID_NORM_BP2_F2)
1154 || (sid == SID_BURST_BP1_F0) || (sid == SID_BURST_BP2_F0)
1172 || (sid == SID_BURST_BP1_F0) || (sid == SID_BURST_BP2_F0)
1155 || (sid == SID_BURST_BP1_F1) || (sid == SID_BURST_BP2_F1) )
1173 || (sid == SID_BURST_BP1_F1) || (sid == SID_BURST_BP2_F1) )
1156 {
1174 {
1157 sequence_cnt = (unsigned short *) &sequenceCounters_SCIENCE_NORMAL_BURST;
1175 sequence_cnt = (unsigned short *) &sequenceCounters_SCIENCE_NORMAL_BURST;
1158 }
1176 }
1159 else if ( (sid ==SID_SBM1_CWF_F1) || (sid ==SID_SBM2_CWF_F2)
1177 else if ( (sid ==SID_SBM1_CWF_F1) || (sid ==SID_SBM2_CWF_F2)
1160 || (sid == SID_SBM1_BP1_F0) || (sid == SID_SBM1_BP2_F0)
1178 || (sid == SID_SBM1_BP1_F0) || (sid == SID_SBM1_BP2_F0)
1161 || (sid == SID_SBM2_BP1_F0) || (sid == SID_SBM2_BP2_F0)
1179 || (sid == SID_SBM2_BP1_F0) || (sid == SID_SBM2_BP2_F0)
1162 || (sid == SID_SBM2_BP1_F1) || (sid == SID_SBM2_BP2_F1) )
1180 || (sid == SID_SBM2_BP1_F1) || (sid == SID_SBM2_BP2_F1) )
1163 {
1181 {
1164 sequence_cnt = (unsigned short *) &sequenceCounters_SCIENCE_SBM1_SBM2;
1182 sequence_cnt = (unsigned short *) &sequenceCounters_SCIENCE_SBM1_SBM2;
1165 }
1183 }
1166 else
1184 else
1167 {
1185 {
1168 sequence_cnt = (unsigned short *) NULL;
1186 sequence_cnt = (unsigned short *) NULL;
1169 PRINTF1("in increment_seq_counter_source_id *** ERR apid_destid %d not known\n", sid)
1187 PRINTF1("in increment_seq_counter_source_id *** ERR apid_destid %d not known\n", sid)
1170 }
1188 }
1171
1189
1172 if (sequence_cnt != NULL)
1190 if (sequence_cnt != NULL)
1173 {
1191 {
1174 segmentation_grouping_flag = TM_PACKET_SEQ_CTRL_STANDALONE << 8;
1192 segmentation_grouping_flag = TM_PACKET_SEQ_CTRL_STANDALONE << 8;
1175 *sequence_cnt = (*sequence_cnt) & 0x3fff;
1193 *sequence_cnt = (*sequence_cnt) & 0x3fff;
1176
1194
1177 new_packet_sequence_control = segmentation_grouping_flag | (*sequence_cnt) ;
1195 new_packet_sequence_control = segmentation_grouping_flag | (*sequence_cnt) ;
1178
1196
1179 packet_sequence_control[0] = (unsigned char) (new_packet_sequence_control >> 8);
1197 packet_sequence_control[0] = (unsigned char) (new_packet_sequence_control >> 8);
1180 packet_sequence_control[1] = (unsigned char) (new_packet_sequence_control );
1198 packet_sequence_control[1] = (unsigned char) (new_packet_sequence_control );
1181
1199
1182 // increment the sequence counter
1200 // increment the sequence counter
1183 if ( *sequence_cnt < SEQ_CNT_MAX)
1201 if ( *sequence_cnt < SEQ_CNT_MAX)
1184 {
1202 {
1185 *sequence_cnt = *sequence_cnt + 1;
1203 *sequence_cnt = *sequence_cnt + 1;
1186 }
1204 }
1187 else
1205 else
1188 {
1206 {
1189 *sequence_cnt = 0;
1207 *sequence_cnt = 0;
1190 }
1208 }
1191 }
1209 }
1192
1210
1193 //*************************************
1211 //*************************************
1194 // RESTORE THE MODE OF THE CALLING TASK
1212 // RESTORE THE MODE OF THE CALLING TASK
1195 status = rtems_task_mode( initial_mode_set, RTEMS_PREEMPT_MASK, &current_mode_set );
1213 status = rtems_task_mode( initial_mode_set, RTEMS_PREEMPT_MASK, &current_mode_set );
1196 }
1214 }
General Comments 0
You need to be logged in to leave comments. Login now