ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/group/trunk/OOPSE/utils/sysbuilder/sysBuild.cpp
Revision: 678
Committed: Mon Aug 11 22:12:31 2003 UTC (20 years, 11 months ago) by chuckv
File size: 13933 byte(s)
Log Message:
Arranged sysbuilder into a subdirectory. Fixed some of sysbuilder to work with new
atom allocation in libmdtools.

File Contents

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