OB.DAAC Logo
NASA Logo
Ocean Color Science Software

ocssw V2022
GEO_check_ea_headers.c
Go to the documentation of this file.
1 #include <stdio.h>
2 #include "smfio.h"
3 #include "GEO_geo.h"
4 #include "GEO_earth.h"
5 #include "GEO_product.h"
6 #include "PGS_EPH.h"
7 #include "PGS_SMF.h"
8 #include "PGS_TD.h"
9 #include "PGS_MODIS_35251.h"
10 
11 #define TIMEPOS sizeof("2000-01-01")
12 
13 PGSt_SMF_status GEO_check_ea_headers(
14  PGSt_double in_time,
15  PGSt_scTagInfo *scTagInfo
16 )
17 /******************************************************************************
18 !C
19 
20 !Description:
21  Determines whether or not the appropriate ephemeris and attitude files
22  have been staged to cover a specified time. Note: for the purpose of
23  this routine, a file is treated as covering the entire two hour (or
24  for PM1EPH, 24 hour) time period it was intended to cover, regardless
25  of any data gaps that might reduce the actual coverage.
26 
27 !Input Parameters:
28  in_time The time being queried (TAI seconds)
29  scTagInfo Information about the spacecraft whose headers are needed.
30 
31 !Output Parameters:
32  scTagInfo A structure containing information about the spacecraft.
33 
34 Return Values:
35  MODIS_E_BAD_INPUT_ARG If scTagInfo is null
36  MODIS_E_GEO If any subroutine failed.
37  MODIS_N_GEO_EXCESS_FILES If too many files were staged.
38  MODIS_E_GEO_MISSING_INPUTS ephemeris/attitude files weren't staged
39  PGS_S_SUCCESS Otherwise
40 
41 Externally Defined:
42  MAX_EA_FILES "GEO_product.h"
43  MODIS_E_BAD_INPUT_ARG "PGS_MODIS_35251.h"
44  MODIS_E_GEO "PGS_MODIS_35251.h"
45  MODIS_N_GEO_EXCESS_FILES "PGS_MODIS_35251.h"
46  MODIS_E_GEO_MISSING_INPUTS "PGS_MODIS_35251.h"
47  PGS_S_SUCCESS "PGS_SMF.h"
48  PGSd_EOS_AM "PGS_TD.h"
49  PGSd_EOS_AM1 "PGS_TD.h"
50  PGSd_EOS_PM "PGS_TD.h"
51  PGSe_TAG_SEARCH "PGS_TD.h"
52  TIMECODEASIZE "smfio.h"
53 
54 Called by:
55  GEO_interp_ephemeris_attitude()
56 
57 Routines Called:
58  PGS_EPH_getAttitHeaders "PGS_EPH.h"
59  PGS_EPH_getEphemHeaders "PGS_EPH.h"
60  PGS_TD_TAItoUTC "PGS_TD.h"
61  PGS_TD_UTCtoTAI "PGS_TD.h"
62 
63 !Revision History:
64  $Log: GEO_check_ea_headers.c,v $
65  Revision 6.3 2010/05/27 21:02:59 kuyper
66  Changed MAX_EA_FILES to come from a single header file.
67 
68  Revision 6.2 2010/04/09 20:37:32 kuyper
69  Removed parameter, corrected places where it was used.
70 
71  Revision 6.1 2010/03/31 19:58:09 kuyper
72  Helped resolve Bug 2473 by changing scTagInfo into an output argument.
73 
74  James Kuyper james.kuyper@sigmaspace.com
75 
76  Revision 5.1 2008/12/16 18:06:35 kuyper
77  Increased number of ephemeris and attitude files allowed, to allow use of
78  the 5-minute files used in Near Real Time production.
79 
80  Revision 4.4 2003/11/05 16:24:58 kuyper
81  Initialize header_array to NULL before retrieving headers.
82 
83  Revision 4.3 2003/06/24 18:36:37 vlin
84  Changed to match new interface for PGS_EPH_getEphemHeaders and
85  PGS_EPH_getAttitHeaders in SDPTK V5.2.9
86 
87  Revision 4.2 2003/05/15 16:30:08 vlin
88  change EXCESS_FILES from _E_ to _N_
89 
90  Revision 4.1 2003/04/10 16:46:33 vlin
91  updated after code walkthrough
92 
93  Revision 4.0 2003/03/05 21:12:31 vlin
94  initial revision
95  vlin@saicmodis.com
96 
97 Requirements:
98 
99 !Team-unique Header:
100  This software is developed by the MODIS Science Data Support
101  Team for the National Aeronautics and Space Administration,
102  Goddard Space Flight Center, under contract NAS5-32373.
103 
104 !END
105 ******************************************************************************/
106 
107 {
108  static PGSt_integer ephem_files, attit_files;
109  static PGSt_hdrSummary ephem_summary[MAX_EA_FILES];
110  static PGSt_hdrSummary attit_summary[MAX_EA_FILES];
111  static int initialized = 0;
112  PGSt_integer file;
113  PGSt_hdrSummary *header_array=(PGSt_hdrSummary*)NULL;
114  PGSt_integer lendcheck;
115  char asciiUTC[TIMECODEASIZE];
116  PGSt_SMF_status status = PGS_S_SUCCESS;
117  int hour, noon_time, zero_time;
118  PGSt_double offset;
119  char msg[128];
120  char filefunc[] = __FILE__ ", GEO_check_ea_headers";
121 
122  if(scTagInfo == NULL)
123  {
124  modsmf(MODIS_E_BAD_INPUT_ARG, "scTagInfo is null", filefunc);
125  return MODIS_E_BAD_INPUT_ARG;
126  }
127 
128  if (initialized == 0)
129  {
130  if (PGS_EPH_getEphemHeaders(scTagInfo, &header_array, &ephem_files,
131  &lendcheck) != PGS_S_SUCCESS) {
132  modsmf(MODIS_E_GEO, "PGS_EPH_getEphemHeaders()", filefunc);
134  }
135 
136  if (ephem_files > MAX_EA_FILES) {
137  sprintf(msg, "%d ephemeris", ephem_files);
138  modsmf(MODIS_N_GEO_EXCESS_FILES, msg, filefunc);
140  }
141 
142  for (file = 0; file < ephem_files; file++) {
143  /* Round start times downward */
144  if (PGS_TD_TAItoUTC(header_array[file].startTAI93, asciiUTC) !=
145  PGS_S_SUCCESS) {
146  sprintf(msg, "PGS_TD_TAItoUTC(%.6f) at ephemeris start",
147  header_array[file].startTAI93);
148  modsmf(MODIS_E_GEO, msg, filefunc);
150  }
151 
152  hour = atoi(asciiUTC+TIMEPOS);
153  if (scTagInfo->spacecraftTag == PGSd_EOS_AM)
154  { /* Round down to nearest even hour */
155  sprintf(asciiUTC+TIMEPOS,"%02d:00:00.000000Z", hour);
156  if (hour%2) /* hour is odd */
157  offset = -3600.0;
158  else
159  offset = 0.0;
160  }
161  else { /* Aqua ephemeris files - round down to the nearest noon */
162  sprintf(asciiUTC+TIMEPOS,"12:00:00.000000Z");
163  if (hour < 12)
164  offset = -86400.0;
165  else
166  offset = 0.0;
167  }
168 
169  if (PGS_TD_UTCtoTAI(asciiUTC, &ephem_summary[file].startTAI93) !=
170  PGS_S_SUCCESS) {
171  sprintf(msg, "PGS_TD_UTCtoTAI(%s) at ephemeris start", asciiUTC);
172  modsmf(MODIS_E_GEO, msg, filefunc);
174  }
175 
176  ephem_summary[file].startTAI93 += offset;
177 
178  /* Round stop times upward. */
179  if (PGS_TD_TAItoUTC(header_array[file].stopTAI93, asciiUTC) !=
180  PGS_S_SUCCESS) {
181  sprintf(msg, "PGS_TD_TAItoUTC(%.6f) at ephemeris stop",
182  header_array[file].stopTAI93);
183  modsmf(MODIS_E_GEO, msg, filefunc);
185  }
186 
187  hour = atoi(asciiUTC+TIMEPOS);
188  noon_time = strcmp(asciiUTC+TIMEPOS, "12:00:00.000000Z");
189  zero_time = strcmp(asciiUTC+TIMEPOS+2, ":00:00.000000Z");
190 
191  if (scTagInfo->spacecraftTag == PGSd_EOS_AM1)
192  { /* Round upward to nearest even hour */
193  if (hour%2)
194  offset = 3600.0;
195  else if (zero_time == 0)
196  offset = 0.0;
197  else
198  offset = 7200.0;
199  sprintf(asciiUTC+TIMEPOS,"%02d:00:00.000000Z", hour);
200  }
201  else { /* Aqua ephemeris files - round upward to the nearest noon */
202  if (hour < 12 || noon_time == 0)
203  offset = 0.0;
204  else
205  offset = 86400.0;
206  sprintf(asciiUTC+TIMEPOS,"12:00:00.000000Z");
207  }
208 
209  if (PGS_TD_UTCtoTAI(asciiUTC, &ephem_summary[file].stopTAI93) !=
210  PGS_S_SUCCESS) {
211  sprintf(msg, "PGS_TD_UTCtoTAI(%s) at ephemeris stop", asciiUTC);
212  modsmf(MODIS_E_GEO, msg, filefunc);
214  }
215 
216  ephem_summary[file].stopTAI93 += offset;
217 
218  } /* End for */
219 
220  header_array = (PGSt_hdrSummary*)NULL;
221  if (PGS_EPH_getAttitHeaders(scTagInfo, &lendcheck, &header_array,
222  &attit_files) != PGS_S_SUCCESS) {
223  modsmf(MODIS_E_GEO, "PGS_EPH_getAttitHeaders()", filefunc);
225  }
226 
227  if (attit_files > MAX_EA_FILES) {
228  sprintf(msg, "%d attitude", attit_files);
229  modsmf(MODIS_N_GEO_EXCESS_FILES, "attitude", filefunc);
231  }
232 
233  for (file = 0; file < attit_files; file++) {
234  /* Round start times downward */
235  if (PGS_TD_TAItoUTC(header_array[file].startTAI93, asciiUTC) !=
236  PGS_S_SUCCESS) {
237  sprintf(msg, "PGS_TD_TAItoUTC(%.6f) at attitude start",
238  header_array[file].startTAI93);
239  modsmf(MODIS_E_GEO, msg, filefunc);
241  }
242 
243  hour = atoi(asciiUTC+TIMEPOS);
244  sprintf(asciiUTC+TIMEPOS,"%02d:00:00.000000Z", hour);
245 
246  if (hour%2) /* hour is odd */
247  offset = -3600.0;
248  else
249  offset = 0.0;
250 
251  if (PGS_TD_UTCtoTAI(asciiUTC, &attit_summary[file].startTAI93) !=
252  PGS_S_SUCCESS) {
253  sprintf(msg, "PGS_TD_UTCtoTAI(%s) at attitude start", asciiUTC);
254  modsmf(MODIS_E_GEO, msg, filefunc);
256  }
257 
258  attit_summary[file].startTAI93 += offset;
259 
260  /* Round stop times upward. */
261  if (PGS_TD_TAItoUTC(header_array[file].stopTAI93, asciiUTC) !=
262  PGS_S_SUCCESS) {
263  sprintf(msg, "PGS_TD_TAItoUTC(%.6f) at attitude stop",
264  header_array[file].stopTAI93);
265  modsmf(MODIS_E_GEO, msg, filefunc);
267  }
268 
269  hour = atoi(asciiUTC+TIMEPOS);
270  noon_time = strcmp(asciiUTC+TIMEPOS, "12:00:00.000000Z");
271  zero_time = strcmp(asciiUTC+TIMEPOS+2, ":00:00.000000Z");
272 
273  /* Round upward to nearest even hour. */
274  if (hour%2)
275  offset = 3600.0;
276  else if (zero_time == 0)
277  offset = 0.0;
278  else
279  offset = 7200.0;
280  sprintf(asciiUTC+TIMEPOS, "%02d:00:00.000000Z", hour);
281 
282  if (PGS_TD_UTCtoTAI(asciiUTC, &attit_summary[file].stopTAI93) !=
283  PGS_S_SUCCESS) {
284  sprintf(msg, "PGS_TD_UTCtoTAI(%s) at attitude stop", asciiUTC);
285  modsmf(MODIS_E_GEO, msg, filefunc);
287  }
288 
289  attit_summary[file].stopTAI93 += offset;
290 
291  } /* End for */
292 
293  initialized = 1;
294  }
295 
296  if (ephem_files < 1 || attit_files < 1)
298 
299  for (file = 0; file < ephem_files; file++) {
300  if (ephem_summary[file].startTAI93 <= in_time &&
301  in_time <= ephem_summary[file].stopTAI93)
302  break;
303  }
304 
305  if (file > ephem_files - 1) { /* A needed ephemeris file was not staged. */
306  sprintf(msg, "%.6f from ephemeris files.", in_time);
307  modsmf(MODIS_E_GEO_MISSING_INPUTS, msg, filefunc);
309  }
310 
311  for (file = 0; file < attit_files; file++) {
312  if (attit_summary[file].startTAI93 <= in_time &&
313  in_time <= attit_summary[file].stopTAI93)
314  break;
315  }
316 
317  if (file > attit_files - 1) { /* A needed attitude file was not staged. */
318  sprintf(msg, "%.6f from attitude files.", in_time);
319  modsmf(MODIS_E_GEO_MISSING_INPUTS, msg, filefunc);
321  }
322 
323  return status;
324 }
#define TIMEPOS
#define MAX_EA_FILES
Definition: GEO_product.h:253
#define MODIS_N_GEO_EXCESS_FILES
int status
Definition: l1_czcs_hdf.c:32
#define NULL
Definition: decode_rs.h:63
#define MODIS_E_BAD_INPUT_ARG
#define TIMECODEASIZE
Definition: Metadata.c:59
#define MODIS_E_GEO
no change in intended resolving MODur00064 Corrected handling of bad ephemeris attitude resolving resolving GSFcd00179 Corrected handling of fill values for[Sensor|Solar][Zenith|Azimuth] resolving MODxl01751 Changed to validate LUT version against a value retrieved from the resolving MODxl02056 Changed to calculate Solar Diffuser angles without adjustment for estimated post launch changes in the MODIS orientation relative to incidentally resolving defects MODxl01766 Also resolves MODxl01947 Changed to ignore fill values in SCI_ABNORM and SCI_STATE rather than treating them as resolving MODxl01780 Changed to use spacecraft ancillary data to recognise when the mirror encoder data is being set by side A or side B and to change calculations accordingly This removes the need for seperate LUTs for Side A and Side B data it makes the new LUTs incompatible with older versions of the and vice versa Also resolves MODxl01685 A more robust GRing algorithm is being which will create a non default GRing anytime there s even a single geolocated pixel in a granule Removed obsolete messages from seed file
Definition: HISTORY.txt:413
#define MODIS_E_GEO_MISSING_INPUTS
PGSt_SMF_status GEO_check_ea_headers(PGSt_double in_time, PGSt_scTagInfo *scTagInfo)
l2prod offset
string msg
Definition: mapgen.py:227