output_downscaled_analog.c

Go to the documentation of this file.
00001 /* ***************************************************** */
00002 /* Read analog day data and write it for downscaled      */
00003 /* period.                                               */
00004 /* output_downscaled_analog.c                            */
00005 /* ***************************************************** */
00006 /* Author: Christian Page, CERFACS, Toulouse, France.    */
00007 /* ***************************************************** */
00012 /* LICENSE BEGIN
00013 
00014 Copyright Cerfacs (Christian Page) (2015)
00015 
00016 christian.page@cerfacs.fr
00017 
00018 This software is a computer program whose purpose is to downscale climate
00019 scenarios using a statistical methodology based on weather regimes.
00020 
00021 This software is governed by the CeCILL license under French law and
00022 abiding by the rules of distribution of free software. You can use, 
00023 modify and/ or redistribute the software under the terms of the CeCILL
00024 license as circulated by CEA, CNRS and INRIA at the following URL
00025 "http://www.cecill.info". 
00026 
00027 As a counterpart to the access to the source code and rights to copy,
00028 modify and redistribute granted by the license, users are provided only
00029 with a limited warranty and the software's author, the holder of the
00030 economic rights, and the successive licensors have only limited
00031 liability. 
00032 
00033 In this respect, the user's attention is drawn to the risks associated
00034 with loading, using, modifying and/or developing or reproducing the
00035 software by the user in light of its specific status of free software,
00036 that may mean that it is complicated to manipulate, and that also
00037 therefore means that it is reserved for developers and experienced
00038 professionals having in-depth computer knowledge. Users are therefore
00039 encouraged to load and test the software's suitability as regards their
00040 requirements in conditions enabling the security of their systems and/or 
00041 data to be ensured and, more generally, to use and operate it in the 
00042 same conditions as regards security. 
00043 
00044 The fact that you are presently reading this means that you have had
00045 knowledge of the CeCILL license and that you accept its terms.
00046 
00047 LICENSE END */
00048 
00049 
00050 
00051 
00052 
00053 
00054 
00055 #include <dsclim.h>
00056 
00058 int
00059 output_downscaled_analog(analog_day_struct analog_days, double *delta, int output_month_begin, char *output_path,
00060                          char *config, char *time_units, char *cal_type,
00061                          double deltat, int file_format, int file_compression, int file_compression_level,
00062                          int debug,
00063                          info_struct *info, var_struct *obs_var, period_struct *period,
00064                          double *time_ls, int ntime) {
00085   char **infile = NULL; /* Input filename */
00086   char *infile_alt = NULL; /* Input filename for optional altitudes */
00087   char **outfile = NULL; /* Output filename */
00088   char ***outfiles = NULL; /* Output filelist */
00089   int year1 = 0; /* First year of data input file */
00090   int year2 = 0; /* End year of data input file */
00091   double **buf = NULL; /* Temporary data buffer */
00092   double **bufsave = NULL; /* Temporary data buffer for averaging hourly data */
00093   double *buftmp = NULL; /* Temporary buffer for mean temperature */
00094   double *alt = NULL; /* Altitudes of observation points (optional) */
00095   double *pmsl = NULL; /* Standard Pressure of observation points (optional) */
00096   double *timeval = NULL; /* Temporary time information buffer */
00097   double *lat = NULL; /* Temporary latitude buffer */
00098   double *lon = NULL; /* Temporary longitude buffer */
00099   double *y = NULL; /* Temporary Y buffer */
00100   double *x = NULL; /* Temporary X buffer */
00101   char *cal_type_tmp = NULL; /* Input observations calendar type (udunits) */
00102   char *time_units_tmp = NULL; /* Input observations time units (udunits) */
00103   double ctimeval[1]; /* Dummy time info */
00104   int ntime_file; /* Number of times dimension */
00105   int ntime_obs; /* Number of times dimension in observation database */
00106   int nlon; /* Longitude dimension */
00107   int nlat; /* Latitude dimension */
00108   int *noutf = NULL; /* Number of files in filelist */
00109   int found = FALSE; /* Used to tag if we found a specific date */
00110   int *found_file = NULL; /* Used to tag if we found a specific filename in the filelist */
00111   int output_month_end; /* Ending month for observation database */
00112   time_vect_struct *time_s = NULL; /* Time structure for observation database */
00113 
00114   info_field_struct **info_tmp = NULL; /* Temporary field information structure */
00115   proj_struct *proj_tmp = NULL; /* Temporary field projection structure */
00116 
00117   int tmpi; /* Temporay integer value */
00118   double curtas; /* Current temperature value */
00119   double newcurtas; /* New current temperature value */
00120   char *format = NULL; /* Temporay format string */
00121 
00122   int varid_tas; /* Variable index ID */
00123   int varid_tasmax; /* Variable index ID */
00124   int varid_tasmin; /* Variable index ID */
00125   int varid_prsn; /* Variable index ID */
00126   int varid_prr; /* Variable index ID */
00127   int varid_rlds; /* Variable index ID */
00128   int varid_rsds; /* Variable index ID */
00129   int varid_hur; /* Variable index ID */
00130   int varid_hus; /* Variable index ID */
00131   int varid_husmin; /* Variable index ID */
00132   int varid_husmax; /* Variable index ID */
00133   int varid_etp; /* Variable index ID */
00134   int varid_uvas; /* Variable index ID */
00135   int varid_prtot; /* Variable index ID */
00136 
00137   int configstrdimid; /* Variable dimension ID for configuration */
00138   int configstroutid; /* Variable ID for configuration */
00139   size_t start[1]; /* Start element when writing */
00140   size_t count[1]; /* Count of elements to write */
00141 
00142   int t; /* Time loop counter */
00143   int tl; /* Time loop counter */
00144   int var; /* Variable counter */
00145   int vare; /* Variable counter */
00146   int istat; /* Diagnostic status */
00147   int f; /* Loop counter for files */
00148   int i; /* Loop counter */
00149   int j; /* Loop counter */
00150 
00151   double curtime;
00152 
00153   int ncoutid;
00154   ut_system *unitSystem = NULL; /* Unit System (udunits) */
00155   ut_unit *dataunits = NULL; /* udunits variable */
00156 
00157   double period_begin;
00158   double period_end;
00159 
00160   int year;
00161   int month;
00162   int day;
00163   int hour;
00164   int minutes;
00165   double seconds;
00166 
00167   int yy;
00168   int mm;
00169   int dd;
00170   int hh;
00171 
00172   int minh;
00173   int maxh;
00174 
00175   char *tmpstr = NULL;
00176   short int tas_correction = TRUE;
00177 
00178   /*                                       J   F   M   A   M   J   J   A   S   O   N   D    */
00179   static int days_per_month_reg_year[] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
00180 
00181   infile = (char **) malloc(obs_var->nobs_var * sizeof(char *));
00182   if (infile == NULL) alloc_error(__FILE__, __LINE__);
00183   outfile = (char **) malloc(obs_var->nobs_var * sizeof(char *));
00184   if (outfile == NULL) alloc_error(__FILE__, __LINE__);
00185   outfiles = (char ***) malloc(obs_var->nobs_var * sizeof(char **));
00186   if (outfiles == NULL) alloc_error(__FILE__, __LINE__);
00187   buf = (double **) malloc(obs_var->nobs_var * sizeof(double *));
00188   if (buf == NULL) alloc_error(__FILE__, __LINE__);
00189   for (i=0; i<obs_var->nobs_var; i++)
00190     buf[i] = NULL;
00191   if ( !strcmp(info->timestep, "daily") && !strcmp(obs_var->frequency, "hourly") ) {
00192     bufsave = (double **) malloc(obs_var->nobs_var * sizeof(double *));
00193     if (bufsave == NULL) alloc_error(__FILE__, __LINE__);
00194   }
00195   found_file = (int *) malloc(obs_var->nobs_var * sizeof(int));
00196   if (found_file == NULL) alloc_error(__FILE__, __LINE__);
00197   noutf = (int *) malloc(obs_var->nobs_var * sizeof(int));
00198   if (noutf == NULL) alloc_error(__FILE__, __LINE__);
00199   info_tmp = (info_field_struct **) malloc(obs_var->nobs_var * sizeof(info_field_struct *));
00200   if (info_tmp == NULL) alloc_error(__FILE__, __LINE__);
00201   
00202   found = FALSE;
00203   for (var=0; var<obs_var->nobs_var; var++) {
00204     infile[var] = (char *) malloc(MAXPATH * sizeof(char));
00205     if (infile[var] == NULL) alloc_error(__FILE__, __LINE__);
00206     outfile[var] = (char *) malloc(MAXPATH * sizeof(char));
00207     if (outfile[var] == NULL) alloc_error(__FILE__, __LINE__);
00208     found_file[var] = FALSE;
00209   }
00210   format = (char *) malloc(MAXPATH * sizeof(char));
00211   if (format == NULL) alloc_error(__FILE__, __LINE__);
00212 
00213   if (output_month_begin == 1)
00214     output_month_end = 12;
00215   else
00216     output_month_end = output_month_begin - 1;
00217 
00218   if (obs_var->proj->name != NULL)
00219     (void) free(obs_var->proj->name);
00220   obs_var->proj->name = NULL;
00221 
00222   /* Initialize udunits */
00223   ut_set_error_message_handler(ut_ignore);
00224   unitSystem = ut_read_xml(NULL);
00225   ut_set_error_message_handler(ut_write_to_stderr);
00226   dataunits = ut_parse(unitSystem, time_units, UT_ASCII);
00227 
00228   /* Read altitudes if available, and compute pressure using standard atmosphere */
00229   if ( strcmp(obs_var->altitude, "") ) {
00230     infile_alt = (char *) malloc(MAXPATH * sizeof(char));
00231     if (infile_alt == NULL) alloc_error(__FILE__, __LINE__);
00232     (void) sprintf(infile_alt, "%s/%s", obs_var->path, obs_var->altitude);
00233     istat = read_netcdf_var_2d(&alt, (info_field_struct *) NULL, (proj_struct *) NULL, infile_alt, obs_var->altitudename,
00234                                obs_var->dimxname, obs_var->dimyname, &nlon, &nlat, FALSE);
00235     if (istat < 0)
00236       (void) fprintf(stderr, "%s: WARNING: Cannot read observation altitude field in file %s.\n", __FILE__, infile_alt);
00237     else {
00238       pmsl = (double *) malloc(nlon*nlat*sizeof(double));
00239       if (pmsl == NULL) alloc_error(__FILE__, __LINE__);
00240       (void) alt_to_press(pmsl, alt, nlon, nlat);
00241     }
00242     (void) free(infile_alt);
00243   }
00244   
00245   /* Compute time limits for writing */
00246   if (period->year_begin != -1) {
00247     (void) printf("%s: Downscaling output from %02d/%02d/%04d to %02d/%02d/%04d inclusively.\n", __FILE__,
00248                   period->month_begin, period->day_begin, period->year_begin,
00249                   period->month_end, period->day_end, period->year_end);
00250     istat = utInvCalendar2(period->year_begin, period->month_begin, period->day_begin, 0, 0, 0.0, dataunits, &period_begin);
00251     istat = utInvCalendar2(period->year_end, period->month_end, period->day_end, 23, 59, 0.0, dataunits, &period_end);
00252   }
00253   else {
00254     istat = utCalendar2(time_ls[0], dataunits, &year, &month, &day, &hour, &minutes, &seconds);
00255     (void) printf("%s: Downscaling whole period: %02d/%02d/%04d", __FILE__, month, day, year);
00256     istat = utCalendar2(time_ls[ntime-1], dataunits, &year, &month, &day, &hour, &minutes, &seconds);
00257     (void) printf(" to %02d/%02d/%04d inclusively.\n", month, day, year);
00258     period_begin = time_ls[0];
00259     period_end = time_ls[ntime-1];
00260   }
00261 
00262   /* Process each downscaled day */
00263   for (var=0; var<obs_var->nobs_var; var++) {
00264     noutf[var] = 0;
00265     outfiles[var] = NULL;
00266   }
00267   for (t=0; t<ntime; t++) {
00268 
00269     /* Check if we want to write data for this date */
00270     if (time_ls[t] >= period_begin && time_ls[t] <= period_end) {
00271       
00272       /* Create output filename for writing data */
00273       if (analog_days.month_s[t] < output_month_begin)
00274         year1 = analog_days.year_s[t] - 1;
00275       else
00276         year1 = analog_days.year_s[t];
00277       if (output_month_begin != 1)
00278         year2 = year1 + 1;
00279       else
00280         year2 = year1;
00281       /* Process each variable and create output filenames, and output files if necessary */
00282       for (var=0; var<obs_var->nobs_var; var++) {
00283         /* Example: evapn_1d_19790801_19800731.nc */
00284         (void) sprintf(outfile[var], "%s/%s_1d_%04d%02d%02d_%04d%02d%02d.nc", output_path, obs_var->netcdfname[var],
00285                        year1, output_month_begin, 1,
00286                        year2, output_month_end, days_per_month_reg_year[output_month_end-1]);
00287         /* Check if output file has already been created */
00288         found_file[var] = FALSE;
00289         f = 0;
00290         while (f < noutf[var] && found_file[var] == FALSE) {
00291           if ( !strcmp(outfiles[var][f], outfile[var]) ) {
00292             found_file[var] = TRUE;
00293             break;
00294           }
00295           f++;
00296         }
00297         if (found_file[var] == FALSE) {
00298 
00299           if ( !strcmp(obs_var->output[var], "yes") ) {
00300 
00301             /* File was not created already by this algorithm run */
00302             outfiles[var] = (char **) realloc(outfiles[var], (noutf[var]+1) * sizeof(char *));
00303             if (outfiles[var] == NULL) alloc_error(__FILE__, __LINE__);
00304             outfiles[var][noutf[var]++] = strdup(outfile[var]);
00305             
00306             /* Verify if file exists and if we can write into it */
00307             istat = nc_open(outfile[var], NC_WRITE, &ncoutid);
00308             
00309             if (istat != NC_NOERR) {
00310               /* File does not exists */
00311               
00312               /* Create output file */
00313               istat = create_netcdf(info->title, info->title_french, info->summary, info->summary_french,
00314                                     info->keywords, info->processor, info->software,
00315                                     info->description, info->institution,
00316                                     info->creator_email, info->creator_url, info->creator_name,
00317                                     info->version, info->scenario, info->scenario_co2, info->model,
00318                                     info->institution_model, info->country, info->member,
00319                                     info->downscaling_forcing, info->contact_email, info->contact_name,
00320                                     info->other_contact_email, info->other_contact_name,
00321                                     outfile[var], TRUE, file_format, file_compression);
00322               if (istat != 0) {
00323                 /* In case of failure */
00324                 (void) free(outfile[var]);
00325                 for (f=0; f<noutf[var]; f++)
00326                   (void) free(outfiles[var][f]);
00327                 if (noutf[var] > 0)
00328                   (void) free(outfiles[var]);
00329                 if (pmsl != NULL) (void) free(pmsl);
00330                 if (alt != NULL) (void) free(alt);
00331                 (void) ut_free(dataunits);
00332                 (void) ut_free_system(unitSystem);  
00333                 return istat;
00334               }
00335             
00338               istat = nc_open(outfile[var], NC_WRITE, &ncoutid);  /* open NetCDF file */
00339               if (istat != NC_NOERR) handle_netcdf_error(istat, __FILE__, __LINE__);
00340               
00341               /* Go into redefine mode */
00342               istat = nc_redef(ncoutid);
00343               if (istat != NC_NOERR) handle_netcdf_error(istat, __FILE__, __LINE__);
00344               
00345               /* Define configuration */
00346               istat = nc_def_dim(ncoutid, "configstr", strlen(config)+1, &configstrdimid);
00347               if (istat != NC_NOERR) handle_netcdf_error(istat, __FILE__, __LINE__);
00348               istat = nc_def_var(ncoutid, "dsclim_configuration", NC_CHAR, 1, &configstrdimid, &configstroutid);
00349               if (istat != NC_NOERR) handle_netcdf_error(istat, __FILE__, __LINE__);
00350 
00351               /* Update also time_coverage_end and time_coverage_start global attribute */
00352               tmpstr = (char *) malloc(MAXPATH * sizeof(char));
00353               if (tmpstr == NULL) alloc_error(__FILE__, __LINE__);
00354               hour=0;
00355               minutes=0;
00356               seconds=0;
00357               (void) sprintf(tmpstr, "%04d-%02d-%02dT%02d:%02d:%02dZ", year1, output_month_begin, 1, hour, minutes, (int) seconds);
00358               istat = nc_put_att_text(ncoutid, NC_GLOBAL, "time_coverage_start", strlen(tmpstr), tmpstr);
00359               hour=23;
00360               minutes=59;
00361               seconds=59;
00362               (void) sprintf(tmpstr, "%04d-%02d-%02dT%02d:%02d:%02dZ", year2, output_month_end, days_per_month_reg_year[output_month_end-1],
00363                              hour, minutes, (int) seconds);
00364               istat = nc_put_att_text(ncoutid, NC_GLOBAL, "time_coverage_end", strlen(tmpstr), tmpstr);
00365               (void) free(tmpstr);
00366         
00367               /* End definition mode */
00368               istat = nc_enddef(ncoutid);
00369               if (istat != NC_NOERR) handle_netcdf_error(istat, __FILE__, __LINE__);
00370               
00371               /* Write configuration */
00372               start[0] = 0;
00373               count[0] = strlen(config) + 1;
00374               istat = nc_put_vara_text(ncoutid, configstroutid, start, count, config);
00375               if (istat != NC_NOERR) handle_netcdf_error(istat, __FILE__, __LINE__);
00376             }
00377             else
00378               found_file[var] = TRUE;
00379             
00380             /* Close the output netCDF file. */
00381             istat = ncclose(ncoutid);
00382             if (istat != NC_NOERR) handle_netcdf_error(istat, __FILE__, __LINE__);
00383           }
00384         }
00385       }
00386           
00387       /* Create input filename for reading data */
00388       (void) strcpy(format, "%s/%s/");
00389       (void) strcat(format, obs_var->template);
00390       if (obs_var->month_begin != 1) {
00391         /* Months in observation files *does not* begin in January: must have 2 years in filename */
00392         if (analog_days.month[t] < obs_var->month_begin)
00393           year1 = analog_days.year[t] - 1;
00394         else
00395           year1 = analog_days.year[t];
00396         year2 = year1 + 1;
00397         if (obs_var->year_digits == 4)
00398           /* Process each variable and create input filenames */
00399           for (var=0; var<obs_var->nobs_var; var++)
00400             (void) sprintf(infile[var], format, obs_var->path, obs_var->frequency,
00401                            obs_var->acronym[var], year1, year2);
00402         else {
00403           tmpi = year1 / 100;
00404           year1 = year1 - (tmpi*100);
00405           tmpi = year2 / 100;
00406           year2 = year2 - (tmpi*100);
00407           /* Process each variable and create input filenames */
00408           for (var=0; var<obs_var->nobs_var; var++)
00409             (void) sprintf(infile[var], format, obs_var->path, obs_var->frequency,
00410                            obs_var->acronym[var], year1, year2);
00411         }
00412       }
00413       else {
00414         /* Months in observation files begins in January: must have 1 year in filename */
00415         year1 = analog_days.year[t];
00416         if (obs_var->year_digits == 4)
00417           /* Process each variable and create input filenames */
00418           for (var=0; var<obs_var->nobs_var; var++)
00419             (void) sprintf(infile[var], format, obs_var->path, obs_var->frequency,
00420                            obs_var->acronym[var], year1);
00421         else {
00422           tmpi = year1 / 100;
00423           year1 = year1 - (tmpi*100);
00424           /* Process each variable and create input filenames */
00425           for (var=0; var<obs_var->nobs_var; var++) 
00426             (void) sprintf(infile[var], format, obs_var->path, obs_var->frequency,
00427                            obs_var->acronym[var], year1);
00428         }
00429       }
00430       
00431       /* Get time information for first input observation file and assume all files are alike */
00432       time_s = (time_vect_struct *) malloc(sizeof(time_vect_struct));
00433       if (time_s == NULL) alloc_error(__FILE__, __LINE__);
00434       istat = get_time_info(time_s, &timeval, &time_units_tmp, &cal_type_tmp, &ntime_obs, infile[0], obs_var->timename, FALSE);
00435       (void) free(cal_type_tmp);
00436       (void) free(time_units_tmp);
00437       (void) free(timeval);
00438       if (istat < 0) {
00439         for (var=0; var<obs_var->nobs_var; var++) {
00440           (void) free(outfile[var]);
00441           for (f=0; f<noutf[var]; f++) {
00442             (void) free(outfiles[var][f]);
00443           }
00444           if (noutf[var] > 0) {
00445             (void) free(outfiles[var]);
00446           }
00447         }
00448         (void) free(time_s);
00449         if (pmsl != NULL) (void) free(pmsl);
00450         if (alt != NULL) (void) free(alt);
00451         (void) ut_free(dataunits);
00452         (void) ut_free_system(unitSystem);  
00453         return istat;
00454       }
00455 
00456       /* Find date in observation database */
00457 #if DEBUG > 7
00458       (void) printf("Processing %d %d %d %d\n",t,analog_days.year_s[t],analog_days.month_s[t],analog_days.day_s[t]);
00459 #endif
00460       
00461       if ( !strcmp(obs_var->frequency, "hourly") ) {
00462         /* For hourly frequency data, find hours from 0 to 23 */
00463         minh = 0;
00464         maxh = 23;
00465       }
00466       else {
00467         /* For daily data, only read data for one day */
00468         minh = 0;
00469         maxh = 0;
00470       }
00471 
00472       /* Loop over hours if needed */
00473       for (hour=minh; hour<=maxh; hour++) {
00474         found = FALSE;
00475         tl = 0;
00476         
00477         if ( !strcmp(obs_var->frequency, "hourly") ) {
00478           while (tl<ntime_obs && found == FALSE) {
00479 #if DEBUG > 7
00480             (void) printf("%d %d %d %d %d\n",tl,time_s->year[tl],time_s->month[tl],time_s->day[tl],time_s->hour[tl]);
00481 #endif
00482             if (analog_days.year[t] == time_s->year[tl] && analog_days.month[t] == time_s->month[tl] &&
00483                 analog_days.day[t] == time_s->day[tl] && hour == time_s->hour[tl]) {
00484               found = TRUE;
00485 #if DEBUG > 7
00486               (void) printf("Found analog %d %d %d %d\n",tl,analog_days.year[t],analog_days.month[t],analog_days.day[t]);
00487 #endif
00488             }
00489             tl++;
00490           }
00491         }
00492         else {
00493           while (tl<ntime_obs && found == FALSE) {
00494 #if DEBUG > 7
00495             (void) printf("%d %d %d %d\n",tl,time_s->year[tl],time_s->month[tl],time_s->day[tl]);
00496 #endif
00497             if (analog_days.year[t] == time_s->year[tl] && analog_days.month[t] == time_s->month[tl] &&
00498                 analog_days.day[t] == time_s->day[tl]) {
00499               found = TRUE;
00500 #if DEBUG > 7
00501               (void) printf("Found analog %d %d %d %d\n",tl,analog_days.year[t],analog_days.month[t],analog_days.day[t]);
00502 #endif
00503             }
00504             tl++;
00505           }
00506         }
00507         
00508         if (found == TRUE) {
00509           
00510           tl--;
00511           
00512           proj_tmp = (proj_struct *) malloc(sizeof(proj_struct));
00513           if (proj_tmp == NULL) alloc_error(__FILE__, __LINE__);
00514           proj_tmp->name = NULL;
00515           proj_tmp->grid_mapping_name = NULL;
00516           
00517           /* Process each variable and read data */
00518           for (var=0; var<obs_var->nobs_var; var++) {
00519             info_tmp[var] = (info_field_struct *) malloc(sizeof(info_field_struct));
00520             if (info_tmp[var] == NULL) alloc_error(__FILE__, __LINE__);
00521             /* Don't read variables which will be calculated : read only variables already available in datafiles */
00522             if ( !strcmp(obs_var->post[var], "no") ) {
00523               if (proj_tmp->name != NULL) {
00524                 (void) free(proj_tmp->name);
00525                 proj_tmp->name = NULL;
00526               }
00527               if (proj_tmp->grid_mapping_name != NULL) {
00528                 (void) free(proj_tmp->grid_mapping_name);
00529                 proj_tmp->grid_mapping_name = NULL;
00530               }
00531               istat = read_netcdf_var_3d_2d(&(buf[var]), info_tmp[var], proj_tmp, infile[var], obs_var->acronym[var],
00532                                             obs_var->dimxname, obs_var->dimyname, obs_var->timename,
00533                                             tl, &nlon, &nlat, &ntime_file, debug);
00534               /* Apply factor and delta */
00535               for (j=0; j<nlat; j++)
00536                 for (i=0; i<nlon; i++)
00537                   buf[var][i+j*nlon] = (buf[var][i+j*nlon] * obs_var->factor[var]) + obs_var->delta[var];
00538               /* Overwrite units and height if it was specified in configuration file. In that case, the value is not unknown. */
00539               if ( strcmp(obs_var->units[var], "unknown")) {
00540                 (void) free(info_tmp[var]->units);
00541                 info_tmp[var]->units = strdup(obs_var->units[var]);
00542               }
00543               if ( strcmp(obs_var->height[var], "unknown")) {
00544                 (void) free(info_tmp[var]->height);
00545                 info_tmp[var]->height = strdup(obs_var->height[var]);
00546               }
00547             }
00548             else {
00549               /* For post-processing variables, must fill in the info field structure info_tmp.
00550                  The projection structure proj_tmp used is the one of the previous variable,
00551                  because the first variable in the list is enforced to be a non post-processing variable
00552                  when loading the configuration file. */
00553               info_tmp[var]->fillvalue = info_tmp[0]->fillvalue;
00554               info_tmp[var]->coordinates = strdup(info_tmp[0]->coordinates);
00555               info_tmp[var]->grid_mapping = strdup(info_tmp[0]->grid_mapping);
00556               info_tmp[var]->units = strdup(obs_var->units[var]);
00557               info_tmp[var]->height = strdup(obs_var->height[var]);
00558               info_tmp[var]->long_name = strdup(obs_var->name[var]);
00559             }              
00560           }
00561 
00562           if (obs_var->proj->name == NULL) {
00563             /* Retrieve observation grid parameters if not done already */
00564             obs_var->proj->name = strdup(proj_tmp->name);
00565             obs_var->proj->grid_mapping_name = strdup(proj_tmp->grid_mapping_name);
00566             obs_var->proj->latin1 = proj_tmp->latin1;
00567             obs_var->proj->latin2 = proj_tmp->latin2;
00568             obs_var->proj->lonc = proj_tmp->lonc;
00569             obs_var->proj->lat0 = proj_tmp->lat0;
00570             obs_var->proj->false_easting = proj_tmp->false_easting;
00571             obs_var->proj->false_northing = proj_tmp->false_northing;
00572             
00573             /* Get latitude and longitude coordinates information from first file */
00574             istat = read_netcdf_latlon(&lon, &lat, &nlon, &nlat, obs_var->dimcoords, obs_var->proj->coords,
00575                                        obs_var->proj->name, obs_var->lonname,
00576                                        obs_var->latname, obs_var->dimxname,
00577                                        obs_var->dimyname, infile[0]);
00578             if ( !strcmp(obs_var->proj->name, "list") )
00579               /* List of lat + lon points only : keep only X dimension */
00580               nlat = 0;
00581             else
00582               /* Read coordinates information */
00583               istat = read_netcdf_xy(&x, &y, &nlon, &nlat, obs_var->dimxname, obs_var->dimyname, 
00584                                      obs_var->dimxname, obs_var->dimyname, infile[0]);
00585           }
00586           
00587           /*** Apply modifications to data ***/
00590           /* Find known variable IDs for correction or calculation */
00591           varid_tas = find_str_value("tas", obs_var->netcdfname, obs_var->nobs_var);
00592           varid_tasmin = find_str_value("tasmin", obs_var->netcdfname, obs_var->nobs_var);
00593           varid_tasmax = find_str_value("tasmax", obs_var->netcdfname, obs_var->nobs_var);
00594           varid_prsn = find_str_value("prsn", obs_var->netcdfname, obs_var->nobs_var);
00595           varid_prr = find_str_value("prr", obs_var->netcdfname, obs_var->nobs_var);
00596           varid_rlds = find_str_value("rlds", obs_var->netcdfname, obs_var->nobs_var);
00597           varid_rsds = find_str_value("rsds", obs_var->netcdfname, obs_var->nobs_var);
00598           varid_hus = find_str_value("hus", obs_var->netcdfname, obs_var->nobs_var);
00599           varid_husmin = find_str_value("husmin", obs_var->netcdfname, obs_var->nobs_var);
00600           varid_husmax = find_str_value("husmax", obs_var->netcdfname, obs_var->nobs_var);
00601           varid_uvas = find_str_value("uvas", obs_var->netcdfname, obs_var->nobs_var);
00602           varid_hur = find_str_value("hur", obs_var->netcdfname, obs_var->nobs_var);
00603           varid_etp = find_str_value("evapn", obs_var->netcdfname, obs_var->nobs_var);
00604           varid_prtot = find_str_value("prtot", obs_var->netcdfname, obs_var->nobs_var);
00605 
00606           tas_correction = TRUE;
00607 
00608           if ( (varid_tasmax >= 0 || varid_tasmin >= 0 || varid_husmin >= 0 || varid_husmax >= 0) && !strcmp(obs_var->frequency, "hourly")) {
00609             (void) fprintf(stderr, "%s: WARNING: Cannot mix min and/or max observation variables with hourly data! Min and/or max variables will be ignored! \n", __FILE__);
00610             varid_tasmin = -1;
00611             varid_tasmax = -1;
00612             varid_husmin = -1;
00613             varid_husmax = -1;
00614           }
00615 
00616           if ( !strcmp(obs_var->frequency, "daily") ) {
00617             if (varid_tas < 0 && ( varid_tasmin < 0 || varid_tasmax < 0 ) )
00618               tas_correction = FALSE;
00619           }
00620           else {
00621             if (varid_tas < 0)
00622               tas_correction = FALSE;
00623           }
00624 
00625           //            (void) fprintf(stderr, "%s: WARNING: No temperature correction can be done to precipitation partition or infra-red radiation required temperature variables are not available! It needs at least either average daily or hourly temperature, or, with daily data, min and max temperatures.\n", __FILE__);
00626 
00627           /* Correct average temperature and related variables (precipitation partition, infra-red radiation) */
00628           if (varid_tas >= 0 && tas_correction == TRUE) {
00629             if (fabs(delta[t]) >= deltat)
00630               for (j=0; j<nlat; j++)
00631                 for (i=0; i<nlon; i++)
00632                   
00633                   if (buf[varid_tas][i+j*nlon] != info_tmp[varid_tas]->fillvalue) {
00634                     
00635                     /* Save non-corrected temperature */
00636                     curtas = buf[varid_tas][i+j*nlon];
00637                     /* Compute new temperature */                
00638                     buf[varid_tas][i+j*nlon] += delta[t];
00639                     
00640                     /* Compute new rain/snow partition, if needed */
00641                     if (varid_prsn != -1 && varid_prr != -1)
00642                       if (buf[varid_prsn][i+j*nlon] != info_tmp[varid_prsn]->fillvalue &&
00643                           buf[varid_prr][i+j*nlon] != info_tmp[varid_prr]->fillvalue)
00644                         if ( buf[varid_tas][i+j*nlon] >= (K_TKELVIN + 1.5) ) {
00645                           buf[varid_prr][i+j*nlon] += buf[varid_prsn][i+j*nlon];
00646                           buf[varid_prsn][i+j*nlon] = 0.0;
00647                         }
00648                     
00649                     /* Compute new infra-red radiation, if needed */
00650                     if (varid_rlds != -1)
00651                       if (buf[varid_rlds][i+j*nlon] != info_tmp[varid_rlds]->fillvalue)
00652                         buf[varid_rlds][i+j*nlon] += (4.0 * delta[t] / curtas ) * buf[varid_rlds][i+j*nlon];
00653                     
00654                   }
00655           }
00656 
00657           /* Correct min and max temperatures and related variables when having daily data */
00658           if (varid_tasmax >= 0 && varid_tasmin >= 0 && tas_correction == TRUE && !strcmp(obs_var->frequency, "daily")) {
00659             if (fabs(delta[t]) >= deltat)
00660               for (j=0; j<nlat; j++)
00661                 for (i=0; i<nlon; i++)
00662                   
00663                   if (buf[varid_tasmax][i+j*nlon] != info_tmp[varid_tasmax]->fillvalue) {
00664                     
00665                     /* Save non-corrected mean temperature */
00666                     curtas = (buf[varid_tasmax][i+j*nlon] + buf[varid_tasmin][i+j*nlon]) / 2.0;
00667                     /* Compute new temperature */                
00668                     buf[varid_tasmax][i+j*nlon] += delta[t];
00669                     buf[varid_tasmin][i+j*nlon] += delta[t];
00670                     /* New averaged temperature */
00671                     newcurtas = (buf[varid_tasmax][i+j*nlon] + buf[varid_tasmin][i+j*nlon]) / 2.0;
00672 
00673                     /* Do not perform correction twice! */
00674                     if (varid_tas < 0) {
00675                       /* Compute new rain/snow partition, if needed */
00676                       if (varid_prsn != -1 && varid_prr != -1)
00677                         if (buf[varid_prsn][i+j*nlon] != info_tmp[varid_prsn]->fillvalue &&
00678                             buf[varid_prr][i+j*nlon] != info_tmp[varid_prr]->fillvalue)
00679                           if ( newcurtas >= (K_TKELVIN + 1.5) ) {
00680                             buf[varid_prr][i+j*nlon] += buf[varid_prsn][i+j*nlon];
00681                             buf[varid_prsn][i+j*nlon] = 0.0;
00682                           }
00683                   
00684                       /* Compute new infra-red radiation, if needed */
00685                       if (varid_rlds != -1)
00686                         if (buf[varid_rlds][i+j*nlon] != info_tmp[varid_rlds]->fillvalue)
00687                           buf[varid_rlds][i+j*nlon] += (4.0 * delta[t] / curtas ) * buf[varid_rlds][i+j*nlon];
00688                     }
00689                   }
00690           }
00691 
00692           /* Calculate only known post-processed variables */
00693 
00694           if (varid_hur >= 0) {
00695             /* Relative humidity */
00696             if ( !strcmp(obs_var->post[varid_hur], "yes") ) {
00697               if ( varid_hus >= 0 && (varid_tas >= 0 || (varid_tasmax >= 0 && varid_tasmin >= 0 )) && pmsl != NULL ) {
00698                 /* Calculate relative humidity from temperature and specific humidity */
00699                 buf[varid_hur] = (double *) malloc(nlat*nlon * sizeof(double));
00700                 if (buf[varid_hur] == NULL) alloc_error(__FILE__, __LINE__);
00701                 if (varid_tas >= 0)
00702                   info_tmp[varid_hur]->fillvalue = info_tmp[varid_tas]->fillvalue;
00703                 else if (varid_tasmax >= 0)
00704                   info_tmp[varid_hur]->fillvalue = info_tmp[varid_tasmax]->fillvalue;
00705                 else
00706                   info_tmp[varid_hur]->fillvalue = -9999.0;
00707                 /* Create mean temperature temporary matrix when having only min and max temperature */
00708                 if (varid_tas < 0) {
00709                   buftmp = (double *) malloc(nlat*nlon* sizeof(double));
00710                   if (buftmp == NULL) alloc_error(__FILE__, __LINE__);
00711                   info_tmp[varid_tas]->fillvalue = info_tmp[varid_tasmax]->fillvalue;
00712                   for (i=0; i<(nlon*nlat); i++)
00713                     if ((buf[varid_tasmax][i] != info_tmp[varid_tasmax]->fillvalue) &&
00714                         (buf[varid_tasmin][i] != info_tmp[varid_tasmin]->fillvalue))
00715                       buftmp[i] = (buf[varid_tasmax][i] + buf[varid_tasmin][i]) / 2.0;
00716                     else
00717                       buftmp[i] = info_tmp[varid_tas]->fillvalue;
00718                 }
00719                 else
00720                   buftmp = buf[varid_tas];
00721                 (void) spechum_to_hr(buf[varid_hur], buftmp, buf[varid_hus], pmsl, info_tmp[varid_hur]->fillvalue, nlon, nlat);
00722                 if (varid_tas < 0)
00723                   (void) free(buftmp);
00724               }
00725               else {
00726                 (void) fprintf(stderr, "%s: WARNING: Cannot calculate Relative Humidity because needed variables are not available: Specific Humidity; Averaged temperature or Min/Max temperature, Standard Pressure from altitude.\n", __FILE__);                
00727                 buf[varid_hur] = NULL;
00728               }
00729             }
00730           }
00731 
00732           if (varid_prsn >= 0 && varid_prr >= 0 && varid_prtot >= 0) {
00733             /* Total precipitation */
00734             if ( !strcmp(obs_var->post[varid_prtot], "yes") ) {
00735               /* Calculate total precipitation from liquid and solid precipitation */
00736                 buf[varid_prtot] = (double *) malloc(nlat*nlon * sizeof(double));
00737                 if (buf[varid_prtot] == NULL) alloc_error(__FILE__, __LINE__);
00738                 info_tmp[varid_prtot]->fillvalue = info_tmp[varid_prr]->fillvalue;
00739                 for (i=0; i<(nlon*nlat); i++) {
00740                   if ( (buf[varid_prr][i] != info_tmp[varid_prr]->fillvalue) && (buf[varid_prsn][i] != info_tmp[varid_prsn]->fillvalue))
00741                     buf[varid_prtot][i] = buf[varid_prr][i] + buf[varid_prsn][i];
00742                   else
00743                     buf[varid_prtot][i] = info_tmp[varid_prtot]->fillvalue;
00744                 }
00745               }
00746             else {
00747                 (void) fprintf(stderr, "%s: WARNING: Cannot calculate Total Precipitation because needed variables are not available: Liquid and Solid Precipitation.\n", __FILE__);                
00748                 buf[varid_prtot] = NULL;
00749             }
00750           }
00751 
00752           if (varid_etp >= 0) {
00753             /* ETP */
00754             if ( !strcmp(obs_var->post[varid_etp], "yes") ) {
00755               if ( varid_hus >= 0 && (varid_tas >= 0 || (varid_tasmax >= 0 && varid_tasmin >= 0 )) && varid_rsds >= 0 && varid_rlds >= 0 &&
00756                    varid_uvas >= 0 && pmsl != NULL ) {
00757                 /* Calculate ETP */
00758                 buf[varid_etp] = (double *) malloc(nlat*nlon * sizeof(double));
00759                 if (buf[varid_etp] == NULL) alloc_error(__FILE__, __LINE__);
00760                 if (varid_tas >= 0)
00761                   info_tmp[varid_etp]->fillvalue = info_tmp[varid_tas]->fillvalue;
00762                 else if (varid_tasmax >= 0)
00763                   info_tmp[varid_etp]->fillvalue = info_tmp[varid_tasmax]->fillvalue;
00764                 else
00765                   info_tmp[varid_etp]->fillvalue = -9999.0;
00766                 /* Create mean temperature temporary matrix when having only min and max temperature */
00767                 if (varid_tas < 0) {
00768                   buftmp = (double *) malloc(nlat*nlon* sizeof(double));
00769                   if (buftmp == NULL) alloc_error(__FILE__, __LINE__);
00770                   for (i=0; i<(nlon*nlat); i++) {
00771                     if ((buf[varid_tasmax][i] != info_tmp[varid_tasmax]->fillvalue) &&
00772                         (buf[varid_tasmin][i] != info_tmp[varid_tasmin]->fillvalue))
00773                       buftmp[i] = (buf[varid_tasmax][i] + buf[varid_tasmin][i]) / 2.0;
00774                     else
00775                       buftmp[i] = info_tmp[varid_tasmax]->fillvalue;
00776                   }
00777                 }
00778                 else
00779                   buftmp = buf[varid_tas];
00780                 (void) calc_etp_mf(buf[varid_etp], buftmp, buf[varid_hus], buf[varid_rsds], buf[varid_rlds], buf[varid_uvas],
00781                                    pmsl, info_tmp[varid_etp]->fillvalue, nlon, nlat);
00782                 if (varid_tas < 0)
00783                   (void) free(buftmp);
00784               }
00785               else {
00786                 (void) fprintf(stderr, "%s: WARNING: Cannot calculate ETP because needed variables are not available: Specific Humidity; Averaged Temperature or Min/Max Temperature; Short and Long Wave Radiation; Wind Module, Standard Pressure from altitude.\n", __FILE__);
00787                 buf[varid_etp] = NULL;
00788               }
00789             }
00790           }
00791 
00792           /* Process each variable for writing */
00793           for (var=0; var<obs_var->nobs_var; var++) {
00794             if ( !strcmp(obs_var->output[var], "yes") ) {
00795               /* Write dimensions of field in newly-created NetCDF output file */
00796               if (found_file[var] == FALSE && hour == minh && buf[var] != NULL) {
00797                 /* We just created output file: we need to write dimensions */
00798                 ctimeval[0] = time_ls[t];
00799                 istat = write_netcdf_dims_3d(lon, lat, x, y, alt, ctimeval, cal_type,
00800                                              time_units, nlon, nlat, 0,
00801                                              info->timestep, obs_var->proj->name, obs_var->proj->coords,
00802                                              obs_var->proj->grid_mapping_name, obs_var->proj->latin1,
00803                                              obs_var->proj->latin2, obs_var->proj->lonc, obs_var->proj->lat0,
00804                                              obs_var->proj->false_easting, obs_var->proj->false_northing,
00805                                              obs_var->proj->lonpole, obs_var->proj->latpole,
00806                                              obs_var->lonname, obs_var->latname, obs_var->timename,
00807                                              outfile[var], debug);
00808                 if (istat != 0) {
00809                   /* In case of failure */
00810                   (void) free(time_s->year);
00811                   (void) free(time_s->month);
00812                   (void) free(time_s->day);
00813                   (void) free(time_s->hour);
00814                   (void) free(time_s->minutes);
00815                   (void) free(time_s->seconds);
00816                   
00817                   (void) free(time_s);
00818             
00819                   (void) free(infile[var]);
00820                   (void) free(outfile[var]);
00821                   (void) free(info_tmp[var]->grid_mapping);
00822                   (void) free(info_tmp[var]->units);
00823                   (void) free(info_tmp[var]->height);
00824                   (void) free(info_tmp[var]->coordinates);
00825                   (void) free(info_tmp[var]->long_name);
00826                   (void) free(info_tmp[var]);
00827                   (void) free(proj_tmp->name);
00828                   (void) free(proj_tmp->grid_mapping_name);
00829                   (void) free(proj_tmp);
00830                   for (f=0; f<noutf[var]; f++)
00831                     (void) free(outfiles[var][f]);
00832                   if (noutf[var] > 0)
00833                     (void) free(outfiles[var]);
00834                   (void) free(outfiles);
00835                   if (pmsl != NULL) (void) free(pmsl);
00836                   if (alt != NULL) (void) free(alt);
00837                   (void) ut_free(dataunits);
00838                   (void) ut_free_system(unitSystem);  
00839                   return istat;
00840                 }
00841               }
00842             }
00843           }
00844 
00845           /* Compute time if output timestep is hourly and not daily */
00846           if ( !strcmp(info->timestep, "hourly") ) {
00847             istat = utCalendar2(time_ls[t], dataunits, &yy, &mm, &dd, &hh, &minutes, &seconds);
00848             istat = utInvCalendar2(yy, mm, dd, hour, 0, 0.0, dataunits, &curtime);
00849           }
00850           else
00851             curtime = time_ls[t];
00852 
00853           /* Process each variable */
00854           for (var=0; var<obs_var->nobs_var; var++) {
00855             if (buf[var] != NULL && !strcmp(obs_var->output[var], "yes")) {
00856               if ( !strcmp(info->timestep, obs_var->frequency) ) {
00857                 /* Output and input data are at same frequency */
00858                 if (found_file[var] == FALSE && hour == minh)
00859                   (void) fprintf(stderr, "%s: Writing data to %s\n", __FILE__, outfile[var]);
00860                 /* Write data */
00861                 istat = write_netcdf_var_3d_2d(buf[var], &curtime, info_tmp[var]->fillvalue, outfile[var], obs_var->netcdfname[var],
00862                                                info_tmp[var]->long_name, info_tmp[var]->units, info_tmp[var]->height, proj_tmp->name, 
00863                                                obs_var->dimxname, obs_var->dimyname, obs_var->timename,
00864                                                0, !(found_file[var]), file_format, file_compression_level,
00865                                                nlon, nlat, ntime_file, debug);
00866                 found_file[var] = TRUE;
00867               }
00868               else if ( !strcmp(info->timestep, "daily") && !strcmp(obs_var->frequency, "hourly") ) {
00869                 if (hour == maxh) {
00870                   /* Last hour of day */
00871                   for (i=0; i<nlon*nlat; i++)
00872                     /* Average data */
00873                     buf[var][i] = (bufsave[var][i] + buf[var][i]) / 24.0;
00874                   /* Free memory */
00875                   (void) free(bufsave[var]);
00876                   bufsave[var] = NULL;
00877                   if (found_file[var] == FALSE && hour == minh)
00878                     (void) fprintf(stderr, "%s: Writing data to %s\n",__FILE__, outfile[var]);
00879                   /* Write data */
00880                   istat = write_netcdf_var_3d_2d(buf[var], &curtime, info_tmp[var]->fillvalue, outfile[var], obs_var->netcdfname[var],
00881                                                  info_tmp[var]->long_name, info_tmp[var]->units, info_tmp[var]->height, proj_tmp->name, 
00882                                                  obs_var->dimxname, obs_var->dimyname, obs_var->timename,
00883                                                  0, !(found_file[var]),  file_format, file_compression_level,
00884                                                  nlon, nlat, ntime_file, debug);
00885                   found_file[var] = TRUE;
00886                 }
00887                 else {
00888                   /* Allocate memory if first hour accumulating */
00889                   if (bufsave[var] == NULL) {
00890                     bufsave[var] = (double *) calloc(nlat*nlon, sizeof(double));
00891                     if (bufsave[var] == NULL) alloc_error(__FILE__, __LINE__);
00892                   }
00893                   /* Accumulate data to compute average when input data is hourly and output is daily */
00894                   for (i=0; i<nlon*nlat; i++)
00895                     bufsave[var][i] += buf[var][i];
00896                 }
00897               }
00898               else {
00899                 (void) fprintf(stderr, "%s: Fatal error in configuration of output timestep and observation variables frequency! Output timestep = %s    Observation variables frequency = %s\n", __FILE__, info->timestep, obs_var->frequency);
00900                 
00901                 /* Fatal error */
00902                 if (buf[var] != NULL) (void) free(buf[var]);
00903                 (void) free(info_tmp[var]->grid_mapping);
00904                 (void) free(info_tmp[var]->units);
00905                 (void) free(info_tmp[var]->height);
00906                 (void) free(info_tmp[var]->coordinates);
00907                 (void) free(info_tmp[var]->long_name);
00908                 (void) free(info_tmp[var]);
00909                 
00910                 for (vare=0; vare<=var; vare++) {
00911                   for (f=0; f<noutf[vare]; f++)
00912                     (void) free(outfiles[vare][f]);
00913                   if (noutf[vare] > 0)
00914                     (void) free(outfiles[vare]);
00915                   (void) free(infile[vare]);
00916                   (void) free(outfile[vare]);
00917                 }
00918                 (void) free(outfiles);
00919                 (void) free(noutf);
00920                 (void) free(found_file);
00921                 (void) free(info_tmp);
00922                 (void) free(buf);
00923                 
00924                 (void) free(lat);
00925                 (void) free(lon);
00926                 
00927                 (void) free(x);
00928                 (void) free(y);
00929                 
00930                 (void) free(format);
00931                 
00932                 (void) free(proj_tmp->name);
00933                 (void) free(proj_tmp->grid_mapping_name);
00934                 (void) free(proj_tmp);
00935                 
00936                 (void) free(time_s->year);
00937                 (void) free(time_s->month);
00938                 (void) free(time_s->day);
00939                 (void) free(time_s->hour);
00940                 (void) free(time_s->minutes);
00941                 (void) free(time_s->seconds);
00942                 
00943                 (void) free(time_s);
00944 
00945                 if (alt != NULL) (void) free(alt);
00946 
00947                 (void) ut_free(dataunits);
00948                 (void) ut_free_system(unitSystem);  
00949 
00950                 return -3;
00951               }
00952             }
00953             
00954             /* Free allocated memory */
00955             if (buf[var] != NULL) (void) free(buf[var]);
00956             (void) free(info_tmp[var]->grid_mapping);
00957             (void) free(info_tmp[var]->units);
00958             (void) free(info_tmp[var]->height);
00959             (void) free(info_tmp[var]->coordinates);
00960             (void) free(info_tmp[var]->long_name);
00961             (void) free(info_tmp[var]);
00962           }
00963 
00964           /* Free allocated memory */
00965           (void) free(proj_tmp->name);
00966           (void) free(proj_tmp->grid_mapping_name);
00967           (void) free(proj_tmp);        
00968         }
00969         else {
00970           //output_downscaled_analog.c: Fatal error in algorithm: analog date 3276 2000 12 31 19 not found in database!!
00971           //output_downscaled_analog.c: Writing data to /home/globc/page/downscaling_v2/data/results/scratch2010/hourly/arpege/arpege_ref/uvas_1d_19820101_19821231.nc
00972           //output_downscaled_analog.c: Fatal error in algorithm: analog date 12050 2000 12 31 19 not found in database!!
00973           if ( !strcmp(obs_var->frequency, "hourly") ) {
00974             (void) fprintf(stderr, "%s: Fatal error in algorithm: analog date %d %d %d %d %d not found in database!!\n", __FILE__, t,
00975                            analog_days.year[t],analog_days.month[t],analog_days.day[t],hour);
00976             minh = 0;
00977             maxh = 23;
00978             for (hour=minh; hour<=maxh; hour++) {
00979               found = FALSE;
00980               tl = 0;
00981               while (tl<ntime_obs && found == FALSE) {
00982                 (void) printf("%d %d %d %d %d\n",tl,time_s->year[tl],time_s->month[tl],time_s->day[tl],time_s->hour[tl]);
00983                 if (analog_days.year[t] == time_s->year[tl] && analog_days.month[t] == time_s->month[tl] &&
00984                     analog_days.day[t] == time_s->day[tl] && hour == time_s->hour[tl]) {
00985                   found = TRUE;
00986                   (void) printf("Found analog %d %d %d %d\n",tl,analog_days.year[t],analog_days.month[t],analog_days.day[t]);
00987                 }
00988                 tl++;
00989               }
00990             }
00991           }
00992           else
00993             (void) fprintf(stderr, "%s: Fatal error in algorithm: analog date %d %d %d %d not found in database!!\n", __FILE__, t,
00994                            analog_days.year[t],analog_days.month[t],analog_days.day[t]);
00995           /* Fatal error */
00996           for (var=0; var<obs_var->nobs_var; var++) {
00997             for (f=0; f<noutf[var]; f++)
00998               (void) free(outfiles[var][f]);
00999             if (noutf[var] > 0)
01000               (void) free(outfiles[var]);
01001             (void) free(infile[var]);
01002             (void) free(outfile[var]);
01003           }
01004           (void) free(outfiles);
01005           (void) free(noutf);
01006           (void) free(found_file);
01007           (void) free(info_tmp);
01008           (void) free(buf);
01009       
01010           (void) free(lat);
01011           (void) free(lon);
01012       
01013           (void) free(x);
01014           (void) free(y);
01015       
01016           (void) free(format);
01017       
01018           (void) free(proj_tmp->name);
01019           (void) free(proj_tmp->grid_mapping_name);
01020           (void) free(proj_tmp);
01021       
01022           (void) free(time_s->year);
01023           (void) free(time_s->month);
01024           (void) free(time_s->day);
01025           (void) free(time_s->hour);
01026           (void) free(time_s->minutes);
01027           (void) free(time_s->seconds);
01028       
01029           (void) free(time_s);
01030       
01031           if (alt != NULL) (void) free(alt);
01032 
01033           (void) ut_free(dataunits);
01034           (void) ut_free_system(unitSystem);  
01035 
01036           return -1;
01037         }
01038       }
01039       (void) free(time_s->year);
01040       (void) free(time_s->month);
01041       (void) free(time_s->day);
01042       (void) free(time_s->hour);
01043       (void) free(time_s->minutes);
01044       (void) free(time_s->seconds);
01045       
01046       (void) free(time_s);
01047     }
01048   }
01049   
01050   /* Free allocated memory */
01051   for (var=0; var<obs_var->nobs_var; var++) {
01052     for (f=0; f<noutf[var]; f++)
01053       (void) free(outfiles[var][f]);
01054     if (noutf[var] > 0)
01055       (void) free(outfiles[var]);
01056     (void) free(infile[var]);
01057     (void) free(outfile[var]);
01058   }
01059   (void) free(outfiles);
01060   (void) free(noutf);
01061   (void) free(found_file);
01062   (void) free(info_tmp);
01063   (void) free(buf);
01064   
01065   (void) free(x);
01066   (void) free(y);
01067   
01068   (void) free(lat);
01069   (void) free(lon);
01070 
01071   if (pmsl != NULL) (void) free(pmsl);
01072   if (alt != NULL) (void) free(alt);
01073 
01074   (void) free(infile);
01075   (void) free(outfile);
01076   (void) free(format);
01077   
01078   (void) ut_free(dataunits);
01079   (void) ut_free_system(unitSystem);  
01080 
01081   /* Success diagnostic */
01082   return 0;
01083 }

Generated on 12 May 2016 for DSCLIM by  doxygen 1.6.1