nco/ncecat.c File Reference

#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <time.h>
#include <unistd.h>
#include "nco_getopt.h"
#include <netcdf.h>
#include "libnco.h"

Include dependency graph for ncecat.c:

Go to the source code of this file.

Defines

#define MAIN_PROGRAM_FILE

Functions

int main (int argc, char **argv)


Define Documentation

#define MAIN_PROGRAM_FILE
 

Definition at line 57 of file ncecat.c.


Function Documentation

int main int  argc,
char **  argv
 

Definition at line 61 of file ncecat.c.

References var_sct_tag::cnt, dmn_sct_tag::cnt, copyright_prn(), var_sct_tag::dim, var_sct_tag::dmn_id, var_sct_tag::end, dmn_sct_tag::end, EXIT_FAILURE, EXIT_SUCCESS, False, FILE, getopt_long, dmn_sct_tag::id, int_CEWI, dmn_sct_tag::is_crd_dmn, dmn_sct_tag::is_rec_dmn, var_sct_tag::is_rec_var, lst_prs_2D(), option::name, var_sct_tag::nbr_dim, NC_FORMAT_64BIT, NC_FORMAT_CLASSIC, NC_FORMAT_NETCDF4, NC_GLOBAL, dmn_sct_tag::nc_id, NC_MAX_DIMS, NC_NOERR, NC_NOFILL, NC_NOWRITE, nco_att_cpy(), nco_bool, nco_close(), nco_cmd_ln_sng(), nco_cnv_ccm_ccsm_cf_inq(), nco_create_mode_prs(), nco_dmn_dfn(), nco_dmn_dpl(), nco_dmn_fll(), nco_dmn_lmt_mrg(), nco_dmn_lst_ass_var(), nco_dmn_lst_free(), nco_dmn_xrf(), nco_enddef(), nco_err_exit(), nco_exit(), nco_exit_gracefully(), nco_fl_cmp_err_chk(), nco_fl_lst_att_cat(), nco_fl_lst_mk(), nco_fl_mk_lcl(), nco_fl_nm_prs(), nco_fl_out_cls(), nco_fl_out_open(), nco_fl_rm(), nco_free(), nco_hst_att_cat(), nco_inq(), nco_lbr_vrs_prn(), nco_lmt_evl(), nco_lmt_lst_free(), nco_lmt_prs(), nco_lst_comma2hash(), nco_lst_srt_nm_id(), nco_malloc(), nco_nm_id_lst_free(), nco_open(), nco_openmp_ini(), nco_pck_map_nil, nco_pck_plc_nil, nco_put_var1(), nco_put_vara(), nco_realloc(), NCO_REC_DMN_UNDEFINED, nco_set_fill(), nco_sng_lst_free(), nco_thr_att_cat(), nco_usg_prn(), nco_var_dfn(), nco_var_dpl(), nco_var_fll(), nco_var_get(), nco_var_lst_add_crd(), nco_var_lst_ass_crd_add(), nco_var_lst_dvd(), nco_var_lst_free(), nco_var_lst_mk(), nco_var_lst_xcl(), nco_var_mtd_refresh(), nco_var_srt_zero(), nco_var_val_cpy(), nco_xrf_dmn(), nco_xrf_var(), dmn_sct_tag::nm, no_argument, NULL_CEWI, omp_get_thread_num(), optarg, optind, prg_nm_get(), prg_prs(), required_argument, var_sct_tag::srt, dmn_sct_tag::srt, var_sct_tag::sz, dmn_sct_tag::sz, var_sct_tag::sz_rec, True, var_sct_tag::type, var_sct_tag::val, option::val, dmn_sct_tag::val, ptr_unn::vp, and dmn_sct_tag::xrf.

