ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/group/trunk/OOPSE/utils/sysBuild.cpp
Revision: 501
Committed: Tue Apr 15 21:20:35 2003 UTC (21 years, 3 months ago) by mmeineke
File size: 11999 byte(s)
Log Message:
finished bilayerSys.cpp

sysBuild still need to write the bass file.

MoLocator.cpp is currently empty

File Contents

# User Rev Content
1 mmeineke 495 #include <cstdlib>
2     #include <cstdio>
3     #include <cstring>
4 mmeineke 501 #include <cmath>
5 mmeineke 495
6     #include "simError.h"
7 mmeineke 501 #include "parse_me.h"
8     #include "MakeStamps.hpp"
9     #include "Globals.hpp"
10     #include "SimInfo.hpp"
11 mmeineke 495
12 mmeineke 501 #include "sysBuild.hpp"
13 mmeineke 498 #include "bilayerSys.hpp"
14    
15 mmeineke 501 // this routine is defined in BASS_interface.cpp
16     extern void set_interface_stamps( MakeStamps* ms, Globals* g );
17 mmeineke 495
18 mmeineke 501
19     // case asignments
20 mmeineke 495 #define BILAYER 1
21    
22    
23     char* program_name;
24 mmeineke 501 bassInfo bsInfo;
25 mmeineke 495 void usage(void);
26    
27    
28     int main( int argc, char* argv[]){
29    
30     int i,j,k;
31     int sysType;
32     int done, have_prefix, isRandom;
33     char current_flag;
34     char* out_prefix;
35     char* in_name;
36 mmeineke 501 char* id;
37 mmeineke 498
38 mmeineke 501 includeLinked* headInc;
39     includeLinked* prevInc;
40     includeLinked* currInc;
41 mmeineke 495
42 mmeineke 501 MakeStamps* the_stamps = NULL;
43     Globals* the_globals = NULL;
44     MoleculeStamp** the_components = NULL;
45     LinkedMolStamp* headStamp = NULL;
46     LinkedMolStamp* currStamp;
47 mmeineke 495
48 mmeineke 501 if(
49    
50     // initialize all functions and variables
51 mmeineke 495
52 mmeineke 501 initSimError();
53     program_name = argv[0];
54 mmeineke 495 sysType = -1;
55     have_prefix = 0;
56     isRandom = 0;
57     in_name = NULL;
58 mmeineke 501 headInc = NULL;
59    
60     bsInfo.includes = NULL;
61     bsInfo.componentsNmol = NULL;
62     bsInfo.compStamps = NULL;
63     bsInfo.havePressure = 0;
64     bsInfo.haveTauBarrostat = 0;
65     bsInfo.haveTauThermostat = 0;
66     bsInfo.haveQmass = 0;
67    
68     headStamp = new LinkedMolStamp();
69     the_stamps = new MakeStamps();
70     the_globals = new Globals();
71     set_interface_stamps( the_stamps, the_globals );
72    
73     // parse command line arguments
74    
75 mmeineke 495 for( i = 1; i < argc; i++){
76    
77     if(argv[i][0] =='-'){
78    
79     // parse the option
80    
81     if(argv[i][1] == '-' ){
82    
83     // parse long word options
84    
85     if( !strcmp( argv[i], "--bilayer" ) ){
86     if( sysType > 0 ){
87     sprintf( painCave.errMsg,
88     "You cannot specify more than one system to build.\n" );
89     painCave.isFatal = 0;
90     simError();
91     usage();
92     }
93     sysType = BILAYER;
94     }
95    
96     else{
97     sprintf( painCave.errMsg,
98     "Invalid option \"%s\"\n", argv[i] );
99     painCave.isFatal = 0;
100     simError();
101     usage();
102     }
103     }
104    
105     else{
106    
107     // parse single character options
108    
109     done =0;
110     j = 1;
111     current_flag = argv[i][j];
112     while( (current_flag != '\0') && (!done) ){
113    
114     switch(current_flag){
115    
116     case 'o':
117     // -o <prefix> => the output prefix.
118    
119     i++;
120     out_prefix = argv[i];
121     have_prefix = 1;
122     done = 1;
123     break;
124    
125 mmeineke 501 case 'I':
126     // -I <include> => the include file.
127    
128     i++;
129     if( headInc == NULL ){
130     headInc = new includeLinked;
131     headInc->next = NULL;
132     strcopy( headInc->name, argv[i] );
133     }
134     else{
135     prevInc = headInc;
136     currInc = headInc->next;
137     while( currInc != NULL ){
138     prevInc = currInc;
139     currInc = previnc->next;
140     }
141     currInc = new includeLinked;
142     currInc->next = NULL;
143     strcopy( currInc->name, argv[i] );
144     prevInc->next = currInc;
145     }
146    
147     done = 1;
148     break;
149    
150 mmeineke 495 case 'h':
151     // -h => give the usage
152    
153     usage();
154     break;
155    
156     case 'r':
157     // toggle random
158    
159     isRandom = 1;;
160     break;
161    
162     default:
163     sprintf(painCave.errMsg,
164 mmeineke 498 "Bad option \"-%c\"\n", current_flag);
165 mmeineke 495 painCave.isFatal = 0;
166     simError();
167     usage();
168     }
169     j++;
170     current_flag = argv[i][j];
171     }
172     }
173     }
174    
175     else{
176    
177     if( in_name != NULL ){
178     sprintf( painCave.errMsg,
179     "Error at \"%s\", program does not support\n"
180     "more than one input file.\n"
181     "\n",
182     argv[i]);
183     painCave.isFatal = 0;
184     simError();
185     usage();
186     }
187    
188     in_name = argv[i];
189     }
190     }
191    
192     if(in_name == NULL){
193 mmeineke 498 sprintf( painCave.errMsg,
194     "No input bass file was specified.\n");
195     painCave.isFatal = 0;
196     simError();
197 mmeineke 495 usage();
198     }
199 mmeineke 498
200     if( sysType < 0 ){
201     sprintf( painCave.errMsg,
202     "No system type was specified.\n");
203     painCave.isFatal = 0;
204     simError();
205     usage();
206     }
207 mmeineke 495
208    
209 mmeineke 498 // if no output prefix is given default to "donkey".
210    
211     if( !have_prefix ){
212     out_prefix = strdup( "donkey" );
213     }
214 mmeineke 495
215 mmeineke 501 // set command line info into the bassInfo struct
216    
217     bsInfo.outPrefix = out_prefix;
218     bsInfo.includes = headInc;
219    
220 mmeineke 498
221 mmeineke 501 // open and parse the bass file.
222    
223     set_interface_stamps( the_stamps, the_globals );
224     yacc_BASS( info.in_name );
225    
226     // set the easy ones first
227     bsInfo.targetTemp = the_globals->getTargetTemp();
228     bsInfo.dt = the_globals->getDt();
229     bsInfo.runTime = the_globals->getRunTime();
230    
231     // get the ones we know are there, yet still may need some work.
232     bsInfo.nComponents = the_globals->getNComponents();
233     strcpy( bsInfo.forceField, the_globals->getForceField() );
234    
235     // get the ensemble:
236     strcpy( bsInfo.ensemble, the_globals->getEnsemble() );
237     if( !strcasecmp( bsInfo.ensemble, "NPT" ) ) {
238    
239     if (the_globals->haveTargetPressure()){
240     bsInfo.targetPressure = the_globals->getTargetPressure();
241     bsInfo.havePressure = 1;
242     }
243     else {
244     sprintf( painCave.errMsg,
245     "sysBuild error: If you use the constant pressure\n"
246     " ensemble, you must set targetPressure.\n"
247     " This was found in the BASS file.\n");
248     painCave.isFatal = 1;
249     simError();
250     }
251    
252     if (the_globals->haveTauThermostat()){
253     bsInfo.tauThermostat = the_globals->getTauThermostat();
254     bsInfo.haveTauThermostat = 1;;
255     }
256     else if (the_globals->haveQmass()){
257     bsinfo.Qmass = the_globals->getQmass();
258     bsInfo.haveQmass = 1;
259     }
260     else {
261     sprintf( painCave.errMsg,
262     "sysBuild error: If you use one of the constant temperature\n"
263     " ensembles, you must set either tauThermostat or qMass.\n"
264     " Neither of these was found in the BASS file.\n");
265     painCave.isFatal = 1;
266     simError();
267     }
268    
269     if (the_globals->haveTauBarostat()){
270     bsInfo.tauBarostat = the_globals->getTauBarostat();
271     bsInfo.haveTauBarostat = 1;
272     }
273     else {
274     sprintf( painCave.errMsg,
275     "sysBuild error: If you use the constant pressure\n"
276     " ensemble, you must set tauBarostat.\n"
277     " This was found in the BASS file.\n");
278     painCave.isFatal = 1;
279     simError();
280     }
281    
282     }
283     else if ( !strcasecmp( bsInfo.ensemble, "NVT") ) {
284    
285     if (the_globals->haveTauThermostat()){
286     bsInfo.tauThermostat = the_globals->getTauThermostat();
287     bsInfo.haveTauThermostat = 1;
288     }
289     else if (the_globals->haveQmass()){
290     bsInfo.Qmass = the_globals->getQmass();
291     bsInfo.haveQmass = 1;
292     }
293     else {
294     sprintf( painCave.errMsg,
295     "sysBuild error: If you use one of the constant temperature\n"
296     " ensembles, you must set either tauThermostat or qMass.\n"
297     " Neither of these was found in the BASS file.\n");
298     painCave.isFatal = 1;
299     simError();
300     }
301    
302     }
303     else if ( !strcasecmp( bsInfo.ensemble, "NVE") ) {
304    
305     // nothing special for now
306     }
307     else {
308     sprintf( painCave.errMsg,
309     "sysBuild Warning. Unrecognized Ensemble -> %s, "
310     "reverting to NVE for this simulation.\n",
311     ensemble );
312     painCave.isFatal = 0;
313     simError();
314     strcpy( bsInfo.ensemble, "NVE" );
315     }
316    
317    
318     // get the components and calculate the tot_nMol and indvidual n_mol
319    
320     the_components = the_globals->getComponents();
321     bsInfo.componentsNmol = new int[bsInfo.nComponents];
322     bsInfo.compStamps = new MoleculeStamp*[bsInfo.nComponents];
323     bsInfo.totNmol = 0;
324     for( i=0; i<bsInfo.nComponents; i++ ){
325    
326     if( !the_components[i]->haveNMol() ){
327     // we have a problem
328     sprintf( painCave.errMsg,
329     "sysBuild Error. No component NMol"
330     " given. Cannot calculate the number of atoms.\n" );
331     painCave.isFatal = 1;
332     simError();
333     }
334    
335     bsInfo.totNmol += the_components[i]->getNMol();
336     bsInfo.componentsNmol[i] = the_components[i]->getNMol();
337     }
338    
339     // make an array of molecule stamps that match the components used.
340     // also extract the used stamps out into a separate linked list
341    
342     for( i=0; i<bsInfo.nComponents; i++ ){
343    
344     id = the_components[i]->getType();
345     bsInfo.compStamps[i] = NULL;
346    
347     // check to make sure the component isn't already in the list
348    
349     bsInfo.compStamps[i] = headStamp->match( id );
350     if( bsInfo.compStamps[i] == NULL ){
351    
352     // extract the component from the list;
353    
354     currStamp = the_stamps->extractMolStamp( id );
355     if( currStamp == NULL ){
356     sprintf( painCave.errMsg,
357     "sysBuild error: Component \"%s\" was not found in the "
358     "list of declared molecules\n",
359     id );
360     painCave.isFatal = 1;
361     simError();
362     }
363    
364     headStamp->add( currStamp );
365     bsInfo.compStamps[i] = headStamp->match( id );
366     }
367     }
368    
369     // get and set the boxSize
370    
371     if( the_globals->haveBox() ){
372     bsInfo.boxX = the_globals->getBox();
373     bsInfo.boxY = the_globals->getBox();
374     bsinfo.boxZ = the_globals->getBox();
375     }
376     else if( the_globals->haveDensity() ){
377    
378     double vol;
379     vol = (double)tot_nmol / the_globals->getDensity();
380     bsInfo.boxX = pow( vol, ( 1.0 / 3.0 ) );
381     bsInfo.boxY = simnfo->box_x;
382     bsInfo.boxZ = simnfo->box_x;
383     }
384     else{
385     if( !the_globals->haveBoxX() ){
386     sprintf( painCave.errMsg,
387     "sysBuild error, no periodic BoxX size given.\n" );
388     painCave.isFatal = 1;
389     simError();
390     }
391     bsInfo.boxX = the_globals->getBoxX();
392    
393     if( !the_globals->haveBoxY() ){
394     sprintf( painCave.errMsg,
395     "sysBuild error, no periodic BoxY size given.\n" );
396     painCave.isFatal = 1;
397     simError();
398     }
399     bsInfo.boxY = the_globals->getBoxY();
400    
401     if( !the_globals->haveBoxZ() ){
402     sprintf( painCave.errMsg,
403     "SimSetup error, no periodic BoxZ size given.\n" );
404     painCave.isFatal = 1;
405     simError();
406     }
407     bsInfo.boxZ = the_globals->getBoxZ();
408     }
409    
410    
411     //************************************************************
412     // that should be all we need from bass. now to switch to the
413     // appropriate system builder.
414     // ***********************************************************
415    
416    
417 mmeineke 498 switch( sysType ){
418    
419     case BILAYER:
420    
421 mmeineke 501 buildBilayer( isRandom );
422 mmeineke 498 break;
423    
424     default:
425     sprintf( painCave.errMsg,
426     "Unknown system type: %d\n", sysType );
427     painCave.isFatal = 1;
428     simError();
429     }
430 mmeineke 495
431 mmeineke 501
432    
433     // clean up memory;
434    
435     if( headStamp!= NULL ) delete headStamp;
436     if( the_stamps != NULL ) delete the_stamps;
437     if( the_globals != NULL ) delete the_globals;
438     if( the_components != NULL ) delete[] the_components;
439    
440     if( bsInfo.componentsNmol != NULL ) delete[] bsInfo.componentsNmol;
441     if( bsInfo.compStamps != NULL ) delete[] bsInfo.compStamps;
442     if( bsInfo.includes != NULL ){
443     prevInc = bsInfo.includes;
444     while( prevInc != NULL ){
445     currInc = prevInc->next;
446     delete prevInc;
447     prevInc = currInc;
448     }
449     }
450    
451 mmeineke 495 return 0;
452     }
453    
454    
455     /***************************************************************************
456     * prints out the usage for the command line arguments, then exits.
457     ***************************************************************************/
458    
459     void usage(){
460     (void)fprintf(stdout,
461     "The proper usage is: %s [options] <input bass>\n"
462     "\n"
463     "Options:\n"
464     "\n"
465     " short:\n"
466     " ------\n"
467     " -h Display this message\n"
468     " -o <prefix> The output prefix\n"
469 mmeineke 501 " -I <include> File name that should be included at the top of the\n"
470     " output bass file.\n"
471 mmeineke 495 " -r toggle the random option\n"
472     "\n"
473     " long:\n"
474     " -----\n"
475     " --bilayer Tries to build a basic bilayer with the specified number\n"
476     " of lipids in the input bass file. The bilayer will be\n"
477     " surrounded by the number of solvent molecules given\n"
478     " in the bass file.\n"
479     " -note: combined with \"-r\" the simulation will start in\n"
480     " an FCC lattice with randomly assigned latice\n"
481 mmeineke 498 " sites for all atoms involved.\n"
482 mmeineke 495 "\n"
483     "\n",
484     program_name);
485     exit(8);
486     }