ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/group/trunk/OOPSE_old/src/mdtools/libmdCode/TraPPE_ExFF.cpp
Revision: 376
Committed: Fri Mar 21 15:24:37 2003 UTC (21 years, 3 months ago) by chuckv
File size: 41097 byte(s)
Log Message:
Bug fixes in TraPPE.
calc_LJ_FF.F90: Removed print lines.
TraPPE_ExFF.cpp: Fixed so idents are being set.

File Contents

# Content
1 #include <cstdlib>
2 #include <cstdio>
3 #include <cstring>
4
5 #include <iostream>
6 using namespace std;
7
8 #include "ForceFields.hpp"
9 #include "SRI.hpp"
10 #include "simError.h"
11
12 #include <fortranWrappers.hpp>
13
14 #ifdef IS_MPI
15 #include <mpi++.h>
16 #include "mpiForceField.h"
17 #endif // is_mpi
18
19 namespace TPE { // restrict the access of the folowing to this file only.
20
21
22 // Declare the structures that will be passed by MPI
23
24 typedef struct{
25 char name[15];
26 double mass;
27 double epslon;
28 double sigma;
29 double dipole;
30 double w0;
31 double v0;
32 int isSSD;
33 int isDipole;
34 int ident;
35 int last; // 0 -> default
36 // 1 -> tells nodes to stop listening
37 } atomStruct;
38
39
40 typedef struct{
41 char nameA[15];
42 char nameB[15];
43 char type[30];
44 double d0;
45 int last; // 0 -> default
46 // 1 -> tells nodes to stop listening
47 } bondStruct;
48
49
50 typedef struct{
51 char nameA[15];
52 char nameB[15];
53 char nameC[15];
54 char type[30];
55 double k1, k2, k3, t0;
56 int last; // 0 -> default
57 // 1 -> tells nodes to stop listening
58 } bendStruct;
59
60
61 typedef struct{
62 char nameA[15];
63 char nameB[15];
64 char nameC[15];
65 char nameD[15];
66 char type[30];
67 double k1, k2, k3, k4;
68 int last; // 0 -> default
69 // 1 -> tells nodes to stop listening
70 } torsionStruct;
71
72
73 int parseAtom( char *lineBuffer, int lineNum, atomStruct &info );
74 int parseBond( char *lineBuffer, int lineNum, bondStruct &info );
75 int parseBend( char *lineBuffer, int lineNum, bendStruct &info );
76 int parseTorsion( char *lineBuffer, int lineNum, torsionStruct &info );
77
78
79 #ifdef IS_MPI
80
81 MPI_Datatype mpiAtomStructType;
82 MPI_Datatype mpiBondStructType;
83 MPI_Datatype mpiBendStructType;
84 MPI_Datatype mpiTorsionStructType;
85
86 #endif
87
88 } // namespace
89
90 using namespace TPE;
91
92
93 //****************************************************************
94 // begins the actual forcefield stuff.
95 //****************************************************************
96
97
98 TraPPE_ExFF::TraPPE_ExFF(){
99
100 char fileName[200];
101 char* ffPath_env = "FORCE_PARAM_PATH";
102 char* ffPath;
103 char temp[200];
104 char errMsg[1000];
105
106 // do the funtion wrapping
107 wrapMeFF( this );
108
109
110 #ifdef IS_MPI
111 int i;
112
113 // **********************************************************************
114 // Init the atomStruct mpi type
115
116 atomStruct atomProto; // mpiPrototype
117 int atomBC[3] = {15,6,4}; // block counts
118 MPI_Aint atomDspls[3]; // displacements
119 MPI_Datatype atomMbrTypes[3]; // member mpi types
120
121 MPI_Address(&atomProto.name, &atomDspls[0]);
122 MPI_Address(&atomProto.mass, &atomDspls[1]);
123 MPI_Address(&atomProto.isSSD, &atomDspls[2]);
124
125 atomMbrTypes[0] = MPI_CHAR;
126 atomMbrTypes[1] = MPI_DOUBLE;
127 atomMbrTypes[2] = MPI_INT;
128
129 for (i=2; i >= 0; i--) atomDspls[i] -= atomDspls[0];
130
131 MPI_Type_struct(3, atomBC, atomDspls, atomMbrTypes, &mpiAtomStructType);
132 MPI_Type_commit(&mpiAtomStructType);
133
134
135 // **********************************************************************
136 // Init the bondStruct mpi type
137
138 bondStruct bondProto; // mpiPrototype
139 int bondBC[3] = {60,1,1}; // block counts
140 MPI_Aint bondDspls[3]; // displacements
141 MPI_Datatype bondMbrTypes[3]; // member mpi types
142
143 MPI_Address(&bondProto.nameA, &bondDspls[0]);
144 MPI_Address(&bondProto.d0, &bondDspls[1]);
145 MPI_Address(&bondProto.last, &bondDspls[2]);
146
147 bondMbrTypes[0] = MPI_CHAR;
148 bondMbrTypes[1] = MPI_DOUBLE;
149 bondMbrTypes[2] = MPI_INT;
150
151 for (i=2; i >= 0; i--) bondDspls[i] -= bondDspls[0];
152
153 MPI_Type_struct(3, bondBC, bondDspls, bondMbrTypes, &mpiBondStructType);
154 MPI_Type_commit(&mpiBondStructType);
155
156
157 // **********************************************************************
158 // Init the bendStruct mpi type
159
160 bendStruct bendProto; // mpiPrototype
161 int bendBC[3] = {75,4,1}; // block counts
162 MPI_Aint bendDspls[3]; // displacements
163 MPI_Datatype bendMbrTypes[3]; // member mpi types
164
165 MPI_Address(&bendProto.nameA, &bendDspls[0]);
166 MPI_Address(&bendProto.k1, &bendDspls[1]);
167 MPI_Address(&bendProto.last, &bendDspls[2]);
168
169 bendMbrTypes[0] = MPI_CHAR;
170 bendMbrTypes[1] = MPI_DOUBLE;
171 bendMbrTypes[2] = MPI_INT;
172
173 for (i=2; i >= 0; i--) bendDspls[i] -= bendDspls[0];
174
175 MPI_Type_struct(3, bendBC, bendDspls, bendMbrTypes, &mpiBendStructType);
176 MPI_Type_commit(&mpiBendStructType);
177
178
179 // **********************************************************************
180 // Init the torsionStruct mpi type
181
182 torsionStruct torsionProto; // mpiPrototype
183 int torsionBC[3] = {90,4,1}; // block counts
184 MPI_Aint torsionDspls[3]; // displacements
185 MPI_Datatype torsionMbrTypes[3]; // member mpi types
186
187 MPI_Address(&torsionProto.nameA, &torsionDspls[0]);
188 MPI_Address(&torsionProto.k1, &torsionDspls[1]);
189 MPI_Address(&torsionProto.last, &torsionDspls[2]);
190
191 torsionMbrTypes[0] = MPI_CHAR;
192 torsionMbrTypes[1] = MPI_DOUBLE;
193 torsionMbrTypes[2] = MPI_INT;
194
195 for (i=2; i >= 0; i--) torsionDspls[i] -= torsionDspls[0];
196
197 MPI_Type_struct(3, torsionBC, torsionDspls, torsionMbrTypes,
198 &mpiTorsionStructType);
199 MPI_Type_commit(&mpiTorsionStructType);
200
201 // ***********************************************************************
202
203 if( worldRank == 0 ){
204 #endif
205
206 // generate the force file name
207
208 strcpy( fileName, "TraPPE_Ex.frc" );
209 // fprintf( stderr,"Trying to open %s\n", fileName );
210
211 // attempt to open the file in the current directory first.
212
213 frcFile = fopen( fileName, "r" );
214
215 if( frcFile == NULL ){
216
217 // next see if the force path enviorment variable is set
218
219 ffPath = getenv( ffPath_env );
220 if( ffPath == NULL ) {
221 STR_DEFINE(ffPath, FRC_PATH );
222 }
223
224
225 strcpy( temp, ffPath );
226 strcat( temp, "/" );
227 strcat( temp, fileName );
228 strcpy( fileName, temp );
229
230 frcFile = fopen( fileName, "r" );
231
232 if( frcFile == NULL ){
233
234 sprintf( painCave.errMsg,
235 "Error opening the force field parameter file: %s\n"
236 "Have you tried setting the FORCE_PARAM_PATH environment "
237 "vairable?\n",
238 fileName );
239 painCave.isFatal = 1;
240 simError();
241 }
242 }
243
244 #ifdef IS_MPI
245 }
246
247 sprintf( checkPointMsg, "TraPPE_ExFF file opened sucessfully." );
248 MPIcheckPoint();
249
250 #endif // is_mpi
251 }
252
253
254 TraPPE_ExFF::~TraPPE_ExFF(){
255
256 #ifdef IS_MPI
257 if( worldRank == 0 ){
258 #endif // is_mpi
259
260 fclose( frcFile );
261
262 #ifdef IS_MPI
263 }
264 #endif // is_mpi
265 }
266
267 void TraPPE_ExFF::initForceField( int ljMixRule ){
268
269 initFortran( ljMixRule, entry_plug->useReactionField );
270 }
271
272
273 void TraPPE_ExFF::initializeAtoms( void ){
274
275 class LinkedType {
276 public:
277 LinkedType(){
278 next = NULL;
279 name[0] = '\0';
280 }
281 ~LinkedType(){ if( next != NULL ) delete next; }
282
283 LinkedType* find(char* key){
284 if( !strcmp(name, key) ) return this;
285 if( next != NULL ) return next->find(key);
286 return NULL;
287 }
288
289 void add( atomStruct &info ){
290
291 // check for duplicates
292
293 if( !strcmp( info.name, name ) ){
294 sprintf( painCave.errMsg,
295 "Duplicate TraPPE_Ex atom type \"%s\" found in "
296 "the TraPPE_ExFF param file./n",
297 name );
298 painCave.isFatal = 1;
299 simError();
300 }
301
302 if( next != NULL ) next->add(info);
303 else{
304 next = new LinkedType();
305 strcpy(next->name, info.name);
306 next->isDipole = info.isDipole;
307 next->isSSD = info.isSSD;
308 next->mass = info.mass;
309 next->epslon = info.epslon;
310 next->sigma = info.sigma;
311 next->dipole = info.dipole;
312 next->w0 = info.w0;
313 next->v0 = info.v0;
314 next->ident = info.ident;
315 }
316 }
317
318 #ifdef IS_MPI
319
320 void duplicate( atomStruct &info ){
321 strcpy(info.name, name);
322 info.isDipole = isDipole;
323 info.isSSD = isSSD;
324 info.mass = mass;
325 info.epslon = epslon;
326 info.sigma = sigma;
327 info.dipole = dipole;
328 info.w0 = w0;
329 info.v0 = v0;
330 info.last = 0;
331 }
332
333
334 #endif
335
336 char name[15];
337 int isDipole;
338 int isSSD;
339 double mass;
340 double epslon;
341 double sigma;
342 double dipole;
343 double w0;
344 double v0;
345 int ident;
346 LinkedType* next;
347 };
348
349 LinkedType* headAtomType;
350 LinkedType* currentAtomType;
351 atomStruct info;
352 info.last = 1; // initialize last to have the last set.
353 // if things go well, last will be set to 0
354
355
356
357 int i;
358 int identNum;
359
360 Atom** the_atoms;
361 int nAtoms;
362 the_atoms = entry_plug->atoms;
363 nAtoms = entry_plug->n_atoms;
364
365 //////////////////////////////////////////////////
366 // a quick water fix
367
368 double waterI[3][3];
369 waterI[0][0] = 1.76958347772500;
370 waterI[0][1] = 0.0;
371 waterI[0][2] = 0.0;
372
373 waterI[1][0] = 0.0;
374 waterI[1][1] = 0.614537057924513;
375 waterI[1][2] = 0.0;
376
377 waterI[2][0] = 0.0;
378 waterI[2][1] = 0.0;
379 waterI[2][2] = 1.15504641980049;
380
381
382 double headI[3][3];
383 headI[0][0] = 1125;
384 headI[0][1] = 0.0;
385 headI[0][2] = 0.0;
386
387 headI[1][0] = 0.0;
388 headI[1][1] = 1125;
389 headI[1][2] = 0.0;
390
391 headI[2][0] = 0.0;
392 headI[2][1] = 0.0;
393 headI[2][2] = 250;
394
395
396
397 //////////////////////////////////////////////////
398
399
400 #ifdef IS_MPI
401 if( worldRank == 0 ){
402 #endif
403
404 // read in the atom types.
405
406 headAtomType = new LinkedType;
407
408 fastForward( "AtomTypes", "initializeAtoms" );
409
410 // we are now at the AtomTypes section.
411
412 eof_test = fgets( readLine, sizeof(readLine), frcFile );
413 lineNum++;
414
415
416 // read a line, and start parseing out the atom types
417
418 if( eof_test == NULL ){
419 sprintf( painCave.errMsg,
420 "Error in reading Atoms from force file at line %d.\n",
421 lineNum );
422 painCave.isFatal = 1;
423 simError();
424 }
425
426 identNum = 1;
427 // stop reading at end of file, or at next section
428 while( readLine[0] != '#' && eof_test != NULL ){
429
430 // toss comment lines
431 if( readLine[0] != '!' ){
432
433 // the parser returns 0 if the line was blank
434 if( parseAtom( readLine, lineNum, info ) ){
435 info.ident = identNum;
436 headAtomType->add( info );;
437 identNum++;
438 }
439 }
440 eof_test = fgets( readLine, sizeof(readLine), frcFile );
441 lineNum++;
442 }
443
444 #ifdef IS_MPI
445
446 // send out the linked list to all the other processes
447
448 sprintf( checkPointMsg,
449 "TraPPE_ExFF atom structures read successfully." );
450 MPIcheckPoint();
451
452 currentAtomType = headAtomType->next; //skip the first element who is a place holder.
453 while( currentAtomType != NULL ){
454 currentAtomType->duplicate( info );
455
456
457
458 sendFrcStruct( &info, mpiAtomStructType );
459
460 sprintf( checkPointMsg,
461 "successfully sent TraPPE_Ex force type: \"%s\"\n",
462 info.name );
463 MPIcheckPoint();
464
465 currentAtomType = currentAtomType->next;
466 }
467 info.last = 1;
468 sendFrcStruct( &info, mpiAtomStructType );
469
470 }
471
472 else{
473
474 // listen for node 0 to send out the force params
475
476 MPIcheckPoint();
477
478 headAtomType = new LinkedType;
479 recieveFrcStruct( &info, mpiAtomStructType );
480
481 while( !info.last ){
482
483
484
485 headAtomType->add( info );
486
487 MPIcheckPoint();
488
489 recieveFrcStruct( &info, mpiAtomStructType );
490 }
491 }
492 #endif // is_mpi
493
494 // call new A_types in fortran
495
496 int isError;
497
498 // dummy variables
499
500 int isGB = 0;
501 int isLJ = 1;
502 double GB_dummy = 0.0;
503
504
505 currentAtomType = headAtomType;
506 while( currentAtomType != NULL ){
507
508 if(currentAtomType->isDipole) entry_plug->useReactionField = 1;
509 if(currentAtomType->isDipole) entry_plug->useDipole = 1;
510 if(currentAtomType->isSSD) entry_plug->useSticky = 1;
511
512 if( currentAtomType->name[0] != '\0' ){
513 isError = 0;
514 makeAtype( &(currentAtomType->ident),
515 &isLJ,
516 &(currentAtomType->isSSD),
517 &(currentAtomType->isDipole),
518 &isGB,
519 &(currentAtomType->epslon),
520 &(currentAtomType->sigma),
521 &(currentAtomType->dipole),
522 &(currentAtomType->w0),
523 &(currentAtomType->v0),
524 &GB_dummy,
525 &GB_dummy,
526 &GB_dummy,
527 &GB_dummy,
528 &GB_dummy,
529 &GB_dummy,
530 &isError );
531 if( isError ){
532 sprintf( painCave.errMsg,
533 "Error initializing the \"%s\" atom type in fortran\n",
534 currentAtomType->name );
535 painCave.isFatal = 1;
536 simError();
537 }
538 }
539 currentAtomType = currentAtomType->next;
540 }
541
542 #ifdef IS_MPI
543 sprintf( checkPointMsg,
544 "TraPPE_ExFF atom structures successfully sent to fortran\n" );
545 MPIcheckPoint();
546 #endif // is_mpi
547
548
549 // initialize the atoms
550
551 double bigSigma = 0.0;
552 DirectionalAtom* dAtom;
553
554 for( i=0; i<nAtoms; i++ ){
555
556 currentAtomType = headAtomType->find( the_atoms[i]->getType() );
557 if( currentAtomType == NULL ){
558 sprintf( painCave.errMsg,
559 "AtomType error, %s not found in force file.\n",
560 the_atoms[i]->getType() );
561 painCave.isFatal = 1;
562 simError();
563 }
564
565 the_atoms[i]->setMass( currentAtomType->mass );
566 the_atoms[i]->setEpslon( currentAtomType->epslon );
567 the_atoms[i]->setSigma( currentAtomType->sigma );
568 the_atoms[i]->setIdent( currentAtomType->ident );
569 the_atoms[i]->setLJ();
570
571 if( bigSigma < currentAtomType->sigma ) bigSigma = currentAtomType->sigma;
572
573 if( currentAtomType->isDipole ){
574 if( the_atoms[i]->isDirectional() ){
575
576 dAtom = (DirectionalAtom *) the_atoms[i];
577 dAtom->setMu( currentAtomType->dipole );
578 dAtom->setHasDipole( 1 );
579 dAtom->setJx( 0.0 );
580 dAtom->setJy( 0.0 );
581 dAtom->setJz( 0.0 );
582
583 if(!strcmp("SSD",the_atoms[i]->getType())){
584 dAtom->setI( waterI );
585 dAtom->setSSD( 1 );
586 }
587 else if(!strcmp("HEAD",the_atoms[i]->getType())){
588 dAtom->setI( headI );
589 dAtom->setSSD( 0 );
590 }
591 else{
592 sprintf(painCave.errMsg,
593 "AtmType error, %s does not have a moment of inertia set.\n",
594 the_atoms[i]->getType() );
595 painCave.isFatal = 1;
596 simError();
597 }
598 entry_plug->n_dipoles++;
599 }
600 else{
601
602 sprintf( painCave.errMsg,
603 "TraPPE_ExFF error: Atom \"%s\" is a dipole, yet no standard"
604 " orientation was specifed in the BASS file.\n",
605 currentAtomType->name );
606 painCave.isFatal = 1;
607 simError();
608 }
609 }
610 else{
611 if( the_atoms[i]->isDirectional() ){
612 sprintf( painCave.errMsg,
613 "TraPPE_ExFF error: Atom \"%s\" was given a standard"
614 "orientation in the BASS file, yet it is not a dipole.\n",
615 currentAtomType->name);
616 painCave.isFatal = 1;
617 simError();
618 }
619 }
620 }
621
622 #ifdef IS_MPI
623 double tempBig = bigSigma;
624 MPI::COMM_WORLD.Allreduce( &tempBig, &bigSigma, 1, MPI_DOUBLE, MPI_MAX );
625 #endif //is_mpi
626
627 //calc rCut and rList
628
629 entry_plug->rCut = 2.5 * bigSigma;
630
631 if(entry_plug->rCut > (entry_plug->box_x / 2.0))
632 entry_plug->rCut = entry_plug->box_x / 2.0;
633
634 if(entry_plug->rCut > (entry_plug->box_y / 2.0))
635 entry_plug->rCut = entry_plug->box_y / 2.0;
636
637 if(entry_plug->rCut > (entry_plug->box_z / 2.0))
638 entry_plug->rCut = entry_plug->box_z / 2.0;
639
640 entry_plug->rList = entry_plug->rCut + 1.0;
641
642 entry_plug->useLJ = 1; // use Lennard Jones is on by default
643
644 // clean up the memory
645
646 delete headAtomType;
647
648 #ifdef IS_MPI
649 sprintf( checkPointMsg, "TraPPE_Ex atoms initialized succesfully" );
650 MPIcheckPoint();
651 #endif // is_mpi
652
653 }
654
655 void TraPPE_ExFF::initializeBonds( bond_pair* the_bonds ){
656
657 class LinkedType {
658 public:
659 LinkedType(){
660 next = NULL;
661 nameA[0] = '\0';
662 nameB[0] = '\0';
663 type[0] = '\0';
664 }
665 ~LinkedType(){ if( next != NULL ) delete next; }
666
667 LinkedType* find(char* key1, char* key2){
668 if( !strcmp(nameA, key1 ) && !strcmp( nameB, key2 ) ) return this;
669 if( !strcmp(nameA, key2 ) && !strcmp( nameB, key1 ) ) return this;
670 if( next != NULL ) return next->find(key1, key2);
671 return NULL;
672 }
673
674
675 void add( bondStruct &info ){
676
677 // check for duplicates
678 int dup = 0;
679
680 if( !strcmp(nameA, info.nameA ) && !strcmp( nameB, info.nameB ) ) dup = 1;
681 if( !strcmp(nameA, info.nameB ) && !strcmp( nameB, info.nameA ) ) dup = 1;
682
683 if(dup){
684 sprintf( painCave.errMsg,
685 "Duplicate TraPPE_Ex bond type \"%s - %s\" found in "
686 "the TraPPE_ExFF param file./n",
687 nameA, nameB );
688 painCave.isFatal = 1;
689 simError();
690 }
691
692
693 if( next != NULL ) next->add(info);
694 else{
695 next = new LinkedType();
696 strcpy(next->nameA, info.nameA);
697 strcpy(next->nameB, info.nameB);
698 strcpy(next->type, info.type);
699 next->d0 = info.d0;
700 }
701 }
702
703 #ifdef IS_MPI
704 void duplicate( bondStruct &info ){
705 strcpy(info.nameA, nameA);
706 strcpy(info.nameB, nameB);
707 strcpy(info.type, type);
708 info.d0 = d0;
709 info.last = 0;
710 }
711
712
713 #endif
714
715 char nameA[15];
716 char nameB[15];
717 char type[30];
718 double d0;
719
720 LinkedType* next;
721 };
722
723
724
725 LinkedType* headBondType;
726 LinkedType* currentBondType;
727 bondStruct info;
728 info.last = 1; // initialize last to have the last set.
729 // if things go well, last will be set to 0
730
731 SRI **the_sris;
732 Atom** the_atoms;
733 int nBonds;
734 the_sris = entry_plug->sr_interactions;
735 the_atoms = entry_plug->atoms;
736 nBonds = entry_plug->n_bonds;
737
738 int i, a, b;
739 char* atomA;
740 char* atomB;
741
742 #ifdef IS_MPI
743 if( worldRank == 0 ){
744 #endif
745
746 // read in the bond types.
747
748 headBondType = new LinkedType;
749
750 fastForward( "BondTypes", "initializeBonds" );
751
752 // we are now at the bondTypes section
753
754 eof_test = fgets( readLine, sizeof(readLine), frcFile );
755 lineNum++;
756
757
758 // read a line, and start parseing out the atom types
759
760 if( eof_test == NULL ){
761 sprintf( painCave.errMsg,
762 "Error in reading bonds from force file at line %d.\n",
763 lineNum );
764 painCave.isFatal = 1;
765 simError();
766 }
767
768 // stop reading at end of file, or at next section
769 while( readLine[0] != '#' && eof_test != NULL ){
770
771 // toss comment lines
772 if( readLine[0] != '!' ){
773
774 // the parser returns 0 if the line was blank
775 if( parseBond( readLine, lineNum, info ) ){
776 headBondType->add( info );
777 }
778 }
779 eof_test = fgets( readLine, sizeof(readLine), frcFile );
780 lineNum++;
781 }
782
783 #ifdef IS_MPI
784
785 // send out the linked list to all the other processes
786
787 sprintf( checkPointMsg,
788 "TraPPE_Ex bond structures read successfully." );
789 MPIcheckPoint();
790
791 currentBondType = headBondType;
792 while( currentBondType != NULL ){
793 currentBondType->duplicate( info );
794 sendFrcStruct( &info, mpiBondStructType );
795 currentBondType = currentBondType->next;
796 }
797 info.last = 1;
798 sendFrcStruct( &info, mpiBondStructType );
799
800 }
801
802 else{
803
804 // listen for node 0 to send out the force params
805
806 MPIcheckPoint();
807
808 headBondType = new LinkedType;
809 recieveFrcStruct( &info, mpiBondStructType );
810 while( !info.last ){
811
812 headBondType->add( info );
813 recieveFrcStruct( &info, mpiBondStructType );
814 }
815 }
816 #endif // is_mpi
817
818
819 // initialize the Bonds
820
821
822 for( i=0; i<nBonds; i++ ){
823
824 a = the_bonds[i].a;
825 b = the_bonds[i].b;
826
827 atomA = the_atoms[a]->getType();
828 atomB = the_atoms[b]->getType();
829 currentBondType = headBondType->find( atomA, atomB );
830 if( currentBondType == NULL ){
831 sprintf( painCave.errMsg,
832 "BondType error, %s - %s not found in force file.\n",
833 atomA, atomB );
834 painCave.isFatal = 1;
835 simError();
836 }
837
838 if( !strcmp( currentBondType->type, "fixed" ) ){
839
840 the_sris[i] = new ConstrainedBond( *the_atoms[a],
841 *the_atoms[b],
842 currentBondType->d0 );
843 entry_plug->n_constraints++;
844 }
845 }
846
847
848 // clean up the memory
849
850 delete headBondType;
851
852 #ifdef IS_MPI
853 sprintf( checkPointMsg, "TraPPE_Ex bonds initialized succesfully" );
854 MPIcheckPoint();
855 #endif // is_mpi
856
857 }
858
859 void TraPPE_ExFF::initializeBends( bend_set* the_bends ){
860
861 class LinkedType {
862 public:
863 LinkedType(){
864 next = NULL;
865 nameA[0] = '\0';
866 nameB[0] = '\0';
867 nameC[0] = '\0';
868 type[0] = '\0';
869 }
870 ~LinkedType(){ if( next != NULL ) delete next; }
871
872 LinkedType* find( char* key1, char* key2, char* key3 ){
873 if( !strcmp( nameA, key1 ) && !strcmp( nameB, key2 )
874 && !strcmp( nameC, key3 ) ) return this;
875 if( !strcmp( nameA, key3 ) && !strcmp( nameB, key2 )
876 && !strcmp( nameC, key1 ) ) return this;
877 if( next != NULL ) return next->find(key1, key2, key3);
878 return NULL;
879 }
880
881 void add( bendStruct &info ){
882
883 // check for duplicates
884 int dup = 0;
885
886 if( !strcmp( nameA, info.nameA ) && !strcmp( nameB, info.nameB )
887 && !strcmp( nameC, info.nameC ) ) dup = 1;
888 if( !strcmp( nameA, info.nameC ) && !strcmp( nameB, info.nameB )
889 && !strcmp( nameC, info.nameA ) ) dup = 1;
890
891 if(dup){
892 sprintf( painCave.errMsg,
893 "Duplicate TraPPE_Ex bend type \"%s - %s - %s\" found in "
894 "the TraPPE_ExFF param file./n",
895 nameA, nameB, nameC );
896 painCave.isFatal = 1;
897 simError();
898 }
899
900 if( next != NULL ) next->add(info);
901 else{
902 next = new LinkedType();
903 strcpy(next->nameA, info.nameA);
904 strcpy(next->nameB, info.nameB);
905 strcpy(next->nameC, info.nameC);
906 strcpy(next->type, info.type);
907 next->k1 = info.k1;
908 next->k2 = info.k2;
909 next->k3 = info.k3;
910 next->t0 = info.t0;
911 }
912 }
913
914 #ifdef IS_MPI
915
916 void duplicate( bendStruct &info ){
917 strcpy(info.nameA, nameA);
918 strcpy(info.nameB, nameB);
919 strcpy(info.nameC, nameC);
920 strcpy(info.type, type);
921 info.k1 = k1;
922 info.k2 = k2;
923 info.k3 = k3;
924 info.t0 = t0;
925 info.last = 0;
926 }
927
928 #endif // is_mpi
929
930 char nameA[15];
931 char nameB[15];
932 char nameC[15];
933 char type[30];
934 double k1, k2, k3, t0;
935
936 LinkedType* next;
937 };
938
939 LinkedType* headBendType;
940 LinkedType* currentBendType;
941 bendStruct info;
942 info.last = 1; // initialize last to have the last set.
943 // if things go well, last will be set to 0
944
945 QuadraticBend* qBend;
946 GhostBend* gBend;
947 SRI **the_sris;
948 Atom** the_atoms;
949 int nBends;
950 the_sris = entry_plug->sr_interactions;
951 the_atoms = entry_plug->atoms;
952 nBends = entry_plug->n_bends;
953
954 int i, a, b, c;
955 char* atomA;
956 char* atomB;
957 char* atomC;
958
959
960 #ifdef IS_MPI
961 if( worldRank == 0 ){
962 #endif
963
964 // read in the bend types.
965
966 headBendType = new LinkedType;
967
968 fastForward( "BendTypes", "initializeBends" );
969
970 // we are now at the bendTypes section
971
972 eof_test = fgets( readLine, sizeof(readLine), frcFile );
973 lineNum++;
974
975 // read a line, and start parseing out the bend types
976
977 if( eof_test == NULL ){
978 sprintf( painCave.errMsg,
979 "Error in reading bends from force file at line %d.\n",
980 lineNum );
981 painCave.isFatal = 1;
982 simError();
983 }
984
985 // stop reading at end of file, or at next section
986 while( readLine[0] != '#' && eof_test != NULL ){
987
988 // toss comment lines
989 if( readLine[0] != '!' ){
990
991 // the parser returns 0 if the line was blank
992 if( parseBend( readLine, lineNum, info ) ){
993 headBendType->add( info );
994 }
995 }
996 eof_test = fgets( readLine, sizeof(readLine), frcFile );
997 lineNum++;
998 }
999
1000 #ifdef IS_MPI
1001
1002 // send out the linked list to all the other processes
1003
1004 sprintf( checkPointMsg,
1005 "TraPPE_Ex bend structures read successfully." );
1006 MPIcheckPoint();
1007
1008 currentBendType = headBendType;
1009 while( currentBendType != NULL ){
1010 currentBendType->duplicate( info );
1011 sendFrcStruct( &info, mpiBendStructType );
1012 currentBendType = currentBendType->next;
1013 }
1014 info.last = 1;
1015 sendFrcStruct( &info, mpiBendStructType );
1016
1017 }
1018
1019 else{
1020
1021 // listen for node 0 to send out the force params
1022
1023 MPIcheckPoint();
1024
1025 headBendType = new LinkedType;
1026 recieveFrcStruct( &info, mpiBendStructType );
1027 while( !info.last ){
1028
1029 headBendType->add( info );
1030 recieveFrcStruct( &info, mpiBendStructType );
1031 }
1032 }
1033 #endif // is_mpi
1034
1035 // initialize the Bends
1036
1037 int index;
1038
1039 for( i=0; i<nBends; i++ ){
1040
1041 a = the_bends[i].a;
1042 b = the_bends[i].b;
1043 c = the_bends[i].c;
1044
1045 atomA = the_atoms[a]->getType();
1046 atomB = the_atoms[b]->getType();
1047
1048 if( the_bends[i].isGhost ) atomC = "GHOST";
1049 else atomC = the_atoms[c]->getType();
1050
1051 currentBendType = headBendType->find( atomA, atomB, atomC );
1052 if( currentBendType == NULL ){
1053 sprintf( painCave.errMsg, "BendType error, %s - %s - %s not found"
1054 " in force file.\n",
1055 atomA, atomB, atomC );
1056 painCave.isFatal = 1;
1057 simError();
1058 }
1059
1060 if( !strcmp( currentBendType->type, "quadratic" ) ){
1061
1062 index = i + entry_plug->n_bonds;
1063
1064 if( the_bends[i].isGhost){
1065
1066 if( the_bends[i].ghost == b ){
1067 // do nothing
1068 }
1069 else if( the_bends[i].ghost == a ){
1070 c = a;
1071 a = b;
1072 b = a;
1073 }
1074 else{
1075 sprintf( painCave.errMsg,
1076 "BendType error, %s - %s - %s,\n"
1077 " --> central atom is not "
1078 "correctly identified with the "
1079 "\"ghostVectorSource = \" tag.\n",
1080 atomA, atomB, atomC );
1081 painCave.isFatal = 1;
1082 simError();
1083 }
1084
1085 gBend = new GhostBend( *the_atoms[a],
1086 *the_atoms[b] );
1087 gBend->setConstants( currentBendType->k1,
1088 currentBendType->k2,
1089 currentBendType->k3,
1090 currentBendType->t0 );
1091 the_sris[index] = gBend;
1092 }
1093 else{
1094 qBend = new QuadraticBend( *the_atoms[a],
1095 *the_atoms[b],
1096 *the_atoms[c] );
1097 qBend->setConstants( currentBendType->k1,
1098 currentBendType->k2,
1099 currentBendType->k3,
1100 currentBendType->t0 );
1101 the_sris[index] = qBend;
1102 }
1103 }
1104 }
1105
1106
1107 // clean up the memory
1108
1109 delete headBendType;
1110
1111 #ifdef IS_MPI
1112 sprintf( checkPointMsg, "TraPPE_Ex bends initialized succesfully" );
1113 MPIcheckPoint();
1114 #endif // is_mpi
1115
1116 }
1117
1118 void TraPPE_ExFF::initializeTorsions( torsion_set* the_torsions ){
1119
1120 class LinkedType {
1121 public:
1122 LinkedType(){
1123 next = NULL;
1124 nameA[0] = '\0';
1125 nameB[0] = '\0';
1126 nameC[0] = '\0';
1127 type[0] = '\0';
1128 }
1129 ~LinkedType(){ if( next != NULL ) delete next; }
1130
1131 LinkedType* find( char* key1, char* key2, char* key3, char* key4 ){
1132
1133
1134
1135
1136 if( !strcmp( nameA, key1 ) && !strcmp( nameB, key2 ) &&
1137 !strcmp( nameC, key3 ) && !strcmp( nameD, key4 ) ) return this;
1138
1139 if( !strcmp( nameA, key4 ) && !strcmp( nameB, key3 ) &&
1140 !strcmp( nameC, key2 ) && !strcmp( nameD, key1 ) ) return this;
1141
1142 if( next != NULL ) return next->find(key1, key2, key3, key4);
1143 return NULL;
1144 }
1145
1146 void add( torsionStruct &info ){
1147
1148 // check for duplicates
1149 int dup = 0;
1150
1151 if( !strcmp( nameA, info.nameA ) && !strcmp( nameB, info.nameB ) &&
1152 !strcmp( nameC, info.nameC ) && !strcmp( nameD, info.nameD ) ) dup = 1;
1153
1154 if( !strcmp( nameA, info.nameD ) && !strcmp( nameB, info.nameC ) &&
1155 !strcmp( nameC, info.nameB ) && !strcmp( nameD, info.nameA ) ) dup = 1;
1156
1157 if(dup){
1158 sprintf( painCave.errMsg,
1159 "Duplicate TraPPE_Ex torsion type \"%s - %s - %s - %s\" found in "
1160 "the TraPPE_ExFF param file./n", nameA, nameB, nameC, nameD );
1161 painCave.isFatal = 1;
1162 simError();
1163 }
1164
1165 if( next != NULL ) next->add(info);
1166 else{
1167 next = new LinkedType();
1168 strcpy(next->nameA, info.nameA);
1169 strcpy(next->nameB, info.nameB);
1170 strcpy(next->nameC, info.nameC);
1171 strcpy(next->nameD, info.nameD);
1172 strcpy(next->type, info.type);
1173 next->k1 = info.k1;
1174 next->k2 = info.k2;
1175 next->k3 = info.k3;
1176 next->k4 = info.k4;
1177
1178 }
1179 }
1180
1181 #ifdef IS_MPI
1182
1183 void duplicate( torsionStruct &info ){
1184 strcpy(info.nameA, nameA);
1185 strcpy(info.nameB, nameB);
1186 strcpy(info.nameC, nameC);
1187 strcpy(info.nameD, nameD);
1188 strcpy(info.type, type);
1189 info.k1 = k1;
1190 info.k2 = k2;
1191 info.k3 = k3;
1192 info.k4 = k4;
1193 info.last = 0;
1194 }
1195
1196 #endif
1197
1198 char nameA[15];
1199 char nameB[15];
1200 char nameC[15];
1201 char nameD[15];
1202 char type[30];
1203 double k1, k2, k3, k4;
1204
1205 LinkedType* next;
1206 };
1207
1208 LinkedType* headTorsionType;
1209 LinkedType* currentTorsionType;
1210 torsionStruct info;
1211 info.last = 1; // initialize last to have the last set.
1212 // if things go well, last will be set to 0
1213
1214 int i, a, b, c, d, index;
1215 char* atomA;
1216 char* atomB;
1217 char* atomC;
1218 char* atomD;
1219 CubicTorsion* cTors;
1220
1221 SRI **the_sris;
1222 Atom** the_atoms;
1223 int nTorsions;
1224 the_sris = entry_plug->sr_interactions;
1225 the_atoms = entry_plug->atoms;
1226 nTorsions = entry_plug->n_torsions;
1227
1228 #ifdef IS_MPI
1229 if( worldRank == 0 ){
1230 #endif
1231
1232 // read in the torsion types.
1233
1234 headTorsionType = new LinkedType;
1235
1236 fastForward( "TorsionTypes", "initializeTorsions" );
1237
1238 // we are now at the torsionTypes section
1239
1240 eof_test = fgets( readLine, sizeof(readLine), frcFile );
1241 lineNum++;
1242
1243
1244 // read a line, and start parseing out the atom types
1245
1246 if( eof_test == NULL ){
1247 sprintf( painCave.errMsg,
1248 "Error in reading torsions from force file at line %d.\n",
1249 lineNum );
1250 painCave.isFatal = 1;
1251 simError();
1252 }
1253
1254 // stop reading at end of file, or at next section
1255 while( readLine[0] != '#' && eof_test != NULL ){
1256
1257 // toss comment lines
1258 if( readLine[0] != '!' ){
1259
1260 // the parser returns 0 if the line was blank
1261 if( parseTorsion( readLine, lineNum, info ) ){
1262 headTorsionType->add( info );
1263
1264 }
1265 }
1266 eof_test = fgets( readLine, sizeof(readLine), frcFile );
1267 lineNum++;
1268 }
1269
1270 #ifdef IS_MPI
1271
1272 // send out the linked list to all the other processes
1273
1274 sprintf( checkPointMsg,
1275 "TraPPE_Ex torsion structures read successfully." );
1276 MPIcheckPoint();
1277
1278 currentTorsionType = headTorsionType;
1279 while( currentTorsionType != NULL ){
1280 currentTorsionType->duplicate( info );
1281 sendFrcStruct( &info, mpiTorsionStructType );
1282 currentTorsionType = currentTorsionType->next;
1283 }
1284 info.last = 1;
1285 sendFrcStruct( &info, mpiTorsionStructType );
1286
1287 }
1288
1289 else{
1290
1291 // listen for node 0 to send out the force params
1292
1293 MPIcheckPoint();
1294
1295 headTorsionType = new LinkedType;
1296 recieveFrcStruct( &info, mpiTorsionStructType );
1297 while( !info.last ){
1298
1299 headTorsionType->add( info );
1300 recieveFrcStruct( &info, mpiTorsionStructType );
1301 }
1302 }
1303 #endif // is_mpi
1304
1305 // initialize the Torsions
1306
1307 for( i=0; i<nTorsions; i++ ){
1308
1309 a = the_torsions[i].a;
1310 b = the_torsions[i].b;
1311 c = the_torsions[i].c;
1312 d = the_torsions[i].d;
1313
1314 atomA = the_atoms[a]->getType();
1315 atomB = the_atoms[b]->getType();
1316 atomC = the_atoms[c]->getType();
1317 atomD = the_atoms[d]->getType();
1318 currentTorsionType = headTorsionType->find( atomA, atomB, atomC, atomD );
1319 if( currentTorsionType == NULL ){
1320 sprintf( painCave.errMsg,
1321 "TorsionType error, %s - %s - %s - %s not found"
1322 " in force file.\n",
1323 atomA, atomB, atomC, atomD );
1324 painCave.isFatal = 1;
1325 simError();
1326 }
1327
1328 if( !strcmp( currentTorsionType->type, "cubic" ) ){
1329 index = i + entry_plug->n_bonds + entry_plug->n_bends;
1330
1331 cTors = new CubicTorsion( *the_atoms[a], *the_atoms[b],
1332 *the_atoms[c], *the_atoms[d] );
1333 cTors->setConstants( currentTorsionType->k1, currentTorsionType->k2,
1334 currentTorsionType->k3, currentTorsionType->k4 );
1335 the_sris[index] = cTors;
1336 }
1337 }
1338
1339
1340 // clean up the memory
1341
1342 delete headTorsionType;
1343
1344 #ifdef IS_MPI
1345 sprintf( checkPointMsg, "TraPPE_Ex torsions initialized succesfully" );
1346 MPIcheckPoint();
1347 #endif // is_mpi
1348
1349 }
1350
1351 void TraPPE_ExFF::fastForward( char* stopText, char* searchOwner ){
1352
1353 int foundText = 0;
1354 char* the_token;
1355
1356 rewind( frcFile );
1357 lineNum = 0;
1358
1359 eof_test = fgets( readLine, sizeof(readLine), frcFile );
1360 lineNum++;
1361 if( eof_test == NULL ){
1362 sprintf( painCave.errMsg, "Error fast forwarding force file for %s: "
1363 " file is empty.\n",
1364 searchOwner );
1365 painCave.isFatal = 1;
1366 simError();
1367 }
1368
1369
1370 while( !foundText ){
1371 while( eof_test != NULL && readLine[0] != '#' ){
1372 eof_test = fgets( readLine, sizeof(readLine), frcFile );
1373 lineNum++;
1374 }
1375 if( eof_test == NULL ){
1376 sprintf( painCave.errMsg,
1377 "Error fast forwarding force file for %s at "
1378 "line %d: file ended unexpectedly.\n",
1379 searchOwner,
1380 lineNum );
1381 painCave.isFatal = 1;
1382 simError();
1383 }
1384
1385 the_token = strtok( readLine, " ,;\t#\n" );
1386 foundText = !strcmp( stopText, the_token );
1387
1388 if( !foundText ){
1389 eof_test = fgets( readLine, sizeof(readLine), frcFile );
1390 lineNum++;
1391
1392 if( eof_test == NULL ){
1393 sprintf( painCave.errMsg,
1394 "Error fast forwarding force file for %s at "
1395 "line %d: file ended unexpectedly.\n",
1396 searchOwner,
1397 lineNum );
1398 painCave.isFatal = 1;
1399 simError();
1400 }
1401 }
1402 }
1403 }
1404
1405
1406 int TPE::parseAtom( char *lineBuffer, int lineNum, atomStruct &info ){
1407
1408 char* the_token;
1409
1410 the_token = strtok( lineBuffer, " \n\t,;" );
1411 if( the_token != NULL ){
1412
1413 strcpy( info.name, the_token );
1414
1415 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1416 sprintf( painCave.errMsg,
1417 "Error parseing AtomTypes: line %d\n", lineNum );
1418 painCave.isFatal = 1;
1419 simError();
1420 }
1421
1422 info.isDipole = atoi( the_token );
1423
1424 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1425 sprintf( painCave.errMsg,
1426 "Error parseing AtomTypes: line %d\n", lineNum );
1427 painCave.isFatal = 1;
1428 simError();
1429 }
1430
1431 info.isSSD = atoi( the_token );
1432
1433 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1434 sprintf( painCave.errMsg,
1435 "Error parseing AtomTypes: line %d\n", lineNum );
1436 painCave.isFatal = 1;
1437 simError();
1438 }
1439
1440 info.mass = atof( the_token );
1441
1442 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1443 sprintf( painCave.errMsg,
1444 "Error parseing AtomTypes: line %d\n", lineNum );
1445 painCave.isFatal = 1;
1446 simError();
1447 }
1448
1449 info.epslon = atof( the_token );
1450
1451 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1452 sprintf( painCave.errMsg,
1453 "Error parseing AtomTypes: line %d\n", lineNum );
1454 painCave.isFatal = 1;
1455 simError();
1456 }
1457
1458 info.sigma = atof( the_token );
1459
1460 if( info.isDipole ){
1461
1462 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1463 sprintf( painCave.errMsg,
1464 "Error parseing AtomTypes: line %d\n", lineNum );
1465 painCave.isFatal = 1;
1466 simError();
1467 }
1468
1469 info.dipole = atof( the_token );
1470 }
1471 else info.dipole = 0.0;
1472
1473 if( info.isSSD ){
1474
1475 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1476 sprintf( painCave.errMsg,
1477 "Error parseing AtomTypes: line %d\n", lineNum );
1478 painCave.isFatal = 1;
1479 simError();
1480 }
1481
1482 info.w0 = atof( the_token );
1483
1484 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1485 sprintf( painCave.errMsg,
1486 "Error parseing AtomTypes: line %d\n", lineNum );
1487 painCave.isFatal = 1;
1488 simError();
1489 }
1490
1491 info.v0 = atof( the_token );
1492 }
1493 else info.v0 = info.w0 = 0.0;
1494
1495 return 1;
1496 }
1497 else return 0;
1498 }
1499
1500 int TPE::parseBond( char *lineBuffer, int lineNum, bondStruct &info ){
1501
1502 char* the_token;
1503
1504 the_token = strtok( lineBuffer, " \n\t,;" );
1505 if( the_token != NULL ){
1506
1507 strcpy( info.nameA, the_token );
1508
1509 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1510 sprintf( painCave.errMsg,
1511 "Error parseing BondTypes: line %d\n", lineNum );
1512 painCave.isFatal = 1;
1513 simError();
1514 }
1515
1516 strcpy( info.nameB, the_token );
1517
1518 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1519 sprintf( painCave.errMsg,
1520 "Error parseing BondTypes: line %d\n", lineNum );
1521 painCave.isFatal = 1;
1522 simError();
1523 }
1524
1525 strcpy( info.type, the_token );
1526
1527 if( !strcmp( info.type, "fixed" ) ){
1528 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1529 sprintf( painCave.errMsg,
1530 "Error parseing BondTypes: line %d\n", lineNum );
1531 painCave.isFatal = 1;
1532 simError();
1533 }
1534
1535 info.d0 = atof( the_token );
1536 }
1537 else{
1538 sprintf( painCave.errMsg,
1539 "Unknown TraPPE_Ex bond type \"%s\" at line %d\n",
1540 info.type,
1541 lineNum );
1542 painCave.isFatal = 1;
1543 simError();
1544 }
1545
1546 return 1;
1547 }
1548 else return 0;
1549 }
1550
1551
1552 int TPE::parseBend( char *lineBuffer, int lineNum, bendStruct &info ){
1553
1554 char* the_token;
1555
1556 the_token = strtok( lineBuffer, " \n\t,;" );
1557 if( the_token != NULL ){
1558
1559 strcpy( info.nameA, the_token );
1560
1561 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1562 sprintf( painCave.errMsg,
1563 "Error parseing BondTypes: line %d\n", lineNum );
1564 painCave.isFatal = 1;
1565 simError();
1566 }
1567
1568 strcpy( info.nameB, the_token );
1569
1570 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1571 sprintf( painCave.errMsg,
1572 "Error parseing BondTypes: line %d\n", lineNum );
1573 painCave.isFatal = 1;
1574 simError();
1575 }
1576
1577 strcpy( info.nameC, the_token );
1578
1579 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1580 sprintf( painCave.errMsg,
1581 "Error parseing BondTypes: line %d\n", lineNum );
1582 painCave.isFatal = 1;
1583 simError();
1584 }
1585
1586 strcpy( info.type, the_token );
1587
1588 if( !strcmp( info.type, "quadratic" ) ){
1589 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1590 sprintf( painCave.errMsg,
1591 "Error parseing BendTypes: line %d\n", lineNum );
1592 painCave.isFatal = 1;
1593 simError();
1594 }
1595
1596 info.k1 = atof( the_token );
1597
1598 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1599 sprintf( painCave.errMsg,
1600 "Error parseing BendTypes: line %d\n", lineNum );
1601 painCave.isFatal = 1;
1602 simError();
1603 }
1604
1605 info.k2 = atof( the_token );
1606
1607 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1608 sprintf( painCave.errMsg,
1609 "Error parseing BendTypes: line %d\n", lineNum );
1610 painCave.isFatal = 1;
1611 simError();
1612 }
1613
1614 info.k3 = atof( the_token );
1615
1616 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1617 sprintf( painCave.errMsg,
1618 "Error parseing BendTypes: line %d\n", lineNum );
1619 painCave.isFatal = 1;
1620 simError();
1621 }
1622
1623 info.t0 = atof( the_token );
1624 }
1625
1626 else{
1627 sprintf( painCave.errMsg,
1628 "Unknown TraPPE_Ex bend type \"%s\" at line %d\n",
1629 info.type,
1630 lineNum );
1631 painCave.isFatal = 1;
1632 simError();
1633 }
1634
1635 return 1;
1636 }
1637 else return 0;
1638 }
1639
1640 int TPE::parseTorsion( char *lineBuffer, int lineNum, torsionStruct &info ){
1641
1642 char* the_token;
1643
1644 the_token = strtok( lineBuffer, " \n\t,;" );
1645 if( the_token != NULL ){
1646
1647 strcpy( info.nameA, the_token );
1648
1649 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1650 sprintf( painCave.errMsg,
1651 "Error parseing TorsionTypes: line %d\n", lineNum );
1652 painCave.isFatal = 1;
1653 simError();
1654 }
1655
1656 strcpy( info.nameB, the_token );
1657
1658 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1659 sprintf( painCave.errMsg,
1660 "Error parseing TorsionTypes: line %d\n", lineNum );
1661 painCave.isFatal = 1;
1662 simError();
1663 }
1664
1665 strcpy( info.nameC, the_token );
1666
1667 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1668 sprintf( painCave.errMsg,
1669 "Error parseing TorsionTypes: line %d\n", lineNum );
1670 painCave.isFatal = 1;
1671 simError();
1672 }
1673
1674 strcpy( info.nameD, the_token );
1675
1676 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1677 sprintf( painCave.errMsg,
1678 "Error parseing TorsionTypes: line %d\n", lineNum );
1679 painCave.isFatal = 1;
1680 simError();
1681 }
1682
1683 strcpy( info.type, the_token );
1684
1685 if( !strcmp( info.type, "cubic" ) ){
1686 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1687 sprintf( painCave.errMsg,
1688 "Error parseing TorsionTypes: line %d\n", lineNum );
1689 painCave.isFatal = 1;
1690 simError();
1691 }
1692
1693 info.k1 = atof( the_token );
1694
1695 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1696 sprintf( painCave.errMsg,
1697 "Error parseing TorsionTypes: line %d\n", lineNum );
1698 painCave.isFatal = 1;
1699 simError();
1700 }
1701
1702 info.k2 = atof( the_token );
1703
1704 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1705 sprintf( painCave.errMsg,
1706 "Error parseing TorsionTypes: line %d\n", lineNum );
1707 painCave.isFatal = 1;
1708 simError();
1709 }
1710
1711 info.k3 = atof( the_token );
1712
1713 if( ( the_token = strtok( NULL, " \n\t,;" ) ) == NULL ){
1714 sprintf( painCave.errMsg,
1715 "Error parseing TorsionTypes: line %d\n", lineNum );
1716 painCave.isFatal = 1;
1717 simError();
1718 }
1719
1720 info.k4 = atof( the_token );
1721
1722 }
1723
1724 else{
1725 sprintf( painCave.errMsg,
1726 "Unknown TraPPE_Ex torsion type \"%s\" at line %d\n",
1727 info.type,
1728 lineNum );
1729 painCave.isFatal = 1;
1730 simError();
1731 }
1732
1733 return 1;
1734 }
1735
1736 else return 0;
1737 }