• Main Page
  • Related Pages
  • Modules
  • Namespaces
  • Data Structures
  • Files
  • File List
  • Globals

bin/main.c

00001 
00067 #include "apbscfg.h"
00068 #include "apbs/apbs.h"  
00069 #include "apbs/nosh.h"  
00070 #include "apbs/mgparm.h"  
00071 #include "apbs/pbeparm.h"  
00072 #include "apbs/femparm.h"  
00073 
00074 #include "routines.h"
00075 
00076 VEMBED(rcsid="$Id: main.c 1595 2010-08-24 15:26:42Z yhuang01 $")
00077 
00078 
00084 int main(
00085                        int argc,  
00086                        char **argv  
00087                        ) 
00088 {
00089            
00090            NOsh *nosh = VNULL;
00091            
00092            MGparm *mgparm = VNULL;
00093            FEMparm *feparm = VNULL;
00094            PBEparm *pbeparm = VNULL;
00095            APOLparm *apolparm = VNULL;
00096            Vparam *param = VNULL;
00097            
00098            Vmem *mem = VNULL;
00099            Vcom *com = VNULL;
00100            Vio *sock = VNULL;
00101 #ifdef HAVE_MC_H
00102            Vfetk *fetk[NOSH_MAXCALC];
00103            Gem *gm[NOSH_MAXMOL];
00104 #else
00105            void *fetk[NOSH_MAXCALC];
00106            void *gm[NOSH_MAXMOL];
00107 #endif
00108            Vpmg *pmg[NOSH_MAXCALC];
00109            Vpmgp *pmgp[NOSH_MAXCALC];
00110            Vpbe *pbe[NOSH_MAXCALC];
00111            Valist *alist[NOSH_MAXMOL];
00112            Vgrid *dielXMap[NOSH_MAXMOL],*dielYMap[NOSH_MAXMOL],*dielZMap[NOSH_MAXMOL];
00113            Vgrid *kappaMap[NOSH_MAXMOL];
00114            Vgrid *potMap[NOSH_MAXMOL];
00115            Vgrid *chargeMap[NOSH_MAXMOL];
00116            char *input_path = VNULL;
00117            char *output_path = VNULL;
00118            int i, rank, size, isolve, k;
00119            size_t bytesTotal, highWater;
00120            Voutput_Format outputformat;
00121            
00122            int rc = 0;
00123            
00124            /* These variables require some explaining... The energy double arrays
00125                       * store energies from the various calculations.  The energy int array
00126                       * stores either a flag (0,1) displaying whether energies were calculated
00127                       * or if PCE_COMPS is used, the number of atom energies stored
00128                       * for the given calculation.  Likewise, the
00129                       * force double arrays store forces from the various calcualtions.  The
00130                       * force int array stores an integer which either says no calculation was
00131                       * performed (0) or gives the number of entries in the force array for each
00132                       * calculation */
00133            double qfEnergy[NOSH_MAXCALC], qmEnergy[NOSH_MAXCALC];
00134            double dielEnergy[NOSH_MAXCALC], totEnergy[NOSH_MAXCALC];
00135            AtomForce *atomForce[NOSH_MAXCALC];
00136            double *atomEnergy[NOSH_MAXCALC];
00137            int nenergy[NOSH_MAXCALC], nforce[NOSH_MAXCALC];
00138            /* THe real partition centers */
00139            double realCenter[3];
00140            
00141            /* Instructions: */
00142            char header[] = {"\n\n\
00143 ----------------------------------------------------------------------\n\
00144            APBS -- Adaptive Poisson-Boltzmann Solver\n\
00145            Version 1.3\n\
00146            \n\
00147            Nathan A. Baker (baker@biochem.wustl.edu)\n\
00148            Dept. Biochemistry and Molecular Biophysics\n\
00149            Center for Computational Biology\n\
00150            Washington University in St. Louis\n\
00151            \n\
00152            Additional contributing authors listed in the code documentation.\n\
00153            \n\
00154            Copyright (c) 2002-2010, Washington University in St. Louis.\n\
00155            Portions Copyright (c) 2002-2010.  Nathan A. Baker\n\
00156            Portions Copyright (c) 1999-2002.  The Regents of the University of California.\n\
00157            Portions Copyright (c) 1995.  Michael Holst\n\
00158            \n\
00159            All rights reserved.\n\
00160            \n\
00161            Redistribution and use in source and binary forms, with or without\n\
00162            modification, are permitted provided that the following conditions are met: \n\
00163            \n\
00164            * Redistributions of source code must retain the above copyright notice, this\n\
00165            list of conditions and the following disclaimer.  \n\
00166            \n\
00167            * Redistributions in binary form must reproduce the above copyright notice,\n\
00168            this list of conditions and the following disclaimer in the documentation\n\
00169            and/or other materials provided with the distribution.\n\
00170            \n\
00171            * Neither the name of Washington University in St. Louis nor the names of its\n\
00172            contributors may be used to endorse or promote products derived from this\n\
00173            software without specific prior written permission.\n\
00174            \n\
00175            THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n\
00176            \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n\
00177            LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\n\
00178            A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR\n\
00179            CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,\n\
00180            EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,\n\
00181            PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR\n\
00182            PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF\n\
00183            LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING\n\
00184            NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n\
00185            SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\
00186 ----------------------------------------------------------------------\n\
00187            APBS uses FETK (the Finite Element ToolKit) to solve the\n\
00188            Poisson-Boltzmann equation numerically.  FETK is a portable collection\n\
00189            of finite element modeling class libraries developed by the Michael Holst\n\
00190            research group and written in an object-oriented form of C.  FEtk is\n\
00191            designed to solve general coupled systems of nonlinear partial differential\n\
00192            equations using adaptive finite element methods, inexact Newton methods,\n\
00193            and algebraic multilevel methods.  More information about FEtk may be found\n\
00194            at <http://www.FEtk.ORG>.\n\
00195 ----------------------------------------------------------------------\n\
00196            APBS also uses Aqua to solve the Poisson-Boltzmann equation numerically.  \n\
00197            Aqua is a modified form of the Holst group PMG library <http://www.FEtk.ORG>\n\
00198            which has been modified by Patrice Koehl\n\
00199            <http://koehllab.genomecenter.ucdavis.edu/> for improved efficiency and\n\
00200            memory usage when solving the Poisson-Boltzmann equation.\n\
00201 ----------------------------------------------------------------------\n\
00202            Please cite your use of APBS as:\n\n\
00203            Baker NA, Sept D, Joseph S, Holst MJ, McCammon JA. Electrostatics of\n\
00204            nanosystems: application to microtubules and the ribosome. Proc.\n\
00205            Natl. Acad. Sci. USA 98, 10037-10041 2001.\n\
00206            \n\n"};
00207            char *usage = 
00208 {"\n\n\
00209 ----------------------------------------------------------------------\n\
00210            This driver program calculates electrostatic potentials, energies,\n\
00211            and forces using both multigrid and finite element methods.\n\
00212         It is invoked as:\n\n\
00213            apbs [options] apbs.in\n\n\
00214            where apbs.in is a formatted input file and [options] are:\n\n\
00215 --output-file=<name>     Enables output logging to the path\n\
00216            listed in <name>.  Uses flat-file\n\
00217            format is --output-format is not used.\n\
00218 --output-format=<type>   Specifies format for logging.  Options\n\
00219            for type are either \"xml\" or \"flat\".\n\
00220 --help                   Display this help information.\n\
00221 --version                Display the current APBS version.\n\
00222 ----------------------------------------------------------------------\n\n"};
00223 
00224            /* ************** CHECK PARALLEL STATUS *************** */
00225            VASSERT(Vcom_init(&argc, &argv));
00226            com = Vcom_ctor(1);
00227            rank = Vcom_rank(com);
00228            size = Vcom_size(com);
00229            startVio(); 
00230            Vnm_setIoTag(rank, size);
00231            Vnm_tprint( 0, "Hello world from PE %d\n", rank);
00232 
00233            /* A bit of array/pointer initialization */
00234            mem = Vmem_ctor("MAIN");
00235            for (i=0; i<NOSH_MAXCALC; i++) {
00236                       pmg[i] = VNULL;
00237                       pmgp[i] = VNULL;
00238                       fetk[i] = VNULL;
00239                       pbe[i] = VNULL;
00240                       qfEnergy[i] = 0;
00241                       qmEnergy[i] = 0;
00242                       dielEnergy[i] = 0;
00243                       totEnergy[i] = 0;
00244                       atomForce[i] = VNULL;
00245                       nenergy[i] = 0;
00246                       nforce[i] = 0;
00247            }
00248            for (i=0; i<NOSH_MAXMOL; i++) {
00249                       alist[i] = VNULL;
00250                       dielXMap[i] = VNULL;
00251                       dielYMap[i] = VNULL;
00252                       dielZMap[i] = VNULL;
00253                       kappaMap[i] = VNULL;
00254                       potMap[i] = VNULL;
00255                       chargeMap[i] = VNULL;
00256            }
00257 
00258            /* ********* CHECK INVOCATION AND OPTIONS ************* */
00259            Vnm_tstart(APBS_TIMER_WALL_CLOCK, "APBS WALL CLOCK");
00260            Vnm_tprint( 1, "%s", header);
00261 
00262 #ifdef APBS_FAST
00263            printf("WARNING: APBS was compiled with the --enable-fast option.\n"
00264                          "WARNING: This mode is experimental and subject to change in future releases.\n"
00265                          "WARNING: The fast mode enables: Gauess-Seidel Smoothing and \n"
00266                          "WARNING:   Conjugate Gradient Multigrid methods.\n\n");
00267 #endif
00268 
00269            Vnm_tprint( 1, "This executable compiled on %s at %s\n\n", __DATE__, __TIME__);
00270 
00271 #if defined(WITH_TINKER)
00272            Vnm_tprint( 2, "This executable was compiled with TINKER support and is not intended for stand-alone execution.\n");
00273            Vnm_tprint( 2, "Please compile another version without TINKER support.\n");
00274            exit(2);
00275 #endif
00276            
00277            i=0;
00278            outputformat = OUTPUT_NULL;
00279            while (i<argc){
00280                       if (strncmp(argv[i], "--", 2) == 0) {
00281                                  
00282                                  /* Long Options */
00283                                  if (Vstring_strcasecmp("--version", argv[i]) == 0){
00284                                             Vnm_tprint(2, "%s\n", PACKAGE_STRING);
00285                                             VJMPERR1(0);
00286                                  } else if (Vstring_strcasecmp("--help", argv[i]) == 0){
00287                                             Vnm_tprint(2, "%s\n", usage);
00288                                             VJMPERR1(0); 
00289                                  } else if (strncmp(argv[i], "--output-format", 15) == 0) {
00290                                             if (strstr(argv[i], "xml") != NULL) {
00291                                                        Vnm_tprint(2, "XML output format is now deprecated, please use --output-format=flat instead!\n\n");
00292                                                        VJMPERR1(0); 
00293                                             }
00294                                             else if (strstr(argv[i], "flat") != NULL) {
00295                                                        outputformat = OUTPUT_FLAT;
00296                                             } else {
00297                                                        Vnm_tprint(2, "Invalid output-format type!\n");
00298                                                        VJMPERR1(0);
00299                                             }
00300                                  } else if (strncmp(argv[i], "--output-file=", 14) == 0){
00301                                             output_path = strstr(argv[i], "=");
00302                                             ++output_path;
00303                                             if (outputformat == OUTPUT_NULL) outputformat = OUTPUT_FLAT;
00304                                  } else {
00305                                             Vnm_tprint(2, "UNRECOGNIZED COMMAND LINE OPTION %s!\n", argv[i]);
00306                                             Vnm_tprint(2, "%s\n", usage);
00307                                             VJMPERR1(0); 
00308                                  }  
00309                       } else {
00310                                  
00311                                  /* Set the path to the input file */
00312                                  if ((input_path == VNULL) && (i != 0)) input_path = argv[i];
00313                                  else if (i != 0) {
00314                                             Vnm_tprint(2, "ERROR -- CALLED WITH TOO MANY ARGUMENTS!\n", \
00315                                                                      argc);
00316                                             Vnm_tprint(2, "%s\n", usage);
00317                                             VJMPERR1(0);
00318                                  }
00319                       }
00320                       i++; 
00321            }
00322 
00323            if ((outputformat != 0) && (output_path == NULL)) {
00324                       Vnm_tprint(2, "The --output-path variable must be set when using --output-format!\n");
00325                       VJMPERR1(0);
00326            }
00327 
00328            if (input_path == NULL) {
00329                       Vnm_tprint(2, "ERROR -- APBS input file not specified!\n", argc);
00330                       Vnm_tprint(2, "%s\n", usage);
00331                       VJMPERR1(0);
00332            } 
00333 
00334            /* Append rank info if a parallel run */
00335            if ((size > 1) && (output_path != NULL))
00336                       printf(output_path, "%s_%d", output_path, rank);
00337 
00338            /* *************** PARSE INPUT FILE ******************* */
00339            nosh = NOsh_ctor(rank, size);
00340            Vnm_tprint( 1, "Parsing input file %s...\n", input_path);
00341            sock = Vio_ctor("FILE", "ASC", VNULL, input_path, "r");
00342            if (sock == VNULL) {
00343                       Vnm_tprint(2, "Error while opening input file %s!\n", input_path);
00344                       VJMPERR1(0);
00345            }
00346            if (!NOsh_parseInput(nosh, sock)) {
00347                       Vnm_tprint( 2, "Error while parsing input file.\n");
00348                       VJMPERR1(0);
00349            } else Vnm_tprint( 1, "Parsed input file.\n");
00350            Vio_dtor(&sock);
00351            
00352            /* *************** LOAD PARAMETERS AND MOLECULES ******************* */      
00353            param = loadParameter(nosh);
00354            if (loadMolecules(nosh, param, alist) != 1) {
00355                       Vnm_tprint(2, "Error reading molecules!\n");
00356                       VJMPERR1(0);
00357            }
00358 
00359            /* *************** SETUP CALCULATIONS *************** */
00360            if (NOsh_setupElecCalc(nosh, alist) != 1) {
00361                       Vnm_tprint(2, "Error setting up ELEC calculations\n");
00362                       VJMPERR1(0);
00363            }
00364            
00365            if ((rc = NOsh_setupApolCalc(nosh, alist)) == ACD_ERROR) {
00366                       Vnm_tprint(2, "Error setting up APOL calculations\n");
00367                       VJMPERR1(0);
00368            }
00369            
00370            /* ******************* CHECK APOL********************** */
00371            /* if((nosh->gotparm == 0) && (rc == ACD_YES)){
00372                       Vnm_print(1,"\nError you must provide a parameter file if you\n" \
00373                                                        "     are performing an APOLAR calculation\n");
00374                       VJMPERR1(0);
00375            } */
00376            
00377 #if defined(DEBUG_MAC_OSX_OCL)
00378 #include "mach_chud.h"
00379 #include <stdint.h>
00380            uint64_t mbeg;
00381            machm_(&mbeg);
00382            
00383            if(clFinish != NULL)
00384            {
00385                       int ret = initOpenCL();
00386         printf("OpenCL runtime present - initialized = %i\n",ret);
00387     }
00388     else
00389            {
00390                       setkOpenCLAvailable_(0);
00391         printf("OpenCL is not present!\n");
00392            }
00393 #endif
00394            
00395 #if defined(DEBUG_MAC_OSX_STANDARD)
00396 #include "mach_chud.h"
00397 #include <stdint.h>
00398            uint64_t mbeg;
00399            machm_(&mbeg);
00400 #endif
00401            
00402            /* *************** LOAD MAPS ******************* */
00403            if (loadDielMaps(nosh, dielXMap, dielYMap, dielZMap) != 1) {
00404                       Vnm_tprint(2, "Error reading dielectric maps!\n");
00405                       VJMPERR1(0);
00406            }
00407            if (loadKappaMaps(nosh, kappaMap) != 1) {
00408                       Vnm_tprint(2, "Error reading kappa maps!\n");
00409                       VJMPERR1(0);
00410            }
00411            if (loadPotMaps(nosh, potMap) != 1) {
00412                       Vnm_tprint(2, "Error reading potential maps!\n");
00413                       VJMPERR1(0);
00414            }
00415            if (loadChargeMaps(nosh, chargeMap) != 1) {
00416                       Vnm_tprint(2, "Error reading charge maps!\n");
00417                       VJMPERR1(0);
00418            }
00419            
00420            /* *************** DO THE CALCULATIONS ******************* */
00421            Vnm_tprint( 1, "Preparing to run %d PBE calculations.\n",
00422                                             nosh->ncalc);
00423            for (i=0; i<nosh->ncalc; i++) {
00424                       Vnm_tprint( 1, "----------------------------------------\n");
00425                       
00426                       switch (nosh->calc[i]->calctype) {  
00427                                  case NCT_MG:
00428                                             /* What is this?  This seems like a very awkward way to find 
00429                                             the right ELEC statement... */
00430                                             for (k=0; k<nosh->nelec; k++) {
00431                                                        if (nosh->elec2calc[k] >= i) {
00432                                                                   break;
00433                                                        }
00434                                             }
00435                                             if (Vstring_strcasecmp(nosh->elecname[k], "") == 0) {
00436                                                        Vnm_tprint( 1, "CALCULATION #%d: MULTIGRID\n", i+1);
00437                                             } else {
00438                                                        Vnm_tprint( 1, "CALCULATION #%d (%s): MULTIGRID\n", 
00439                                                                                         i+1, nosh->elecname[k]);
00440                                             }
00441                                             /* Useful local variables */
00442                                             mgparm = nosh->calc[i]->mgparm;
00443                                             pbeparm = nosh->calc[i]->pbeparm;
00444                                             
00445                                             /* Set up problem */
00446                                             Vnm_tprint( 1, "  Setting up problem...\n");
00447 
00448                                             if (!initMG(i, nosh, mgparm, pbeparm, realCenter, pbe, 
00449                                                                              alist, dielXMap, dielYMap, dielZMap, kappaMap,
00450                                                                              chargeMap, pmgp, pmg, potMap)) {
00451                                                        Vnm_tprint( 2, "Error setting up MG calculation!\n");
00452                                                        VJMPERR1(0);
00453                                             }
00454 
00455                                             /* Print problem parameters */
00456                                             printMGPARM(mgparm, realCenter);
00457                                             printPBEPARM(pbeparm);
00458                                             
00459                                             /* Solve PDE */
00460                                             if (solveMG(nosh, pmg[i], mgparm->type) != 1) {
00461                                                        Vnm_tprint(2, "Error solving PDE!\n");
00462                                                        VJMPERR1(0);
00463                                             }
00464                                                        
00465                                             /* Set partition information for observables and I/O */
00466                                             if (setPartMG(nosh, mgparm, pmg[i]) != 1) {
00467                                                        Vnm_tprint(2, "Error setting partition info!\n");
00468                                                        VJMPERR1(0);
00469                                             }
00470                                                        
00471                                             /* Write out energies */
00472                                             energyMG(nosh, i, pmg[i], 
00473                                                                   &(nenergy[i]), &(totEnergy[i]), &(qfEnergy[i]), 
00474                                                                   &(qmEnergy[i]), &(dielEnergy[i]));
00475                                             
00476                                             /* Write out forces */
00477                                             forceMG(mem, nosh, pbeparm, mgparm, pmg[i], &(nforce[i]), 
00478                                                                   &(atomForce[i]), alist);
00479                                                        
00480                                             /* Write out data folks might want */
00481                                             writedataMG(rank, nosh, pbeparm, pmg[i]);
00482                                             
00483                                             /* Write matrix */
00484                                             writematMG(rank, nosh, pbeparm, pmg[i]);
00485                                             
00486                                             /* If needed, cache atom energies */                                         
00487                                             nenergy[i] = 0;
00488                                             if ((pbeparm->calcenergy == PCE_COMPS) && (outputformat != OUTPUT_NULL)){
00489                                                        storeAtomEnergy(pmg[i], i, &(atomEnergy[i]), &(nenergy[i]));
00490                                             }
00491                                                        
00492                                             fflush(stdout);
00493                                             fflush(stderr);
00494                                             
00495                                             break;
00496                                             
00497                                             /* ***** Do FEM calculation ***** */
00498                                  case NCT_FEM:
00499 #ifdef HAVE_MC_H
00500                                             for (k=0; k<nosh->nelec; k++) {
00501                                                        if (nosh->elec2calc[k] >= i) break;
00502                                             }
00503                                             if (Vstring_strcasecmp(nosh->elecname[i+1], "") == 0) {
00504                                                        Vnm_tprint( 1, "CALCULATION #%d: FINITE ELEMENT\n", i+1);
00505                                             } else {
00506                                                        Vnm_tprint( 1, "CALCULATION #%d (%s): FINITE ELEMENT\n", i+1, nosh->elecname[k+1]);
00507                                             }
00508                                             
00509                                             /* Useful local variables */
00510                                             feparm = nosh->calc[i]->femparm;
00511                                             pbeparm = nosh->calc[i]->pbeparm;
00512                                             
00513                                             /* Warn the user about some things */
00514                                             Vnm_tprint(2, "#################### WARNING ###################\n");
00515                                             Vnm_tprint(2, "## FE support is currently very experimental! ##\n");
00516                                             Vnm_tprint(2, "#################### WARNING ###################\n");
00517                                             
00518                                             /* Set up problem */
00519                                             Vnm_tprint( 1, "  Setting up problem...\n");
00520                                             if (initFE(i, nosh, feparm, pbeparm, pbe, alist, fetk, gm) != VRC_SUCCESS) {
00521                                                        Vnm_tprint( 2, "Error setting up FE calculation!\n");
00522                                                        VJMPERR1(0);
00523                                             }
00524                                                        
00525                                                        /* Print problem parameters */
00526                                                        printFEPARM(i, nosh, feparm, fetk);
00527                                             printPBEPARM(pbeparm);
00528                                             
00529                                             /* Refine mesh */
00530                                             if (!preRefineFE(i, nosh, feparm, fetk)) {
00531                                                        Vnm_tprint( 2, "Error pre-refining mesh!\n");
00532                                                        VJMPERR1(0);
00533                                             }
00534                                                        
00535                                             /* Solve-estimate-refine */
00536                                             Vnm_tprint(2, "\n\nWARNING!  DO NOT EXPECT PERFORMANCE OUT OF THE APBS/FEtk\n");
00537                                             Vnm_tprint(2, "INTERFACE AT THIS TIME.  THE FINITE ELEMENT SOLVER IS\n");
00538                                             Vnm_tprint(2, "CURRENTLY NOT OPTIMIZED FOR THE PB EQUATION.  IF YOU WANT\n");
00539                                             Vnm_tprint(2, "PERFORMANCE, PLEASE USE THE MULTIGRID-BASED METHODS, E.G.\n");
00540                                             Vnm_tprint(2, "MG-AUTO, MG-PARA, and MG-MANUAL (SEE DOCS.)\n\n");
00541                                             Vnm_tprint(1, "  Beginning solve-estimate-refine cycle:\n");
00542                                             for (isolve=0; isolve<feparm->maxsolve; isolve++) {
00543                                                        Vnm_tprint(1, "    Solve #%d...\n", isolve);
00544                                                        if (!solveFE(i, nosh, pbeparm, feparm, fetk)) {
00545                                                                   Vnm_tprint(2, "ERROR SOLVING EQUATION!\n");
00546                                                                   VJMPERR1(0);
00547                                                        }
00548                                                        if (!energyFE(nosh, i, fetk, &(nenergy[i]), 
00549                                                                                           &(totEnergy[i]), &(qfEnergy[i]), 
00550                                                                                           &(qmEnergy[i]), &(dielEnergy[i]))) {
00551                                                                   Vnm_tprint(2, "ERROR SOLVING EQUATION!\n");
00552                                                                   VJMPERR1(0);
00553                                                        }
00554                                                        /* We're not going to refine if we've hit the max number
00555                                                                   * of solves */
00556                                                        if (isolve < (feparm->maxsolve)-1) {
00557                                                                   if (!postRefineFE(i, nosh, feparm, fetk)) break;
00558                                                        }
00559                                                        bytesTotal = Vmem_bytesTotal();
00560                                                        highWater = Vmem_highWaterTotal();
00561                                                        Vnm_tprint(1, "      Currently memory use:  %g MB\n", 
00562                                                                                 ((double)bytesTotal/(1024.)/(1024.)));
00563                                                        Vnm_tprint(1, "      High-water memory use:  %g MB\n", 
00564                                                                                 ((double)highWater/(1024.)/(1024.)));
00565                                             }
00566                                                        
00567                                                        Vnm_tprint(1, "  Writing FEM data to files.\n");
00568                                             if (!writedataFE(rank, nosh, pbeparm, fetk[i])) {
00569                                                        Vnm_tprint(2, "  Error while writing FEM data!\n");
00570                                             }
00571 #else /* ifdef HAVE_MC_H */
00572                                                        Vnm_print(2, "Error!  APBS not compiled with FEtk!\n");
00573                                             exit(2);
00574 #endif /* ifdef HAVE_MC_H */
00575                                             break;
00576                                             
00577                                  /* Do an apolar calculation */
00578                                  case NCT_APOL:
00579                                             /* Copied from NCT_MG. See the note above (top of loop) for
00580                                                        information about this loop.
00581                                             */
00582                                             for (k=0; k<nosh->napol; k++) {
00583                                                        if (nosh->apol2calc[k] >= i) {
00584                                                                   break;
00585                                                        }
00586                                             }
00587                                             
00588                                             if (Vstring_strcasecmp(nosh->apolname[k], "") == 0) {
00589                                                        Vnm_tprint( 1, "CALCULATION #%d: APOLAR\n", i+1);
00590                                             } else {
00591                                                        Vnm_tprint( 1, "CALCULATION #%d (%s): APOLAR\n", 
00592                                                                                         i+1, nosh->apolname[k]);
00593                                             }
00594 
00595                                             apolparm = nosh->calc[i]->apolparm;
00596                                             rc = initAPOL(nosh, mem, param, apolparm, &(nforce[i]), &(atomForce[i]), 
00597                                                                    alist[(apolparm->molid)-1]);
00598                                             if(rc == 0) {
00599                                                        Vnm_tprint(2, "Error calculating apolar solvation quantities!\n");
00600                                                        VJMPERR1(0);
00601                                             }
00602                                             break;
00603                                  default:
00604                                             Vnm_tprint(2, "  Unknown calculation type (%d)!\n", 
00605                                                                      nosh->calc[i]->calctype);
00606                                             exit(2);
00607                       }
00608            }
00609            
00610            //Clear out the parameter file memory
00611            if(param != VNULL) Vparam_dtor(&param);
00612            
00613            /* *************** HANDLE PRINT STATEMENTS ******************* */
00614            if (nosh->nprint > 0) {
00615                       Vnm_tprint( 1, "----------------------------------------\n");
00616                       Vnm_tprint( 1, "PRINT STATEMENTS\n");
00617            }
00618            for (i=0; i<nosh->nprint; i++) {
00619                       /* Print energy */
00620                       if (nosh->printwhat[i] == NPT_ENERGY) {
00621                                  printEnergy(com, nosh, totEnergy, i);
00622                                  /* Print force */
00623                       } else if (nosh->printwhat[i] == NPT_FORCE) {
00624                                  printForce(com, nosh, nforce, atomForce, i);
00625                       } else if (nosh->printwhat[i] == NPT_ELECENERGY) {
00626                                  printElecEnergy(com, nosh, totEnergy, i);
00627                       } else if (nosh->printwhat[i] == NPT_ELECFORCE) {
00628                                  printElecForce(com, nosh, nforce, atomForce, i);
00629                       } else if (nosh->printwhat[i] == NPT_APOLENERGY) {
00630                                  printApolEnergy(nosh, i);
00631                       } else if (nosh->printwhat[i] == NPT_APOLFORCE) {
00632                                  printApolForce(com, nosh, nforce, atomForce, i);
00633                       } else {
00634                                  Vnm_tprint( 2, "Undefined PRINT keyword!\n");
00635                                  break;
00636                       }
00637            } 
00638            Vnm_tprint( 1, "----------------------------------------\n");
00639            
00640            /* *************** HANDLE LOGGING *********************** */
00641 
00642            if (outputformat == OUTPUT_FLAT) {
00643                       Vnm_tprint(2," Writing data to flat file %s...\n\n", output_path);
00644                       writedataFlat(nosh, com, output_path, totEnergy, qfEnergy, qmEnergy,
00645                                                          dielEnergy, nenergy, atomEnergy, nforce, atomForce);
00646            }
00647 
00648            /* Destroy energy arrays if they still exist */
00649 
00650            for (i=0; i<nosh->ncalc; i++) {
00651                       if (nenergy[i] > 0) Vmem_free(mem, nenergy[i], sizeof(double),
00652                                                                                                      (void **)&(atomEnergy[i]));    
00653            }
00654            
00655            /* *************** GARBAGE COLLECTION ******************* */
00656 
00657            Vnm_tprint( 1, "CLEANING UP AND SHUTTING DOWN...\n");
00658            /* Clean up APBS structures */
00659            killForce(mem, nosh, nforce, atomForce);
00660            killEnergy();
00661            killMG(nosh, pbe, pmgp, pmg);
00662 #ifdef HAVE_MC_H
00663            killFE(nosh, pbe, fetk, gm);
00664 #endif
00665            killChargeMaps(nosh, chargeMap);
00666            killKappaMaps(nosh, kappaMap);
00667            killDielMaps(nosh, dielXMap, dielYMap, dielZMap);
00668            killMolecules(nosh, alist);
00669            NOsh_dtor(&nosh);
00670            
00671            /* Memory statistics */
00672            bytesTotal = Vmem_bytesTotal();
00673            highWater = Vmem_highWaterTotal();
00674            Vnm_tprint( 1, "Final memory usage:  %4.3f MB total, %4.3f MB high water\n", 
00675                                             (double)(bytesTotal)/(1024.*1024.), 
00676                                             (double)(highWater)/(1024.*1024.));
00677 
00678            /* Clean up MALOC structures */
00679            Vcom_dtor(&com);
00680            Vmem_dtor(&mem);
00681 
00682            /* And now it's time to so "so long"... */
00683            Vnm_tprint(1, "\n\n");
00684            Vnm_tprint( 1, "Thanks for using APBS!\n\n");
00685 
00686 #if defined(DEBUG_MAC_OSX_OCL)
00687            mets_(&mbeg, "Main Program CL");
00688 #endif
00689 #if defined(DEBUG_MAC_OSX_STANDARD)
00690            mets_(&mbeg, "Main Program Standard");
00691 #endif
00692            
00693            /* This should be last */
00694            Vnm_tstop(APBS_TIMER_WALL_CLOCK, "APBS WALL CLOCK");
00695            Vnm_flush(1);
00696            Vnm_flush(2);
00697            Vcom_finalize();
00698 
00699            fflush(NULL);
00700            
00701            return 0;
00702 
00703            VERROR1:
00704            Vcom_finalize();
00705            Vcom_dtor(&com);
00706            Vmem_dtor(&mem);
00707            return APBSRC;
00708 }

Generated on Wed Oct 20 2010 11:12:14 for APBS by  doxygen 1.7.2