#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 mpncflint.c:

Go to the source code of this file.
Defines | |
| #define | MAIN_PROGRAM_FILE |
Functions | |
| int | main (int argc, char **argv) |
|
|
Definition at line 67 of file mpncflint.c. |
|
||||||||||||
|
Definition at line 71 of file mpncflint.c. References copyright_prn(), val_unn::d, double_CEWI, ptr_unn::dp, EXIT_FAILURE, EXIT_SUCCESS, False, FILE, getopt_long, var_sct_tag::has_mss_val, var_sct_tag::id, idx_all_wrk_ass, int_CEWI, lst_prs_2D(), msg_bfr_lng, msg_tag_tkn_wrt_rqs, msg_tag_tkn_wrt_rsp, msg_tag_wrk_rqs, msg_tag_wrk_rsp, var_sct_tag::mss_val, option::name, var_sct_tag::nbr_dim, NC_DOUBLE, NC_FORMAT_64BIT, NC_FORMAT_CLASSIC, NC_FORMAT_NETCDF4, NC_GLOBAL, NC_MAX_DIMS, NC_NOERR, NC_NOFILL, NC_NOWRITE, NC_SHARE, NC_WRITE, nco_att_cpy(), nco_bool, nco_close(), nco_cmd_ln_sng(), nco_cnt_run(), 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_mk(), nco_fl_mk_lcl(), nco_fl_mv(), nco_fl_nm_prs(), nco_fl_out_cls(), nco_fl_out_open(), nco_fl_rm(), nco_free(), nco_hst_att_cat(), nco_inq(), nco_inq_varid(), 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_mpi_att_cat(), nco_mss_val_cnf(), 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_set_fill(), nco_sng_lst_free(), nco_spn_lck_brk, nco_spn_lck_us, nco_thr_att_cat(), nco_usg_prn(), nco_var_add_tll_ncflint(), nco_var_cnf_dmn(), nco_var_cnf_typ(), nco_var_dfn(), nco_var_dpl(), nco_var_dvd(), nco_var_fll(), nco_var_free(), 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_mlt(), nco_var_mtd_refresh(), nco_var_sbt(), nco_var_srt_zero(), nco_var_val_cpy(), nco_xrf_dmn(), nco_xrf_var(), nco_zero_long(), no_argument, NULL_CEWI, omp_get_thread_num(), optarg, optind, prg_nm_get(), prg_prs(), required_argument, rnk_mgr, scl_mk_var(), var_sct_tag::sz, var_sct_tag::tally, tkn_wrt_rqs_dny, tkn_wrt_rqs_ntv, tkn_wrt_rqs_xcp, True, type, var_sct_tag::type, option::val, var_sct_tag::val, and wrk_id_bfr_lng. 00072 { 00073 nco_bool CMD_LN_NTP_VAR=False; /* Option i */ 00074 nco_bool CMD_LN_NTP_WGT=True; /* Option w */ 00075 nco_bool DO_CONFORM=False; /* Did nco_var_cnf_dmn() find truly conforming variables? */ 00076 nco_bool EXCLUDE_INPUT_LIST=False; /* Option c */ 00077 nco_bool EXTRACT_ALL_COORDINATES=False; /* Option c */ 00078 nco_bool EXTRACT_ASSOCIATED_COORDINATES=True; /* Option C */ 00079 nco_bool FILE_1_RETRIEVED_FROM_REMOTE_LOCATION; 00080 nco_bool FILE_2_RETRIEVED_FROM_REMOTE_LOCATION; 00081 nco_bool FL_LST_IN_FROM_STDIN=False; /* [flg] fl_lst_in comes from stdin */ 00082 nco_bool FORCE_APPEND=False; /* Option A */ 00083 nco_bool FORCE_OVERWRITE=False; /* Option O */ 00084 nco_bool FORTRAN_IDX_CNV=False; /* Option F */ 00085 nco_bool HISTORY_APPEND=True; /* Option h */ 00086 nco_bool MUST_CONFORM=False; /* Must nco_var_cnf_dmn() find truly conforming variables? */ 00087 nco_bool CNV_CCM_CCSM_CF; 00088 nco_bool REMOVE_REMOTE_FILES_AFTER_PROCESSING=True; /* Option R */ 00089 00090 char **fl_lst_abb=NULL; /* Option a */ 00091 char **fl_lst_in; 00092 char **ntp_lst_in; 00093 char **var_lst_in=NULL_CEWI; 00094 char *cmd_ln; 00095 char *fl_in_1=NULL; /* fl_in_1 is nco_realloc'd when not NULL */; 00096 char *fl_in_2=NULL; /* fl_in_2 is nco_realloc'd when not NULL */; 00097 char *fl_out=NULL; /* Option o */ 00098 char *fl_out_tmp=NULL; /* MPI CEWI */ 00099 char *fl_pth=NULL; /* Option p */ 00100 char *fl_pth_lcl=NULL; /* Option l */ 00101 char *lmt_arg[NC_MAX_DIMS]; 00102 char *ntp_nm=NULL; /* Option i */ 00103 char *opt_crr=NULL; /* [sng] String representation of current long-option name */ 00104 char *optarg_lcl=NULL; /* [sng] Local copy of system optarg */ 00105 char *time_bfr_srt; 00106 00107 const char * const CVS_Id="$Id: mpncflint.c,v 1.35 2006/02/26 07:41:55 zender Exp $"; 00108 const char * const CVS_Revision="$Revision: 1.35 $"; 00109 const char * const opt_sht_lst="4ACcD:d:Fhi:l:Oo:p:rRSt:v:xw:-:"; 00110 00111 dmn_sct **dim; 00112 dmn_sct **dmn_out; 00113 00114 double ntp_val_out=double_CEWI; /* Option i */ 00115 double wgt_val_1=0.5; /* Option w */ 00116 double wgt_val_2=0.5; /* Option w */ 00117 00118 extern char *optarg; 00119 extern int optind; 00120 00121 /* Using naked stdin/stdout/stderr in parallel region generates warning 00122 Copy appropriate filehandle to variable scoped shared in parallel clause */ 00123 FILE * const fp_stderr=stderr; /* [fl] stderr filehandle CEWI */ 00124 FILE * const fp_stdout=stdout; /* [fl] stdout filehandle CEWI */ 00125 00126 int *in_id_1_arr; 00127 int *in_id_2_arr; 00128 00129 int abb_arg_nbr=0; 00130 int fl_idx; 00131 int fl_nbr=0; 00132 int fl_out_fmt=NC_FORMAT_CLASSIC; /* [enm] Output file format */ 00133 int fll_md_old; /* [enm] Old fill mode */ 00134 int has_mss_val=False; 00135 int idx; 00136 int in_id_1; 00137 int in_id_2; 00138 int lmt_nbr=0; /* Option d. NB: lmt_nbr gets incremented */ 00139 int nbr_dmn_fl; 00140 int nbr_dmn_xtr; 00141 int nbr_ntp; 00142 int nbr_var_fix; /* nbr_var_fix gets incremented */ 00143 int nbr_var_fl; 00144 int nbr_var_prc; /* nbr_var_prc gets incremented */ 00145 int nbr_xtr=0; /* nbr_xtr won't otherwise be set for -c with no -v */ 00146 int opt; 00147 int out_id; 00148 int rcd=NC_NOERR; /* [rcd] Return code */ 00149 int thr_idx; /* [idx] Index of current thread */ 00150 int thr_nbr=int_CEWI; /* [nbr] Thread number Option t */ 00151 int var_lst_in_nbr=0; 00152 00153 lmt_sct **lmt; 00154 00155 nm_id_sct *dmn_lst; 00156 nm_id_sct *xtr_lst=NULL; /* xtr_lst may be alloc()'d from NULL with -c option */ 00157 00158 time_t time_crr_time_t; 00159 00160 val_unn val_gnr_unn; /* Generic container for arrival point or weight */ 00161 00162 var_sct *wgt_1=NULL_CEWI; 00163 var_sct *wgt_2=NULL_CEWI; 00164 var_sct *wgt_out_1=NULL; 00165 var_sct *wgt_out_2=NULL; 00166 var_sct **var; 00167 var_sct **var_fix; 00168 var_sct **var_fix_out; 00169 var_sct **var_out; 00170 var_sct **var_prc_1; 00171 var_sct **var_prc_2; 00172 var_sct **var_prc_out; 00173 00174 #ifdef ENABLE_MPI 00175 /* Declare all MPI-specific variables here */ 00176 MPI_Status mpi_stt; /* [enm] Status check to decode msg_tag_typ */ 00177 00178 bool TKN_WRT_FREE=True; /* [flg] Write-access to output file is available */ 00179 00180 const double tkn_wrt_rqs_ntv=0.04; /* [s] Token request interval */ 00181 00182 const int msg_bfr_lng=3; /* [nbr] Number of elements in msg_bfr */ 00183 const int wrk_id_bfr_lng=1; /* [nbr] Number of elements in wrk_id_bfr */ 00184 00185 int fl_nm_lng; /* [nbr] Output file name length */ 00186 int msg_bfr[msg_bfr_lng]; /* [bfr] Buffer containing var, idx, tkn_wrt_rsp */ 00187 int msg_tag_typ; /* [enm] MPI message tag type */ 00188 int prc_rnk; /* [idx] Process rank */ 00189 int prc_nbr=0; /* [nbr] Number of MPI processes */ 00190 int tkn_wrt_rsp; /* [enm] Response to request for write token */ 00191 int var_wrt_nbr=0; /* [nbr] Variables written to output file until now */ 00192 int rnk_wrk; /* [idx] Worker rank */ 00193 int wrk_id_bfr[wrk_id_bfr_lng]; /* [bfr] Buffer for rnk_wrk */ 00194 #endif /* !ENABLE_MPI */ 00195 00196 static struct option opt_lng[]= 00197 { /* Structure ordered by short option key if possible */ 00198 /* Long options with no argument, no short option counterpart */ 00199 /* Long options with argument, no short option counterpart */ 00200 {"fl_fmt",required_argument,0,0}, 00201 {"file_format",required_argument,0,0}, 00202 /* Long options with short counterparts */ 00203 {"4",no_argument,0,'4'}, 00204 {"64bit",no_argument,0,'4'}, 00205 {"netcdf4",no_argument,0,'4'}, 00206 {"append",no_argument,0,'A'}, 00207 {"coords",no_argument,0,'c'}, 00208 {"crd",no_argument,0,'c'}, 00209 {"no-coords",no_argument,0,'C'}, 00210 {"no-crd",no_argument,0,'C'}, 00211 {"debug",required_argument,0,'D'}, 00212 {"dbg_lvl",required_argument,0,'D'}, 00213 {"dimension",required_argument,0,'d'}, 00214 {"dmn",required_argument,0,'d'}, 00215 {"fortran",no_argument,0,'F'}, 00216 {"ftn",no_argument,0,'F'}, 00217 {"history",no_argument,0,'h'}, 00218 {"hst",no_argument,0,'h'}, 00219 {"interpolate",required_argument,0,'i'}, 00220 {"ntp",required_argument,0,'i'}, 00221 {"local",required_argument,0,'l'}, 00222 {"lcl",required_argument,0,'l'}, 00223 {"overwrite",no_argument,0,'O'}, 00224 {"ovr",no_argument,0,'O'}, 00225 {"output",required_argument,0,'o'}, 00226 {"fl_out",required_argument,0,'o'}, 00227 {"path",required_argument,0,'p'}, 00228 {"retain",no_argument,0,'R'}, 00229 {"rtn",no_argument,0,'R'}, 00230 {"revision",no_argument,0,'r'}, 00231 {"suspend", no_argument,0,'S'}, 00232 {"thr_nbr",required_argument,0,'t'}, 00233 {"variable",required_argument,0,'v'}, 00234 {"version",no_argument,0,'r'}, 00235 {"vrs",no_argument,0,'r'}, 00236 {"weight",required_argument,0,'w'}, 00237 {"wgt_var",no_argument,0,'w'}, 00238 {"help",no_argument,0,'?'}, 00239 {0,0,0,0} 00240 }; /* end opt_lng */ 00241 int opt_idx=0; /* Index of current long option into opt_lng array */ 00242 00243 #ifdef ENABLE_MPI 00244 /* MPI Initialization */ 00245 MPI_Init(&argc,&argv); 00246 MPI_Comm_size(MPI_COMM_WORLD,&prc_nbr); 00247 MPI_Comm_rank(MPI_COMM_WORLD,&prc_rnk); 00248 #endif /* !ENABLE_MPI */ 00249 00250 /* Start clock and save command line */ 00251 cmd_ln=nco_cmd_ln_sng(argc,argv); 00252 time_crr_time_t=time((time_t *)NULL); 00253 time_bfr_srt=ctime(&time_crr_time_t); time_bfr_srt=time_bfr_srt; /* Avoid compiler warning until variable is used for something */ 00254 00255 /* Get program name and set program enum (e.g., prg=ncra) */ 00256 prg_nm=prg_prs(argv[0],&prg); 00257 00258 /* Parse command line arguments */ 00259 while(1){ 00260 /* getopt_long_only() allows one dash to prefix long options */ 00261 opt=getopt_long(argc,argv,opt_sht_lst,opt_lng,&opt_idx); 00262 /* NB: access to opt_crr is only valid when long_opt is detected */ 00263 if(opt == EOF) break; /* Parse positional arguments once getopt_long() returns EOF */ 00264 opt_crr=(char *)strdup(opt_lng[opt_idx].name); 00265 00266 /* Process long options without short option counterparts */ 00267 if(opt == 0){ 00268 if(!strcmp(opt_crr,"fl_fmt") || !strcmp(opt_crr,"file_format")) rcd=nco_create_mode_prs(optarg,&fl_out_fmt); 00269 } /* opt != 0 */ 00270 /* Process short options */ 00271 switch(opt){ 00272 case 0: /* Long options have already been processed, return */ 00273 break; 00274 case '4': /* [flg] Catch-all to prescribe output storage format */ 00275 if(!strcmp(opt_crr,"64bit")) fl_out_fmt=NC_FORMAT_64BIT; else fl_out_fmt=NC_FORMAT_NETCDF4; 00276 break; 00277 case 'A': /* Toggle FORCE_APPEND */ 00278 FORCE_APPEND=!FORCE_APPEND; 00279 break; 00280 case 'C': /* Extract all coordinates associated with extracted variables? */ 00281 EXTRACT_ASSOCIATED_COORDINATES=False; 00282 break; 00283 case 'c': 00284 EXTRACT_ALL_COORDINATES=True; 00285 break; 00286 case 'D': /* The debugging level. Default is 0. */ 00287 dbg_lvl=(unsigned short)strtol(optarg,(char **)NULL,10); 00288 break; 00289 case 'd': /* Copy argument for later processing */ 00290 lmt_arg[lmt_nbr]=(char *)strdup(optarg); 00291 lmt_nbr++; 00292 break; 00293 case 'F': /* Toggle index convention. Default is 0-based arrays (C-style). */ 00294 FORTRAN_IDX_CNV=!FORTRAN_IDX_CNV; 00295 break; 00296 case 'h': /* Toggle appending to history global attribute */ 00297 HISTORY_APPEND=!HISTORY_APPEND; 00298 break; 00299 case 'i': 00300 /* Name of variable to guide interpolation. Default is none */ 00301 ntp_lst_in=lst_prs_2D(optarg,",",&nbr_ntp); 00302 if(nbr_ntp > 2){ 00303 (void)fprintf(stdout,"%s: ERROR too many arguments to -i\n",prg_nm_get()); 00304 (void)nco_usg_prn(); 00305 nco_exit(EXIT_FAILURE); 00306 } /* end if */ 00307 ntp_nm=ntp_lst_in[0]; 00308 ntp_val_out=strtod(ntp_lst_in[1],(char **)NULL); 00309 CMD_LN_NTP_VAR=True; 00310 CMD_LN_NTP_WGT=False; 00311 break; 00312 case 'l': /* Local path prefix for files retrieved from remote file system */ 00313 fl_pth_lcl=(char *)strdup(optarg); 00314 break; 00315 case 'O': /* Toggle FORCE_OVERWRITE */ 00316 FORCE_OVERWRITE=!FORCE_OVERWRITE; 00317 break; 00318 case 'o': /* Name of output file */ 00319 fl_out=(char *)strdup(optarg); 00320 break; 00321 case 'p': /* Common file path */ 00322 fl_pth=(char *)strdup(optarg); 00323 break; 00324 case 'R': /* Toggle removal of remotely-retrieved-files. Default is True. */ 00325 REMOVE_REMOTE_FILES_AFTER_PROCESSING=!REMOVE_REMOTE_FILES_AFTER_PROCESSING; 00326 break; 00327 case 'r': /* Print CVS program information and copyright notice */ 00328 (void)copyright_prn(CVS_Id,CVS_Revision); 00329 (void)nco_lbr_vrs_prn(); 00330 nco_exit(EXIT_SUCCESS); 00331 break; 00332 #ifdef ENABLE_MPI 00333 case 'S': /* Suspend with signal handler to facilitate debugging */ 00334 if(signal(SIGUSR1,nco_cnt_run) == SIG_ERR) (void)fprintf(fp_stdout,"%s: ERROR Could not install suspend handler.\n",prg_nm); 00335 while(!nco_spn_lck_brk) usleep(nco_spn_lck_us); /* Spinlock. fxm: should probably insert a sched_yield */ 00336 break; 00337 #endif /* !ENABLE_MPI */ 00338 case 't': /* Thread number */ 00339 thr_nbr=(int)strtol(optarg,(char **)NULL,10); 00340 break; 00341 case 'v': /* Variables to extract/exclude */ 00342 /* Replace commas with hashes when within braces (convert back later) */ 00343 optarg_lcl=(char *)strdup(optarg); 00344 (void)nco_lst_comma2hash(optarg_lcl); 00345 var_lst_in=lst_prs_2D(optarg_lcl,",",&var_lst_in_nbr); 00346 optarg_lcl=(char *)nco_free(optarg_lcl); 00347 nbr_xtr=var_lst_in_nbr; 00348 break; 00349 case 'w': 00350 /* Weight(s) for interpolation. Default is wgt_val_1=wgt_val_2=0.5 */ 00351 ntp_lst_in=lst_prs_2D(optarg,",",&nbr_ntp); 00352 if(nbr_ntp > 2){ 00353 (void)fprintf(stdout,"%s: ERROR too many arguments to -w\n",prg_nm_get()); 00354 (void)nco_usg_prn(); 00355 nco_exit(EXIT_FAILURE); 00356 }else if(nbr_ntp == 2){ 00357 wgt_val_1=strtod(ntp_lst_in[0],(char **)NULL); 00358 wgt_val_2=strtod(ntp_lst_in[1],(char **)NULL); 00359 }else if(nbr_ntp == 1){ 00360 wgt_val_1=strtod(ntp_lst_in[0],(char **)NULL); 00361 wgt_val_2=1.0-wgt_val_1; 00362 } /* end else */ 00363 CMD_LN_NTP_WGT=True; 00364 break; 00365 case 'x': /* Exclude rather than extract variables specified with -v */ 00366 EXCLUDE_INPUT_LIST=True; 00367 break; 00368 case '?': /* Print proper usage */ 00369 (void)nco_usg_prn(); 00370 nco_exit(EXIT_SUCCESS); 00371 break; 00372 case '-': /* Long options are not allowed */ 00373 (void)fprintf(stderr,"%s: ERROR Long options are not available in this build. Use single letter options instead.\n",prg_nm_get()); 00374 nco_exit(EXIT_FAILURE); 00375 break; 00376 default: /* Print proper usage */ 00377 (void)nco_usg_prn(); 00378 nco_exit(EXIT_FAILURE); 00379 break; 00380 } /* end switch */ 00381 if(opt_crr != NULL) opt_crr=(char *)nco_free(opt_crr); 00382 } /* end while loop */ 00383 00384 if(CMD_LN_NTP_VAR && CMD_LN_NTP_WGT){ 00385 (void)fprintf(stdout,"%s: ERROR interpolating variable (-i) and fixed weight(s) (-w) both set\n",prg_nm_get()); 00386 nco_exit(EXIT_FAILURE); 00387 }else if(!CMD_LN_NTP_VAR && !CMD_LN_NTP_WGT){ 00388 (void)fprintf(stdout,"%s: ERROR interpolating variable (-i) or fixed weight(s) (-w) must be set\n",prg_nm_get()); 00389 nco_exit(EXIT_FAILURE); 00390 } /* end else */ 00391 00392 /* Process positional arguments and fill in filenames */ 00393 fl_lst_in=nco_fl_lst_mk(argv,argc,optind,&fl_nbr,&fl_out,&FL_LST_IN_FROM_STDIN); 00394 00395 /* Make uniform list of user-specified dimension limits */ 00396 lmt=nco_lmt_prs(lmt_nbr,lmt_arg); 00397 00398 /* Initialize thread information */ 00399 thr_nbr=nco_openmp_ini(thr_nbr); 00400 in_id_1_arr=(int *)nco_malloc(thr_nbr*sizeof(int)); 00401 in_id_2_arr=(int *)nco_malloc(thr_nbr*sizeof(int)); 00402 00403 /* Parse filenames */ 00404 fl_idx=0; /* Input file _1 */ 00405 fl_in_1=nco_fl_nm_prs(fl_in_1,fl_idx,&fl_nbr,fl_lst_in,abb_arg_nbr,fl_lst_abb,fl_pth); 00406 if(dbg_lvl > 0) (void)fprintf(stderr,"\nInput file %d is %s; ",fl_idx,fl_in_1); 00407 /* Make sure file is on local system and is readable or die trying */ 00408 fl_in_1=nco_fl_mk_lcl(fl_in_1,fl_pth_lcl,&FILE_1_RETRIEVED_FROM_REMOTE_LOCATION); 00409 if(dbg_lvl > 0) (void)fprintf(stderr,"local file %s:\n",fl_in_1); 00410 /* Open file once per thread to improve caching */ 00411 for(thr_idx=0;thr_idx<thr_nbr;thr_idx++) rcd=nco_open(fl_in_1,NC_NOWRITE,in_id_1_arr+thr_idx); 00412 in_id_1=in_id_1_arr[0]; 00413 00414 fl_idx=1; /* Input file _2 */ 00415 fl_in_2=nco_fl_nm_prs(fl_in_2,fl_idx,&fl_nbr,fl_lst_in,abb_arg_nbr,fl_lst_abb,fl_pth); 00416 if(dbg_lvl > 0) (void)fprintf(stderr,"\nInput file %d is %s; ",fl_idx,fl_in_2); 00417 /* Make sure file is on local system and is readable or die trying */ 00418 fl_in_2=nco_fl_mk_lcl(fl_in_2,fl_pth_lcl,&FILE_2_RETRIEVED_FROM_REMOTE_LOCATION); 00419 if(dbg_lvl > 0) (void)fprintf(stderr,"local file %s:\n",fl_in_2); 00420 /* Open file once per thread to improve caching */ 00421 for(thr_idx=0;thr_idx<thr_nbr;thr_idx++) rcd=nco_open(fl_in_2,NC_NOWRITE,in_id_2_arr+thr_idx); 00422 in_id_2=in_id_2_arr[0]; 00423 00424 /* Get number of variables and dimensions in file */ 00425 (void)nco_inq(in_id_1,&nbr_dmn_fl,&nbr_var_fl,(int *)NULL,(int *)NULL); 00426 00427 /* Form initial extraction list which may include extended regular expressions */ 00428 xtr_lst=nco_var_lst_mk(in_id_1,nbr_var_fl,var_lst_in,EXTRACT_ALL_COORDINATES,&nbr_xtr); 00429 00430 /* Change included variables to excluded variables */ 00431 if(EXCLUDE_INPUT_LIST) xtr_lst=nco_var_lst_xcl(in_id_1,nbr_var_fl,xtr_lst,&nbr_xtr); 00432 00433 /* Add all coordinate variables to extraction list */ 00434 if(EXTRACT_ALL_COORDINATES) xtr_lst=nco_var_lst_add_crd(in_id_1,nbr_dmn_fl,xtr_lst,&nbr_xtr); 00435 00436 /* Make sure coordinates associated extracted variables are also on extraction list */ 00437 if(EXTRACT_ASSOCIATED_COORDINATES) xtr_lst=nco_var_lst_ass_crd_add(in_id_1,xtr_lst,&nbr_xtr); 00438 00439 /* Sort extraction list by variable ID for fastest I/O */ 00440 if(nbr_xtr > 1) xtr_lst=nco_lst_srt_nm_id(xtr_lst,nbr_xtr,False); 00441 00442 /* We now have final list of variables to extract. Phew. */ 00443 00444 /* Find coordinate/dimension values associated with user-specified limits 00445 NB: nco_lmt_evl() with same nc_id contains OpenMP critical region */ 00446 for(idx=0;idx<lmt_nbr;idx++) (void)nco_lmt_evl(in_id_1,lmt[idx],0L,FORTRAN_IDX_CNV); 00447 00448 /* Find dimensions associated with variables to be extracted */ 00449 dmn_lst=nco_dmn_lst_ass_var(in_id_1,xtr_lst,nbr_xtr,&nbr_dmn_xtr); 00450 00451 /* Fill in dimension structure for all extracted dimensions */ 00452 dim=(dmn_sct **)nco_malloc(nbr_dmn_xtr*sizeof(dmn_sct *)); 00453 for(idx=0;idx<nbr_dmn_xtr;idx++) dim[idx]=nco_dmn_fll(in_id_1,dmn_lst[idx].id,dmn_lst[idx].nm); 00454 /* Dimension list no longer needed */ 00455 dmn_lst=nco_nm_id_lst_free(dmn_lst,nbr_dmn_xtr); 00456 00457 /* Merge hyperslab limit information into dimension structures */ 00458 if(lmt_nbr > 0) (void)nco_dmn_lmt_mrg(dim,nbr_dmn_xtr,lmt,lmt_nbr); 00459 00460 /* Duplicate input dimension structures for output dimension structures */ 00461 dmn_out=(dmn_sct **)nco_malloc(nbr_dmn_xtr*sizeof(dmn_sct *)); 00462 for(idx=0;idx<nbr_dmn_xtr;idx++){ 00463 dmn_out[idx]=nco_dmn_dpl(dim[idx]); 00464 (void)nco_dmn_xrf(dim[idx],dmn_out[idx]); 00465 } /* end loop over idx */ 00466 00467 /* Is this an CCM/CCSM/CF-format history tape? */ 00468 CNV_CCM_CCSM_CF=nco_cnv_ccm_ccsm_cf_inq(in_id_1); 00469 00470 /* Fill in variable structure list for all extracted variables */ 00471 var=(var_sct **)nco_malloc(nbr_xtr*sizeof(var_sct *)); 00472 var_out=(var_sct **)nco_malloc(nbr_xtr*sizeof(var_sct *)); 00473 for(idx=0;idx<nbr_xtr;idx++){ 00474 var[idx]=nco_var_fll(in_id_1,xtr_lst[idx].id,xtr_lst[idx].nm,dim,nbr_dmn_xtr); 00475 var_out[idx]=nco_var_dpl(var[idx]); 00476 (void)nco_xrf_var(var[idx],var_out[idx]); 00477 (void)nco_xrf_dmn(var_out[idx]); 00478 } /* end loop over idx */ 00479 /* Extraction list no longer needed */ 00480 xtr_lst=nco_nm_id_lst_free(xtr_lst,nbr_xtr); 00481 00482 /* Divide variable lists into lists of fixed variables and variables to be processed */ 00483 (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_1,&var_prc_out,&nbr_var_prc); 00484 00485 /* Zero start vectors for all output variables */ 00486 (void)nco_var_srt_zero(var_out,nbr_xtr); 00487 00488 #ifdef ENABLE_MPI 00489 if(prc_rnk == rnk_mgr){ /* MPI manager code */ 00490 #endif /* !ENABLE_MPI */ 00491 /* Open output file */ 00492 fl_out_tmp=nco_fl_out_open(fl_out,FORCE_APPEND,FORCE_OVERWRITE,fl_out_fmt,&out_id); 00493 00494 /* Copy global attributes */ 00495 (void)nco_att_cpy(in_id_1,out_id,NC_GLOBAL,NC_GLOBAL,True); 00496 00497 /* Catenate time-stamped command line to "history" global attribute */ 00498 if(HISTORY_APPEND) (void)nco_hst_att_cat(out_id,cmd_ln); 00499 00500 if(thr_nbr > 0 && HISTORY_APPEND) (void)nco_thr_att_cat(out_id,thr_nbr); 00501 00502 #ifdef ENABLE_MPI 00503 /* Initialize MPI task information */ 00504 if(prc_nbr > 0 && HISTORY_APPEND) (void)nco_mpi_att_cat(out_id,prc_nbr); 00505 #endif /* !ENABLE_MPI */ 00506 00507 /* Define dimensions in output file */ 00508 (void)nco_dmn_dfn(fl_out,out_id,dmn_out,nbr_dmn_xtr); 00509 00510 /* Define variables in output file, copy their attributes */ 00511 (void)nco_var_dfn(in_id_1,fl_out,out_id,var_out,nbr_xtr,(dmn_sct **)NULL,(int)0,nco_pck_plc_nil,nco_pck_map_nil); 00512 00513 /* Turn off default filling behavior to enhance efficiency */ 00514 rcd=nco_set_fill(out_id,NC_NOFILL,&fll_md_old); 00515 00516 /* Take output file out of define mode */ 00517 (void)nco_enddef(out_id); 00518 00519 #ifdef ENABLE_MPI 00520 } /* prc_rnk != rnk_mgr */ 00521 00522 /* Manager obtains output filename and broadcasts to workers */ 00523 if(prc_rnk == rnk_mgr) fl_nm_lng=(int)strlen(fl_out_tmp); 00524 MPI_Bcast(&fl_nm_lng,1,MPI_INT,0,MPI_COMM_WORLD); 00525 if(prc_rnk != rnk_mgr) fl_out_tmp=(char *)malloc((fl_nm_lng+1)*sizeof(char)); 00526 MPI_Bcast(fl_out_tmp,fl_nm_lng+1,MPI_CHAR,0,MPI_COMM_WORLD); 00527 00528 if(prc_rnk == rnk_mgr){ /* MPI manager code */ 00529 TKN_WRT_FREE=False; 00530 #endif /* !ENABLE_MPI */ 00531 /* Copy variable data for non-processed variables */ 00532 (void)nco_var_val_cpy(in_id_1,out_id,var_fix,nbr_var_fix); 00533 #ifdef ENABLE_MPI 00534 /* Close output file so workers can open it */ 00535 nco_close(out_id); 00536 TKN_WRT_FREE=True; 00537 } /* prc_rnk != rnk_mgr */ 00538 #endif /* !ENABLE_MPI */ 00539 00540 /* Perform various error-checks on input file */ 00541 if(False) (void)nco_fl_cmp_err_chk(); 00542 00543 /* ncflint-specific stuff: */ 00544 /* Find the weighting variable in input file */ 00545 if(CMD_LN_NTP_VAR){ 00546 int ntp_id_1; 00547 int ntp_id_2; 00548 00549 var_sct *ntp_1; 00550 var_sct *ntp_2; 00551 var_sct *ntp_var_out; 00552 00553 /* Turn arrival point into pseudo-variable */ 00554 val_gnr_unn.d=ntp_val_out; /* Generic container for arrival point or weight */ 00555 ntp_var_out=scl_mk_var(val_gnr_unn,NC_DOUBLE); 00556 00557 rcd=nco_inq_varid(in_id_1,ntp_nm,&ntp_id_1); 00558 rcd=nco_inq_varid(in_id_2,ntp_nm,&ntp_id_2); 00559 00560 ntp_1=nco_var_fll(in_id_1,ntp_id_1,ntp_nm,dim,nbr_dmn_xtr); 00561 ntp_2=nco_var_fll(in_id_2,ntp_id_2,ntp_nm,dim,nbr_dmn_xtr); 00562 00563 /* Currently, only support scalar variables */ 00564 if(ntp_1->sz > 1 || ntp_2->sz > 1){ 00565 (void)fprintf(stdout,"%s: ERROR interpolation variable %s must be scalar\n",prg_nm_get(),ntp_nm); 00566 nco_exit(EXIT_FAILURE); 00567 } /* end if */ 00568 00569 /* Retrieve interpolation variable */ 00570 /* NB: nco_var_get() with same nc_id contains OpenMP critical region */ 00571 (void)nco_var_get(in_id_1,ntp_1); 00572 (void)nco_var_get(in_id_2,ntp_2); 00573 00574 /* Weights must be NC_DOUBLE */ 00575 ntp_1=nco_var_cnf_typ((nc_type)NC_DOUBLE,ntp_1); 00576 ntp_2=nco_var_cnf_typ((nc_type)NC_DOUBLE,ntp_2); 00577 00578 /* Check for degenerate case */ 00579 if(ntp_1->val.dp[0] == ntp_2->val.dp[0]){ 00580 (void)fprintf(stdout,"%s: ERROR Interpolation variable %s is identical (%g) in input files, therefore unable to interpolate.\n",prg_nm_get(),ntp_nm,ntp_1->val.dp[0]); 00581 nco_exit(EXIT_FAILURE); 00582 } /* end if */ 00583 00584 /* Turn weights into pseudo-variables */ 00585 wgt_1=nco_var_dpl(ntp_2); 00586 wgt_2=nco_var_dpl(ntp_var_out); 00587 00588 /* Subtract to find interpolation distances */ 00589 (void)nco_var_sbt(ntp_1->type,ntp_1->sz,ntp_1->has_mss_val,ntp_1->mss_val,ntp_var_out->val,wgt_1->val); 00590 (void)nco_var_sbt(ntp_1->type,ntp_1->sz,ntp_1->has_mss_val,ntp_1->mss_val,ntp_1->val,wgt_2->val); 00591 (void)nco_var_sbt(ntp_1->type,ntp_1->sz,ntp_1->has_mss_val,ntp_1->mss_val,ntp_1->val,ntp_2->val); 00592 00593 /* Normalize to obtain final interpolation weights */ 00594 (void)nco_var_dvd(wgt_1->type,wgt_1->sz,wgt_1->has_mss_val,wgt_1->mss_val,ntp_2->val,wgt_1->val); 00595 (void)nco_var_dvd(wgt_2->type,wgt_2->sz,wgt_2->has_mss_val,wgt_2->mss_val,ntp_2->val,wgt_2->val); 00596 00597 if(ntp_1 != NULL) ntp_1=nco_var_free(ntp_1); 00598 if(ntp_2 != NULL) ntp_2=nco_var_free(ntp_2); 00599 if(ntp_var_out != NULL) ntp_var_out=nco_var_free(ntp_var_out); 00600 } /* end if CMD_LN_NTP_VAR */ 00601 00602 if(CMD_LN_NTP_WGT){ 00603 val_gnr_unn.d=wgt_val_1; /* Generic container for arrival point or weight */ 00604 wgt_1=scl_mk_var(val_gnr_unn,NC_DOUBLE); 00605 val_gnr_unn.d=wgt_val_2; /* Generic container for arrival point or weight */ 00606 wgt_2=scl_mk_var(val_gnr_unn,NC_DOUBLE); 00607 } /* end if CMD_LN_NTP_WGT */ 00608 00609 if(dbg_lvl > 1) (void)fprintf(stderr,"wgt_1 = %g, wgt_2 = %g\n",wgt_1->val.dp[0],wgt_2->val.dp[0]); 00610 00611 /* Create structure list for second file */ 00612 var_prc_2=(var_sct **)nco_malloc(nbr_var_prc*sizeof(var_sct *)); 00613 00614 /* Loop over each interpolated variable */ 00615 #ifdef ENABLE_MPI 00616 if(prc_rnk == rnk_mgr){ /* MPI manager code */ 00617 /* Compensate for incrementing on each worker's first message */ 00618 var_wrt_nbr=-prc_nbr+1; 00619 idx=0; 00620 /* While variables remain to be processed or written... */ 00621 while(var_wrt_nbr < nbr_var_prc){ 00622 /* Receive message from any worker */ 00623 MPI_Recv(wrk_id_bfr,wrk_id_bfr_lng,MPI_INT,MPI_ANY_SOURCE,MPI_ANY_TAG,MPI_COMM_WORLD,&mpi_stt); 00624 /* Obtain MPI message tag type */ 00625 msg_tag_typ=mpi_stt.MPI_TAG; 00626 /* Get sender's prc_rnk */ 00627 rnk_wrk=wrk_id_bfr[0]; 00628 00629 /* Allocate next variable, if any, to worker */ 00630 if(msg_tag_typ == msg_tag_wrk_rqs){ 00631 var_wrt_nbr++; /* [nbr] Number of variables written */ 00632 /* Worker closed output file before sending msg_tag_wrk_rqs */ 00633 TKN_WRT_FREE=True; 00634 00635 if(idx > nbr_var_prc-1){ 00636 msg_bfr[0]=idx_all_wrk_ass; /* [enm] All variables already assigned */ 00637 msg_bfr[1]=out_id; /* Output file ID */ 00638 }else{ 00639 /* Tell requesting worker to allocate space for next variable */ 00640 msg_bfr[0]=idx; /* [idx] Variable to be processed */ 00641 msg_bfr[1]=out_id; /* Output file ID */ 00642 msg_bfr[2]=var_prc_out[idx]->id; /* [id] Variable ID in output file */ 00643 /* Point to next variable on list */ 00644 idx++; 00645 } /* endif idx */ 00646 MPI_Send(msg_bfr,msg_bfr_lng,MPI_INT,rnk_wrk,msg_tag_wrk_rsp,MPI_COMM_WORLD); 00647 /* msg_tag_typ != msg_tag_wrk_rqs */ 00648 }else if(msg_tag_typ == msg_tag_tkn_wrt_rqs){ 00649 /* Allocate token if free, else ask worker to try later */ 00650 if(TKN_WRT_FREE){ 00651 TKN_WRT_FREE=False; 00652 msg_bfr[0]=tkn_wrt_rqs_xcp; /* Accept request for write token */ 00653 }else{ 00654 msg_bfr[0]=tkn_wrt_rqs_dny; /* Deny request for write token */ 00655 } /* !TKN_WRT_FREE */ 00656 MPI_Send(msg_bfr,msg_bfr_lng,MPI_INT,rnk_wrk,msg_tag_tkn_wrt_rsp,MPI_COMM_WORLD); 00657 } /* msg_tag_typ != msg_tag_tkn_wrt_rqs */ 00658 } /* end while var_wrt_nbr < nbr_var_prc */ 00659 }else{ /* prc_rnk != rnk_mgr, end Manager code begin Worker code */ 00660 wrk_id_bfr[0]=prc_rnk; 00661 while(1){ /* While work remains... */ 00662 /* Send msg_tag_wrk_rqs */ 00663 wrk_id_bfr[0]=prc_rnk; 00664 MPI_Send(wrk_id_bfr,wrk_id_bfr_lng,MPI_INT,rnk_mgr,msg_tag_wrk_rqs,MPI_COMM_WORLD); 00665 /* Receive msg_tag_wrk_rsp */ 00666 MPI_Recv(msg_bfr,msg_bfr_lng,MPI_INT,0,msg_tag_wrk_rsp,MPI_COMM_WORLD,&mpi_stt); 00667 idx=msg_bfr[0]; 00668 out_id=msg_bfr[1]; 00669 if(idx == idx_all_wrk_ass) break; 00670 else{ 00671 var_prc_out[idx]->id=msg_bfr[2]; 00672 /* Process this variable same as UP code */ 00673 #else /* !ENABLE_MPI */ 00674 #ifdef _OPENMP 00675 /* OpenMP notes: 00676 shared(): msk and wgt are not altered within loop 00677 private(): wgt_avg does not need initialization */ 00678 #pragma omp parallel for default(none) firstprivate(wgt_1,wgt_2,wgt_out_1,wgt_out_2) private(DO_CONFORM,MUST_CONFORM,idx,in_id_1,in_id_2,has_mss_val) shared(dbg_lvl,dim,fl_in_1,fl_in_2,fl_out,fp_stderr,in_id_1_arr,in_id_2_arr,nbr_dmn_xtr,nbr_var_prc,out_id,prg_nm,var_prc_1,var_prc_2,var_prc_out) 00679 #endif /* !_OPENMP */ 00680 /* UP and SMP codes main loop over variables */ 00681 for(idx=0;idx<nbr_var_prc;idx++){ 00682 #endif /* !ENABLE_MPI */ 00683 if(dbg_lvl > 0) (void)fprintf(fp_stderr,"%s, ",var_prc_1[idx]->nm); 00684 if(dbg_lvl > 0) (void)fflush(fp_stderr); 00685 00686 in_id_1=in_id_1_arr[omp_get_thread_num()]; 00687 in_id_2=in_id_2_arr[omp_get_thread_num()]; 00688 00689 var_prc_2[idx]=nco_var_dpl(var_prc_1[idx]); 00690 (void)nco_var_mtd_refresh(in_id_2,var_prc_2[idx]); 00691 00692 /* NB: nco_var_get() with same nc_id contains OpenMP critical region */ 00693 (void)nco_var_get(in_id_1,var_prc_1[idx]); 00694 (void)nco_var_get(in_id_2,var_prc_2[idx]); 00695 00696 wgt_out_1=nco_var_cnf_dmn(var_prc_1[idx],wgt_1,wgt_out_1,MUST_CONFORM,&DO_CONFORM); 00697 wgt_out_2=nco_var_cnf_dmn(var_prc_2[idx],wgt_2,wgt_out_2,MUST_CONFORM,&DO_CONFORM); 00698 00699 var_prc_1[idx]=nco_var_cnf_typ((nc_type)NC_DOUBLE,var_prc_1[idx]); 00700 var_prc_2[idx]=nco_var_cnf_typ((nc_type)NC_DOUBLE,var_prc_2[idx]); 00701 00702 /* Allocate and, if necesssary, initialize space for processed variable */ 00703 var_prc_out[idx]->sz=var_prc_1[idx]->sz; 00704 /* NB: must not try to free() same tally buffer twice */ 00705 /* var_prc_out[idx]->tally=var_prc_1[idx]->tally=(long *)nco_malloc(var_prc_out[idx]->sz*sizeof(long));*/ 00706 var_prc_out[idx]->tally=(long *)nco_malloc(var_prc_out[idx]->sz*sizeof(long)); 00707 (void)nco_zero_long(var_prc_out[idx]->sz,var_prc_out[idx]->tally); 00708 00709 /* Weight variable by taking product of weight with variable */ 00710 (void)nco_var_mlt(var_prc_1[idx]->type,var_prc_1[idx]->sz,var_prc_1[idx]->has_mss_val,var_prc_1[idx]->mss_val,wgt_out_1->val,var_prc_1[idx]->val); 00711 (void)nco_var_mlt(var_prc_2[idx]->type,var_prc_2[idx]->sz,var_prc_2[idx]->has_mss_val,var_prc_2[idx]->mss_val,wgt_out_2->val,var_prc_2[idx]->val); 00712 /* Change missing_value of var_prc_2, if any, to missing_value of var_prc_1, if any */ 00713 has_mss_val=nco_mss_val_cnf(var_prc_1[idx],var_prc_2[idx]); 00714 /* NB: fxm: use tally to determine when to "unweight" answer? TODO */ 00715 (void)nco_var_add_tll_ncflint(var_prc_1[idx]->type,var_prc_1[idx]->sz,has_mss_val,var_prc_1[idx]->mss_val,var_prc_out[idx]->tally,var_prc_1[idx]->val,var_prc_2[idx]->val); 00716 00717 /* Re-cast output variable to original type */ 00718 var_prc_2[idx]=nco_var_cnf_typ(var_prc_out[idx]->type,var_prc_2[idx]); 00719 00720 #ifdef ENABLE_MPI 00721 /* Obtain token and prepare to write */ 00722 while(1){ /* Send msg_tag_tkn_wrt_rqs repeatedly until token obtained */ 00723 wrk_id_bfr[0]=prc_rnk; 00724 MPI_Send(wrk_id_bfr,wrk_id_bfr_lng,MPI_INT,rnk_mgr,msg_tag_tkn_wrt_rqs,MPI_COMM_WORLD); 00725 MPI_Recv(msg_bfr,msg_bfr_lng,MPI_INT,rnk_mgr,msg_tag_tkn_wrt_rsp,MPI_COMM_WORLD,&mpi_stt); 00726 tkn_wrt_rsp=msg_bfr[0]; 00727 /* Wait then re-send request */ 00728 if(tkn_wrt_rsp == tkn_wrt_rqs_dny) sleep(tkn_wrt_rqs_ntv); else break; 00729 } /* end while loop waiting for write token */ 00730 00731 /* Worker has token---prepare to write */ 00732 if(tkn_wrt_rsp == tkn_wrt_rqs_xcp){ 00733 rcd=nco_open(fl_out_tmp,NC_WRITE|NC_SHARE,&out_id); 00734 /* Turn off default filling behavior to enhance efficiency */ 00735 rcd=nco_set_fill(out_id,NC_NOFILL,&fll_md_old); 00736 #else /* !ENABLE_MPI */ 00737 #ifdef _OPENMP 00738 #pragma omp critical 00739 #endif /* _OPENMP */ 00740 #endif /* !ENABLE_MPI */ 00741 /* Common code for UP, SMP, and MPI */ 00742 { /* begin OpenMP critical */ 00743 /* Copy interpolations to output file */ 00744 if(var_prc_out[idx]->nbr_dim == 0){ 00745 (void)nco_put_var1(out_id,var_prc_out[idx]->id,var_prc_out[idx]->srt,var_prc_2[idx]->val.vp,var_prc_out[idx]->type); 00746 }else{ /* end if variable is a scalar */ 00747 (void)nco_put_vara(out_id,var_prc_out[idx]->id,var_prc_out[idx]->srt,var_prc_out[idx]->cnt,var_prc_2[idx]->val.vp,var_prc_out[idx]->type); 00748 } /* end else */ 00749 } /* end OpenMP critical */ 00750 00751 /* Free dynamically allocated buffers */ 00752 if(var_prc_1[idx] != NULL) var_prc_1[idx]=nco_var_free(var_prc_1[idx]); 00753 if(var_prc_2[idx] != NULL) var_prc_2[idx]=nco_var_free(var_prc_2[idx]); 00754 if(var_prc_out[idx] != NULL) var_prc_out[idx]=nco_var_free(var_prc_out[idx]); 00755 00756 #ifdef ENABLE_MPI 00757 /* Close output file and increment written counter */ 00758 nco_close(out_id); 00759 var_wrt_nbr++; 00760 } /* endif tkn_wrt_rqs_xcp */ 00761 } /* end else !idx_all_wrk_ass */ 00762 } /* end while loop requesting work/token */ 00763 } /* endif Worker */ 00764 #else /* !ENABLE_MPI */ 00765 } /* end (OpenMP parallel for) loop over idx */ 00766 #endif /* !ENABLE_MPI */ 00767 00768 if(dbg_lvl > 0) (void)fprintf(stderr,"\n"); 00769 00770 /* Close input netCDF files */ 00771 for(thr_idx=0;thr_idx<thr_nbr;thr_idx++) nco_close(in_id_1_arr[thr_idx]); 00772 for(thr_idx=0;thr_idx<thr_nbr;thr_idx++) nco_close(in_id_2_arr[thr_idx]); 00773 00774 #ifdef ENABLE_MPI 00775 /* Manager moves output file (closed by workers) from temporary to permanent location */ 00776 if(prc_rnk == rnk_mgr) (void)nco_fl_mv(fl_out_tmp,fl_out); 00777 #else /* !ENABLE_MPI */ 00778 /* Close output file and move it from temporary to permanent location */ 00779 (void)nco_fl_out_cls(fl_out,fl_out_tmp,out_id); 00780 #endif /* end !ENABLE_MPI */ 00781 00782 /* Remove local copy of file */ 00783 if(FILE_1_RETRIEVED_FROM_REMOTE_LOCATION && REMOVE_REMOTE_FILES_AFTER_PROCESSING) (void)nco_fl_rm(fl_in_1); 00784 if(FILE_2_RETRIEVED_FROM_REMOTE_LOCATION && REMOVE_REMOTE_FILES_AFTER_PROCESSING) (void)nco_fl_rm(fl_in_2); 00785 00786 /* ncflint-unique memory */ 00787 if(fl_in_1 != NULL) fl_in_1=(char *)nco_free(fl_in_1); 00788 if(fl_in_2 != NULL) fl_in_2=(char *)nco_free(fl_in_2); 00789 var_prc_1=(var_sct **)nco_free(var_prc_1); 00790 var_prc_2=(var_sct **)nco_free(var_prc_2); 00791 if(wgt_1 != NULL) wgt_1=(var_sct *)nco_var_free(wgt_1); 00792 if(wgt_2 != NULL) wgt_2=(var_sct *)nco_var_free(wgt_2); 00793 if(wgt_out_1 != NULL) wgt_out_1=(var_sct *)nco_var_free(wgt_out_1); 00794 if(wgt_out_2 != NULL) wgt_out_2=(var_sct *)nco_var_free(wgt_out_2); 00795 00796 /* NCO-generic clean-up */ 00797 /* Free individual strings/arrays */ 00798 if(cmd_ln != NULL) cmd_ln=(char *)nco_free(cmd_ln); 00799 if(fl_out != NULL) fl_out=(char *)nco_free(fl_out); 00800 if(fl_out_tmp != NULL) fl_out_tmp=(char *)nco_free(fl_out_tmp); 00801 if(fl_pth != NULL) fl_pth=(char *)nco_free(fl_pth); 00802 if(fl_pth_lcl != NULL) fl_pth_lcl=(char *)nco_free(fl_pth_lcl); 00803 00804 /* Free lists of strings */ 00805 if(fl_lst_in != NULL && fl_lst_abb == NULL) fl_lst_in=nco_sng_lst_free(fl_lst_in,fl_nbr); 00806 if(fl_lst_in != NULL && fl_lst_abb != NULL) fl_lst_in=nco_sng_lst_free(fl_lst_in,1); 00807 if(fl_lst_abb != NULL) fl_lst_abb=nco_sng_lst_free(fl_lst_abb,abb_arg_nbr); 00808 if(var_lst_in_nbr > 0) var_lst_in=nco_sng_lst_free(var_lst_in,var_lst_in_nbr); 00809 /* Free limits */ 00810 for(idx=0;idx<lmt_nbr;idx++) lmt_arg[idx]=(char *)nco_free(lmt_arg[idx]); 00811 if(lmt_nbr > 0) lmt=nco_lmt_lst_free(lmt,lmt_nbr); 00812 /* Free dimension lists */ 00813 if(nbr_dmn_xtr > 0) dim=nco_dmn_lst_free(dim,nbr_dmn_xtr); 00814 if(nbr_dmn_xtr > 0) dmn_out=nco_dmn_lst_free(dmn_out,nbr_dmn_xtr); 00815 /* Free variable lists */ 00816 /* ncflint free()s _prc variables at end of main loop */ 00817 var=(var_sct **)nco_free(var); 00818 var_out=(var_sct **)nco_free(var_out); 00819 var_prc_out=(var_sct **)nco_free(var_prc_out); 00820 if(nbr_var_fix > 0) var_fix=nco_var_lst_free(var_fix,nbr_var_fix); 00821 if(nbr_var_fix > 0) var_fix_out=nco_var_lst_free(var_fix_out,nbr_var_fix); 00822 00823 #ifdef ENABLE_MPI 00824 MPI_Finalize(); 00825 #endif /* !ENABLE_MPI */ 00826 00827 if(rcd != NC_NOERR) nco_err_exit(rcd,"main"); 00828 nco_exit_gracefully(); 00829 return EXIT_SUCCESS; 00830 } /* end main() */
|
1.4.4