00062 {
00063   nco_bool EXCLUDE_INPUT_LIST=False; /* Option c */
00064   nco_bool EXTRACT_ALL_COORDINATES=False; /* Option c */
00065   nco_bool EXTRACT_ASSOCIATED_COORDINATES=True; /* Option C */
00066   nco_bool FILE_RETRIEVED_FROM_REMOTE_LOCATION;
00067   nco_bool FL_LST_IN_APPEND=True; /* Option H */
00068   nco_bool FL_LST_IN_FROM_STDIN=False; /* [flg] fl_lst_in comes from stdin */
00069   nco_bool FORCE_APPEND=False; /* Option A */
00070   nco_bool FORCE_OVERWRITE=False; /* Option O */
00071   nco_bool FORTRAN_IDX_CNV=False; /* Option F */
00072   nco_bool HISTORY_APPEND=True; /* Option h */
00073   nco_bool CNV_CCM_CCSM_CF;
00074   nco_bool REMOVE_REMOTE_FILES_AFTER_PROCESSING=True; /* Option R */
00075 
00076   char **fl_lst_abb=NULL; /* Option a */
00077   char **fl_lst_in;
00078   char **var_lst_in=NULL_CEWI;
00079   char *cmd_ln;
00080   char *fl_in=NULL;
00081   char *fl_out=NULL; /* Option o */
00082   char *fl_out_tmp;
00083   char *fl_pth=NULL; /* Option p */
00084   char *fl_pth_lcl=NULL; /* Option l */
00085   char *lmt_arg[NC_MAX_DIMS];
00086   char *opt_crr=NULL; /* [sng] String representation of current long-option name */
00087   char *optarg_lcl=NULL; /* [sng] Local copy of system optarg */
00088   char *time_bfr_srt;
00089 
00090   const char * const CVS_Id="$Id: ncecat.c,v 1.117 2006/02/19 00:42:34 zender Exp $"; 
00091   const char * const CVS_Revision="$Revision: 1.117 $";
00092   const char * const opt_sht_lst="4ACcD:d:FHhl:n:Oo:p:rRt:v:x-:";
00093 
00094   dmn_sct *rec_dmn;
00095   dmn_sct **dim;
00096   dmn_sct **dmn_out;
00097   
00098   extern char *optarg;
00099   extern int optind;
00100   
00101   /* Using naked stdin/stdout/stderr in parallel region generates warning
00102      Copy appropriate filehandle to variable scoped shared in parallel clause */
00103   FILE * const fp_stderr=stderr; /* [fl] stderr filehandle CEWI */
00104 
00105   int *in_id_arr;
00106 
00107   int abb_arg_nbr=0;
00108   int fl_idx;
00109   int fl_nbr=0;
00110   int fl_out_fmt=NC_FORMAT_CLASSIC; /* [enm] Output file format */
00111   int fll_md_old; /* [enm] Old fill mode */
00112   int idx;
00113   int in_id;  
00114   int lmt_nbr=0; /* Option d. NB: lmt_nbr gets incremented */
00115   int nbr_dmn_fl;
00116   int nbr_dmn_xtr;
00117   int nbr_var_fix; /* nbr_var_fix gets incremented */
00118   int nbr_var_fl;
00119   int nbr_var_prc; /* nbr_var_prc gets incremented */
00120   int nbr_xtr=0; /* nbr_xtr won't otherwise be set for -c with no -v */
00121   int opt;
00122   int out_id;  
00123   int rcd=NC_NOERR; /* [rcd] Return code */
00124   int rec_dmn_id=NCO_REC_DMN_UNDEFINED;
00125   int thr_idx; /* [idx] Index of current thread */
00126   int thr_nbr=int_CEWI; /* [nbr] Thread number Option t */
00127   int var_lst_in_nbr=0;
00128 
00129   lmt_sct **lmt;
00130   
00131   long idx_rec_out=0L; /* idx_rec_out gets incremented */
00132   
00133   nm_id_sct *dmn_lst;
00134   nm_id_sct *xtr_lst=NULL; /* xtr_lst may be alloc()'d from NULL with -c option */
00135   
00136   time_t time_crr_time_t;
00137   
00138   var_sct **var;
00139   var_sct **var_fix;
00140   var_sct **var_fix_out;
00141   var_sct **var_out;
00142   var_sct **var_prc;
00143   var_sct **var_prc_out;
00144   
00145   static struct option opt_lng[]=
00146     { /* Structure ordered by short option key if possible */
00147       /* Long options with no argument, no short option counterpart */
00148       /* Long options with argument, no short option counterpart */
00149       {"fl_fmt",required_argument,0,0},
00150       {"file_format",required_argument,0,0},
00151       /* Long options with short counterparts */
00152       {"4",no_argument,0,'4'},
00153       {"64bit",no_argument,0,'4'},
00154       {"netcdf4",no_argument,0,'4'},
00155       {"append",no_argument,0,'A'},
00156       {"coords",no_argument,0,'c'},
00157       {"crd",no_argument,0,'c'},
00158       {"no-coords",no_argument,0,'C'},
00159       {"no-crd",no_argument,0,'C'},
00160       {"debug",required_argument,0,'D'},
00161       {"dbg_lvl",required_argument,0,'D'},
00162       {"dimension",required_argument,0,'d'},
00163       {"dmn",required_argument,0,'d'},
00164       {"fortran",no_argument,0,'F'},
00165       {"ftn",no_argument,0,'F'},
00166       {"fl_lst_in",no_argument,0,'H'},
00167       {"file_list",no_argument,0,'H'},
00168       {"history",no_argument,0,'h'},
00169       {"hst",no_argument,0,'h'},
00170       {"local",required_argument,0,'l'},
00171       {"lcl",required_argument,0,'l'},
00172       {"nintap",required_argument,0,'n'},
00173       {"overwrite",no_argument,0,'O'},
00174       {"ovr",no_argument,0,'O'},
00175       {"output",required_argument,0,'o'},
00176       {"fl_out",required_argument,0,'o'},
00177       {"path",required_argument,0,'p'},
00178       {"retain",no_argument,0,'R'},
00179       {"rtn",no_argument,0,'R'},
00180       {"revision",no_argument,0,'r'},
00181       {"thr_nbr",required_argument,0,'t'},
00182       {"threads",required_argument,0,'t'},
00183       {"omp_num_threads",required_argument,0,'t'},
00184       {"variable",required_argument,0,'v'},
00185       {"version",no_argument,0,'r'},
00186       {"vrs",no_argument,0,'r'},
00187       {"exclude",no_argument,0,'x'},
00188       {"xcl",no_argument,0,'x'},
00189       {"help",no_argument,0,'?'},
00190       {0,0,0,0}
00191     }; /* end opt_lng */
00192   int opt_idx=0; /* Index of current long option into opt_lng array */
00193 
00194   /* Start clock and save command line */ 
00195   cmd_ln=nco_cmd_ln_sng(argc,argv);
00196   time_crr_time_t=time((time_t *)NULL);
00197   time_bfr_srt=ctime(&time_crr_time_t); time_bfr_srt=time_bfr_srt; /* Avoid compiler warning until variable is used for something */
00198   
00199   /* Get program name and set program enum (e.g., prg=ncra) */
00200   prg_nm=prg_prs(argv[0],&prg);
00201 
00202   /* Parse command line arguments */
00203   while(1){
00204     /* getopt_long_only() allows one dash to prefix long options */
00205     opt=getopt_long(argc,argv,opt_sht_lst,opt_lng,&opt_idx);
00206     /* NB: access to opt_crr is only valid when long_opt is detected */
00207     if(opt == EOF) break; /* Parse positional arguments once getopt_long() returns EOF */
00208     opt_crr=(char *)strdup(opt_lng[opt_idx].name);
00209 
00210     /* Process long options without short option counterparts */
00211     if(opt == 0){
00212       if(!strcmp(opt_crr,"fl_fmt") || !strcmp(opt_crr,"file_format")) rcd=nco_create_mode_prs(optarg,&fl_out_fmt);
00213     } /* opt != 0 */
00214     /* Process short options */
00215     switch(opt){
00216     case 0: /* Long options have already been processed, return */
00217       break;
00218     case '4': /* [flg] Catch-all to prescribe output storage format */
00219       if(!strcmp(opt_crr,"64bit")) fl_out_fmt=NC_FORMAT_64BIT; else fl_out_fmt=NC_FORMAT_NETCDF4; 
00220       break;
00221     case 'A': /* Toggle FORCE_APPEND */
00222       FORCE_APPEND=!FORCE_APPEND;
00223       break;
00224     case 'C': /* Extract all coordinates associated with extracted variables? */
00225       EXTRACT_ASSOCIATED_COORDINATES=False;
00226       break;
00227     case 'c':
00228       EXTRACT_ALL_COORDINATES=True;
00229       break;
00230     case 'D': /* Debugging level. Default is 0. */
00231       dbg_lvl=(unsigned short)strtol(optarg,(char **)NULL,10);
00232       break;
00233     case 'd': /* Copy argument for later processing */
00234       lmt_arg[lmt_nbr]=(char *)strdup(optarg);
00235       lmt_nbr++;
00236       break;
00237     case 'F': /* Toggle index convention. Default is 0-based arrays (C-style). */
00238       FORTRAN_IDX_CNV=!FORTRAN_IDX_CNV;
00239       break;
00240     case 'H': /* Toggle writing input file list attribute */
00241       FL_LST_IN_APPEND=!FL_LST_IN_APPEND;
00242       break;
00243     case 'h': /* Toggle appending to history global attribute */
00244       HISTORY_APPEND=!HISTORY_APPEND;
00245       break;
00246     case 'l': /* Local path prefix for files retrieved from remote file system */
00247       fl_pth_lcl=(char *)strdup(optarg);
00248       break;
00249     case 'n': /* NINTAP-style abbreviation of files to process */
00250       fl_lst_abb=lst_prs_2D(optarg,",",&abb_arg_nbr);
00251       if(abb_arg_nbr < 1 || abb_arg_nbr > 5){
00252         (void)fprintf(stdout,"%s: ERROR Incorrect abbreviation for file list\n",prg_nm);
00253         (void)nco_usg_prn();
00254         nco_exit(EXIT_FAILURE);
00255       } /* end if */
00256       break;
00257     case 'O': /* Toggle FORCE_OVERWRITE */
00258       FORCE_OVERWRITE=!FORCE_OVERWRITE;
00259       break;
00260     case 'o': /* Name of output file */
00261       fl_out=(char *)strdup(optarg);
00262       break;
00263     case 'p': /* Common file path */
00264       fl_pth=(char *)strdup(optarg);
00265       break;
00266     case 'R': /* Toggle removal of remotely-retrieved-files. Default is True. */
00267       REMOVE_REMOTE_FILES_AFTER_PROCESSING=!REMOVE_REMOTE_FILES_AFTER_PROCESSING;
00268       break;
00269     case 'r': /* Print CVS program information and copyright notice */
00270       (void)copyright_prn(CVS_Id,CVS_Revision);
00271       (void)nco_lbr_vrs_prn();
00272       nco_exit(EXIT_SUCCESS);
00273       break;
00274     case 't': /* Thread number */
00275       thr_nbr=(int)strtol(optarg,(char **)NULL,10);
00276       break;
00277     case 'v': /* Variables to extract/exclude */
00278       /* Replace commas with hashes when within braces (convert back later) */
00279       optarg_lcl=(char *)strdup(optarg);
00280       (void)nco_lst_comma2hash(optarg_lcl);
00281       var_lst_in=lst_prs_2D(optarg_lcl,",",&var_lst_in_nbr);
00282       optarg_lcl=(char *)nco_free(optarg_lcl);
00283       nbr_xtr=var_lst_in_nbr;
00284       break;
00285     case 'x': /* Exclude rather than extract variables specified with -v */
00286       EXCLUDE_INPUT_LIST=True;
00287       break;
00288     case '?': /* Print proper usage */
00289       (void)nco_usg_prn();
00290       nco_exit(EXIT_SUCCESS);
00291       break;
00292     case '-': /* Long options are not allowed */
00293       (void)fprintf(stderr,"%s: ERROR Long options are not available in this build. Use single letter options instead.\n",prg_nm_get());
00294       nco_exit(EXIT_FAILURE);
00295       break;
00296     default: /* Print proper usage */
00297       (void)nco_usg_prn();
00298       nco_exit(EXIT_FAILURE);
00299       break;
00300     } /* end switch */
00301     if(opt_crr != NULL) opt_crr=(char *)nco_free(opt_crr);
00302   } /* end while loop */
00303   
00304   /* Process positional arguments and fill in filenames */
00305   fl_lst_in=nco_fl_lst_mk(argv,argc,optind,&fl_nbr,&fl_out,&FL_LST_IN_FROM_STDIN);
00306 
00307   /* Make uniform list of user-specified dimension limits */
00308   lmt=nco_lmt_prs(lmt_nbr,lmt_arg);
00309     
00310   /* Initialize thread information */
00311   thr_nbr=nco_openmp_ini(thr_nbr);
00312   in_id_arr=(int *)nco_malloc(thr_nbr*sizeof(int));
00313 
00314   /* Parse filename */
00315   fl_in=nco_fl_nm_prs(fl_in,0,&fl_nbr,fl_lst_in,abb_arg_nbr,fl_lst_abb,fl_pth);
00316   /* Make sure file is on local system and is readable or die trying */
00317   fl_in=nco_fl_mk_lcl(fl_in,fl_pth_lcl,&FILE_RETRIEVED_FROM_REMOTE_LOCATION);
00318   /* Open file for reading */
00319   rcd=nco_open(fl_in,NC_NOWRITE,&in_id);
00320   
00321   /* Get number of variables, dimensions, and record dimension ID of input file */
00322   (void)nco_inq(in_id,&nbr_dmn_fl,&nbr_var_fl,(int *)NULL,&rec_dmn_id);
00323   
00324   /* Form initial extraction list which may include extended regular expressions */
00325   xtr_lst=nco_var_lst_mk(in_id,nbr_var_fl,var_lst_in,EXTRACT_ALL_COORDINATES,&nbr_xtr);
00326 
00327   /* Change included variables to excluded variables */
00328   if(EXCLUDE_INPUT_LIST) xtr_lst=nco_var_lst_xcl(in_id,nbr_var_fl,xtr_lst,&nbr_xtr);
00329 
00330   /* Add all coordinate variables to extraction list */
00331   if(EXTRACT_ALL_COORDINATES) xtr_lst=nco_var_lst_add_crd(in_id,nbr_dmn_fl,xtr_lst,&nbr_xtr);
00332 
00333   /* Make sure coordinates associated extracted variables are also on extraction list */
00334   if(EXTRACT_ASSOCIATED_COORDINATES) xtr_lst=nco_var_lst_ass_crd_add(in_id,xtr_lst,&nbr_xtr);
00335 
00336   /* Sort extraction list by variable ID for fastest I/O */
00337   if(nbr_xtr > 1) xtr_lst=nco_lst_srt_nm_id(xtr_lst,nbr_xtr,False);
00338     
00339   /* We now have final list of variables to extract. Phew. */
00340   
00341   /* Find coordinate/dimension values associated with user-specified limits
00342      NB: nco_lmt_evl() with same nc_id contains OpenMP critical region */
00343   for(idx=0;idx<lmt_nbr;idx++) (void)nco_lmt_evl(in_id,lmt[idx],0L,FORTRAN_IDX_CNV);
00344   
00345   /* Find dimensions associated with variables to be extracted */
00346   dmn_lst=nco_dmn_lst_ass_var(in_id,xtr_lst,nbr_xtr,&nbr_dmn_xtr);
00347 
00348   /* Fill in dimension structure for all extracted dimensions */
00349   dim=(dmn_sct **)nco_malloc(nbr_dmn_xtr*sizeof(dmn_sct *));
00350   for(idx=0;idx<nbr_dmn_xtr;idx++) dim[idx]=nco_dmn_fll(in_id,dmn_lst[idx].id,dmn_lst[idx].nm);
00351   /* Dimension list no longer needed */
00352   dmn_lst=nco_nm_id_lst_free(dmn_lst,nbr_dmn_xtr);
00353   
00354   /* Merge hyperslab limit information into dimension structures */
00355   if(lmt_nbr > 0) (void)nco_dmn_lmt_mrg(dim,nbr_dmn_xtr,lmt,lmt_nbr);
00356 
00357   /* Duplicate input dimension structures for output dimension structures */
00358   dmn_out=(dmn_sct **)nco_malloc(nbr_dmn_xtr*sizeof(dmn_sct *));
00359   for(idx=0;idx<nbr_dmn_xtr;idx++){
00360     dmn_out[idx]=nco_dmn_dpl(dim[idx]);
00361     (void)nco_dmn_xrf(dim[idx],dmn_out[idx]); 
00362   } /* end loop over idx */
00363 
00364   /* Is this an CCM/CCSM/CF-format history tape? */
00365   CNV_CCM_CCSM_CF=nco_cnv_ccm_ccsm_cf_inq(in_id);
00366 
00367   /* Fill in variable structure list for all extracted variables */
00368   var=(var_sct **)nco_malloc(nbr_xtr*sizeof(var_sct *));
00369   var_out=(var_sct **)nco_malloc(nbr_xtr*sizeof(var_sct *));
00370   for(idx=0;idx<nbr_xtr;idx++){
00371     var[idx]=nco_var_fll(in_id,xtr_lst[idx].id,xtr_lst[idx].nm,dim,nbr_dmn_xtr);
00372     var_out[idx]=nco_var_dpl(var[idx]);
00373     (void)nco_xrf_var(var[idx],var_out[idx]);
00374     (void)nco_xrf_dmn(var_out[idx]);
00375   } /* end loop over idx */
00376   /* Extraction list no longer needed */
00377   xtr_lst=nco_nm_id_lst_free(xtr_lst,nbr_xtr);
00378 
00379   /* Divide variable lists into lists of fixed variables and variables to be processed */
00380   (void)nco_var_lst_dvd(var,var_out,nbr_xtr,CNV_CCM_CCSM_CF,nco_pck_plc_nil,nco_pck_map_nil,(dmn_sct **)NULL,0,&var_fix,&var_fix_out,&nbr_var_fix,&var_prc,&var_prc_out,&nbr_var_prc);
00381 
00382   /* Open output file */
00383   fl_out_tmp=nco_fl_out_open(fl_out,FORCE_APPEND,FORCE_OVERWRITE,fl_out_fmt,&out_id);
00384 
00385   /* Copy global attributes */
00386   (void)nco_att_cpy(in_id,out_id,NC_GLOBAL,NC_GLOBAL,True);
00387   
00388   /* Catenate time-stamped command line to "history" global attribute */
00389   if(HISTORY_APPEND) (void)nco_hst_att_cat(out_id,cmd_ln);
00390 
00391   /* Add input file list global attribute */
00392   if(FL_LST_IN_APPEND  && HISTORY_APPEND && FL_LST_IN_FROM_STDIN) (void)nco_fl_lst_att_cat(out_id,fl_lst_in,fl_nbr);
00393 
00394   /* ncecat-specific operations */
00395   if(True){
00396 
00397     /* Always construct new "record" dimension from scratch */
00398     rec_dmn=(dmn_sct *)nco_malloc(sizeof(dmn_sct));
00399     rec_dmn->nm=(char *)strdup("record");
00400     rec_dmn->id=-1;
00401     rec_dmn->nc_id=-1;
00402     rec_dmn->xrf=NULL;
00403     rec_dmn->val.vp=NULL;
00404     rec_dmn->is_crd_dmn=False;
00405     rec_dmn->is_rec_dmn=True;
00406     rec_dmn->sz=0L;
00407     rec_dmn->cnt=0L;
00408     rec_dmn->srt=0L;
00409     rec_dmn->end=rec_dmn->sz-1L;
00410       
00411     /* Change existing record dimension, if any, to regular dimension */
00412     for(idx=0;idx<nbr_dmn_xtr;idx++){
00413       /* Is any input dimension a record dimension? */
00414       if(dmn_out[idx]->is_rec_dmn){
00415         dmn_out[idx]->is_rec_dmn=False;
00416         break;
00417       } /* end if */
00418     } /* end loop over idx */
00419 
00420     /* Add record dimension to end of dimension list */
00421     nbr_dmn_xtr++;
00422     dmn_out=(dmn_sct **)nco_realloc(dmn_out,nbr_dmn_xtr*sizeof(dmn_sct **));
00423     dmn_out[nbr_dmn_xtr-1]=rec_dmn;
00424 
00425   } /* end if */
00426 
00427   if(thr_nbr > 0 && HISTORY_APPEND) (void)nco_thr_att_cat(out_id,thr_nbr);
00428   
00429   /* Define dimensions in output file */
00430   (void)nco_dmn_dfn(fl_out,out_id,dmn_out,nbr_dmn_xtr);
00431 
00432   if(True){
00433     /* Prepend record dimension to beginning of all vectors for processed variables */
00434     for(idx=0;idx<nbr_var_prc;idx++){
00435       var_prc_out[idx]->nbr_dim++;
00436       var_prc_out[idx]->is_rec_var=True;
00437       var_prc_out[idx]->sz_rec=var_prc_out[idx]->sz;
00438       
00439       /* Allocate space to hold dimension IDs */
00440       var_prc_out[idx]->dim=(dmn_sct **)nco_realloc(var_prc_out[idx]->dim,var_prc_out[idx]->nbr_dim*sizeof(dmn_sct *));
00441       var_prc_out[idx]->dmn_id=(int *)nco_realloc(var_prc_out[idx]->dmn_id,var_prc_out[idx]->nbr_dim*sizeof(int));
00442       var_prc_out[idx]->cnt=(long *)nco_realloc(var_prc_out[idx]->cnt,var_prc_out[idx]->nbr_dim*sizeof(long));
00443       var_prc_out[idx]->srt=(long *)nco_realloc(var_prc_out[idx]->srt,var_prc_out[idx]->nbr_dim*sizeof(long));
00444       var_prc_out[idx]->end=(long *)nco_realloc(var_prc_out[idx]->end,var_prc_out[idx]->nbr_dim*sizeof(long));
00445       
00446       /* Move current array by one to make room for new record dimension info */
00447       (void)memmove((void *)(var_prc_out[idx]->dim+1),(void *)(var_prc_out[idx]->dim),(var_prc_out[idx]->nbr_dim-1)*sizeof(dmn_sct *));
00448       (void)memmove((void *)(var_prc_out[idx]->dmn_id+1),(void *)(var_prc_out[idx]->dmn_id),(var_prc_out[idx]->nbr_dim-1)*sizeof(int));
00449       (void)memmove((void *)(var_prc_out[idx]->cnt+1),(void *)(var_prc_out[idx]->cnt),(var_prc_out[idx]->nbr_dim-1)*sizeof(long));
00450       (void)memmove((void *)(var_prc_out[idx]->srt+1),(void *)(var_prc_out[idx]->srt),(var_prc_out[idx]->nbr_dim-1)*sizeof(long));
00451       (void)memmove((void *)(var_prc_out[idx]->end+1),(void *)(var_prc_out[idx]->end),(var_prc_out[idx]->nbr_dim-1)*sizeof(long));
00452       
00453       /* Insert value for new record dimension */
00454       var_prc_out[idx]->dim[0]=rec_dmn;
00455       var_prc_out[idx]->dmn_id[0]=rec_dmn->id;
00456       var_prc_out[idx]->cnt[0]=1L;
00457       var_prc_out[idx]->srt[0]=-1L;
00458       var_prc_out[idx]->end[0]=-1L;
00459                     
00460     } /* end loop over idx */
00461     
00462   } /* end if */
00463 
00464   /* Define variables in output file, copy their attributes */
00465   (void)nco_var_dfn(in_id,fl_out,out_id,var_out,nbr_xtr,(dmn_sct **)NULL,(int)0,nco_pck_plc_nil,nco_pck_map_nil);
00466 
00467   /* Turn off default filling behavior to enhance efficiency */
00468   rcd=nco_set_fill(out_id,NC_NOFILL,&fll_md_old);
00469   
00470   /* Take output file out of define mode */
00471   (void)nco_enddef(out_id);
00472   
00473   /* Zero start vectors for all output variables */
00474   (void)nco_var_srt_zero(var_out,nbr_xtr);
00475 
00476   /* Copy variable data for non-processed variables */
00477   (void)nco_var_val_cpy(in_id,out_id,var_fix,nbr_var_fix);
00478 
00479   /* Close first input netCDF file */
00480   (void)nco_close(in_id);
00481   
00482   /* Loop over input files */
00483   for(fl_idx=0;fl_idx<fl_nbr;fl_idx++){
00484     /* Parse filename */
00485     if(fl_idx != 0) fl_in=nco_fl_nm_prs(fl_in,fl_idx,(int *)NULL,fl_lst_in,abb_arg_nbr, fl_lst_abb,fl_pth);
00486     if(dbg_lvl > 0) (void)fprintf(fp_stderr,"\nInput file %d is %s; ",fl_idx,fl_in);
00487     /* Make sure file is on local system and is readable or die trying */
00488     if(fl_idx != 0) fl_in=nco_fl_mk_lcl(fl_in,fl_pth_lcl,&FILE_RETRIEVED_FROM_REMOTE_LOCATION);
00489     if(dbg_lvl > 0) (void)fprintf(fp_stderr,"local file %s:\n",fl_in);
00490     
00491     /* Open file once per thread to improve caching */
00492     for(thr_idx=0;thr_idx<thr_nbr;thr_idx++) rcd=nco_open(fl_in,NC_NOWRITE,in_id_arr+thr_idx);
00493     
00494     /* Perform various error-checks on input file */
00495     if(False) (void)nco_fl_cmp_err_chk();
00496 
00497     /* OpenMP with threading over variables, not files */
00498 #ifdef _OPENMP
00499 #pragma omp parallel for default(none) private(idx,in_id) shared(dbg_lvl,fl_nbr,idx_rec_out,in_id_arr,nbr_var_prc,out_id,var_prc,var_prc_out)
00500 #endif /* !_OPENMP */
00501     /* Process all variables in current file */
00502     for(idx=0;idx<nbr_var_prc;idx++){
00503       in_id=in_id_arr[omp_get_thread_num()];
00504       if(dbg_lvl > 1) (void)fprintf(fp_stderr,"%s, ",var_prc[idx]->nm);
00505       if(dbg_lvl > 0) (void)fflush(fp_stderr);
00506       /* Variables may have different ID, missing_value, type, in each file */
00507       (void)nco_var_mtd_refresh(in_id,var_prc[idx]);
00508       /* Retrieve variable from disk into memory */
00509       /* NB: nco_var_get() with same nc_id contains OpenMP critical region */
00510       (void)nco_var_get(in_id,var_prc[idx]);
00511       /* Size of record dimension is 1 in output file */
00512       var_prc_out[idx]->cnt[0]=1L;
00513       var_prc_out[idx]->srt[0]=idx_rec_out;
00514       /* Write variable into current record in output file */
00515 #ifdef _OPENMP
00516 #pragma omp critical
00517 #endif /* _OPENMP */
00518       { /* begin OpenMP critical */
00519         if(var_prc[idx]->nbr_dim == 0){
00520           (void)nco_put_var1(out_id,var_prc_out[idx]->id,var_prc_out[idx]->srt,var_prc[idx]->val.vp,var_prc[idx]->type);
00521         }else{ /* end if variable is a scalar */
00522           (void)nco_put_vara(out_id,var_prc_out[idx]->id,var_prc_out[idx]->srt,var_prc_out[idx]->cnt,var_prc[idx]->val.vp,var_prc[idx]->type);
00523         } /* end if variable is array */
00524         /* Free current input buffer */
00525         var_prc[idx]->val.vp=nco_free(var_prc[idx]->val.vp);
00526       } /* end OpenMP critical */
00527       
00528     } /* end (OpenMP parallel for) loop over idx */
00529     if(dbg_lvl > 1) (void)fprintf(stderr,"\n");
00530 
00531     idx_rec_out++; /* [idx] Index of current record in output file (0 is first, ...) */
00532     
00533     /* Close input netCDF file */
00534     for(thr_idx=0;thr_idx<thr_nbr;thr_idx++) nco_close(in_id_arr[thr_idx]);
00535 
00536     /* Remove local copy of file */
00537     if(FILE_RETRIEVED_FROM_REMOTE_LOCATION && REMOVE_REMOTE_FILES_AFTER_PROCESSING) (void)nco_fl_rm(fl_in);
00538     
00539   } /* end loop over fl_idx */
00540   
00541   /* Close output file and move it from temporary to permanent location */
00542   (void)nco_fl_out_cls(fl_out,fl_out_tmp,out_id);
00543   
00544   /* ncecat-specific memory cleanup */
00545   
00546   /* NCO-generic clean-up */
00547   /* Free individual strings/arrays */
00548   if(cmd_ln != NULL) cmd_ln=(char *)nco_free(cmd_ln);
00549   if(fl_in != NULL) fl_in=(char *)nco_free(fl_in);
00550   if(fl_out != NULL) fl_out=(char *)nco_free(fl_out);
00551   if(fl_out_tmp != NULL) fl_out_tmp=(char *)nco_free(fl_out_tmp);
00552   if(fl_pth != NULL) fl_pth=(char *)nco_free(fl_pth);
00553   if(fl_pth_lcl != NULL) fl_pth_lcl=(char *)nco_free(fl_pth_lcl);
00554   if(in_id_arr != NULL) in_id_arr=(int *)nco_free(in_id_arr);
00555   /* Free lists of strings */
00556   if(fl_lst_in != NULL && fl_lst_abb == NULL) fl_lst_in=nco_sng_lst_free(fl_lst_in,fl_nbr); 
00557   if(fl_lst_in != NULL && fl_lst_abb != NULL) fl_lst_in=nco_sng_lst_free(fl_lst_in,1);
00558   if(fl_lst_abb != NULL) fl_lst_abb=nco_sng_lst_free(fl_lst_abb,abb_arg_nbr);
00559   if(var_lst_in_nbr > 0) var_lst_in=nco_sng_lst_free(var_lst_in,var_lst_in_nbr);
00560   /* Free limits */
00561   for(idx=0;idx<lmt_nbr;idx++) lmt_arg[idx]=(char *)nco_free(lmt_arg[idx]);
00562   if(lmt_nbr > 0) lmt=nco_lmt_lst_free(lmt,lmt_nbr);
00563   /* Free dimension lists */
00564   if(nbr_dmn_xtr > 0) dim=nco_dmn_lst_free(dim,nbr_dmn_xtr-1); /* NB: ncecat has one fewer input than output dimension */
00565   if(nbr_dmn_xtr > 0) dmn_out=nco_dmn_lst_free(dmn_out,nbr_dmn_xtr); 
00566   /* Free variable lists */
00567   if(nbr_xtr > 0) var=nco_var_lst_free(var,nbr_xtr);
00568   if(nbr_xtr > 0) var_out=nco_var_lst_free(var_out,nbr_xtr);
00569   var_prc=(var_sct **)nco_free(var_prc);
00570   var_prc_out=(var_sct **)nco_free(var_prc_out);
00571   var_fix=(var_sct **)nco_free(var_fix);
00572   var_fix_out=(var_sct **)nco_free(var_fix_out);
00573  
00574   if(rcd != NC_NOERR) nco_err_exit(rcd,"main");
00575   nco_exit_gracefully();
00576   return EXIT_SUCCESS;
00577 } /* end main() */


Generated on Thu Mar 16 18:14:52 2006 for nco by  doxygen 1.4.4