// Action_Unwrap::Setup() Action::RetType Action_Unwrap::Setup(ActionSetup& setup) { // Ensure same number of atoms in current parm and ref parm if ( RefParm_!=0 ) { if ( setup.Top().Natom() != RefParm_->Natom() ) { mprinterr("Error: unwrap: # atoms in reference parm %s is not\n", RefParm_->c_str()); mprinterr("Error: equal to # atoms in parm %s\n", setup.Top().c_str()); return Action::ERR; } } // Check box type if (setup.CoordInfo().TrajBox().Type()==Box::NOBOX) { mprintf("Error: unwrap: Parm %s does not contain box information.\n", setup.Top().c_str()); return Action::ERR; } orthogonal_ = false; if (setup.CoordInfo().TrajBox().Type()==Box::ORTHO) orthogonal_ = true; // Setup atom pairs to be unwrapped. imageList_ = Image::CreatePairList(setup.Top(), imageMode_, maskExpression_); if (imageList_.empty()) { mprintf("Warning: Mask selects no atoms for topology '%s'.\n", setup.Top().c_str()); return Action::SKIP; } mprintf("\tNumber of %ss to be unwrapped is %zu\n", Image::ModeString(imageMode_), imageList_.size()/2); // Use current parm as reference if not already set if (RefParm_ == 0) RefParm_ = setup.TopAddress(); return Action::OK; }
/** Set angle up for this parmtop. Get masks etc. */ Action::RetType Action_Esander::Setup(ActionSetup& setup) { if (currentParm_ != 0 && currentParm_->Pindex() != setup.Top().Pindex()) { mprintf("Warning: Current topology is %i:%s but reference is %i:%s. Skipping.\n", setup.Top().Pindex(), setup.Top().c_str(), currentParm_->Pindex(), currentParm_->c_str()); return Action::SKIP; } // Check for LJ terms if (!setup.Top().Nonbond().HasNonbond()) { mprinterr("Error: Topology '%s' does not have non-bonded parameters.\n", setup.Top().c_str()); return Action::ERR; } // If reference specified, init now. Otherwise using first frame. if (currentParm_ != 0 ) { if ( InitForRef() ) return Action::ERR; } else currentParm_ = setup.TopAddress(); // If saving of forces is requested, make sure CoordinateInfo has force. if (save_forces_) { cInfo_ = setup.CoordInfo(); cInfo_.SetForce( true ); newFrame_.SetupFrameV( setup.Top().Atoms(), cInfo_ ); setup.SetCoordInfo( &cInfo_ ); ret_ = Action::MODIFY_COORDS; return Action::MODIFY_TOPOLOGY; } ret_ = Action::OK; return Action::OK; }
Action::RetType Action_DNAionTracker::Setup(ActionSetup& setup) { // Setup masks if (setup.Top().SetupIntegerMask( p1_ )) return Action::ERR; if ( p1_.None() ) { mprinterr("Error: dnaiontracker: No atoms in mask1\n"); return Action::ERR; } if (setup.Top().SetupIntegerMask( p2_ )) return Action::ERR; if ( p2_.None() ) { mprinterr("Error: dnaiontracker: No atoms in mask2\n"); return Action::ERR; } if (setup.Top().SetupIntegerMask( base_ )) return Action::ERR; if ( base_.None() ) { mprinterr("Error: dnaiontracker: No atoms in mask3\n"); return Action::ERR; } if (setup.Top().SetupIntegerMask( ions_ )) return Action::ERR; if ( ions_.None() ) { mprinterr("Error: dnaiontracker: No atoms in mask4\n"); return Action::ERR; } SetupImaging( setup.CoordInfo().TrajBox().Type() ); mprintf("\tPhosphate1 Mask [%s] %i atoms.\n", p1_.MaskString(), p1_.Nselected()); mprintf("\tPhosphate2 Mask [%s] %i atoms.\n", p2_.MaskString(), p2_.Nselected()); mprintf("\t Base Mask [%s] %i atoms.\n", base_.MaskString(), base_.Nselected()); mprintf("\t Ions Mask [%s] %i atoms.\n", ions_.MaskString(), ions_.Nselected()); return Action::OK; }
/** For this to be valid the same # of atoms should be selected each time. */ Action::RetType Action_VelocityAutoCorr::Setup(ActionSetup& setup) { if (setup.Top().SetupIntegerMask( mask_ )) return Action::ERR; mask_.MaskInfo(); if (mask_.None()) { mprintf("Warning: No atoms selected by mask.\n"); return Action::SKIP; } // If using velocity info, check that it is present. if (useVelInfo_ && !setup.CoordInfo().HasVel()) { mprinterr("Error: 'usevelocity' specified but no velocity info assocated with %s\n", setup.Top().c_str()); return Action::ERR; } // If we have already started recording velocities, check that the current // number of selected atoms has remained the same. if (!Vel_.empty()) { if ((int)Vel_.size() != mask_.Nselected()) { mprinterr("Error: # of selected atoms %i has changed (previously %zu)\n", mask_.Nselected(), Vel_.size()); return Action::ERR; } } else Vel_.resize( mask_.Nselected() ); return Action::OK; }
/** Determine what atoms each mask pertains to for the current parm file. */ Action::RetType Action_LIE::Setup(ActionSetup& setup) { if (setup.Top().SetupIntegerMask( Mask1_ )) return Action::ERR; if (setup.Top().SetupIntegerMask( Mask2_ )) return Action::ERR; mprintf("\tLIE: %i Ligand Atoms, %i Surrounding Atoms\n", Mask1_.Nselected(), Mask2_.Nselected()); if (setup.CoordInfo().TrajBox().Type() == Box::NOBOX) { mprinterr("Error: LIE: Must have explicit solvent system with box info\n"); return Action::ERR; } if (Mask1_.None() || Mask2_.None()) { mprintf("Warning: LIE: One or both masks have no atoms.\n"); return Action::SKIP; } if (SetupParms(setup.Top())) return Action::ERR; // Back up the parm CurrentParm_ = setup.TopAddress(); return Action::OK; }
// Action_Outtraj::Setup() Action::RetType Action_Outtraj::Setup(ActionSetup& setup) { if (associatedParm_->Pindex() != setup.Top().Pindex()) return Action::SKIP; if (!isSetup_) { // TODO: Trajout IsOpen? if (outtraj_.SetupTrajWrite(setup.TopAddress(), setup.CoordInfo(), setup.Nframes())) return Action::ERR; outtraj_.PrintInfo(0); isSetup_ = true; } return Action::OK; }
/** Set up solute and solvent masks. If no solvent mask was specified use * solvent information in the current topology. */ Action::RetType Action_Watershell::Setup(ActionSetup& setup) { // Set up solute mask if (setup.Top().SetupIntegerMask( soluteMask_ )) return Action::ERR; if ( soluteMask_.None() ) { mprintf("Warning: No atoms in solute mask [%s].\n",soluteMask_.MaskString()); return Action::SKIP; } // Set up solvent mask if (!solventmaskexpr_.empty()) { if (setup.Top().SetupIntegerMask( solventMask_ )) return Action::ERR; } else { solventMask_.ResetMask(); for (Topology::mol_iterator mol = setup.Top().MolStart(); mol != setup.Top().MolEnd(); ++mol) { if ( mol->IsSolvent() ) solventMask_.AddAtomRange( mol->BeginAtom(), mol->EndAtom() ); } } if ( solventMask_.None() ) { if (!solventmaskexpr_.empty()) mprintf("Warning: No solvent atoms selected by mask [%s]\n", solventmaskexpr_.c_str()); else mprintf("Warning: No solvent atoms in topology %s\n",setup.Top().c_str()); return Action::SKIP; } SetupImaging( setup.CoordInfo().TrajBox().Type() ); // Create space for residues # ifdef _OPENMP // Only re-allocate for larger # of residues if ( setup.Top().Nres() > NactiveResidues_ ) { if (activeResidues_thread_ != 0) { // Deallocate each thread for (int i = 0; i < NactiveResidues_; ++i) delete[] activeResidues_thread_[i]; } else { // Initial thread allocation needed activeResidues_thread_ = new int*[ numthreads_ ]; } // Allocate each thread for (int i = 0; i < numthreads_; ++i) { activeResidues_thread_[i] = new int[ setup.Top().Nres() ]; std::fill( activeResidues_thread_[i], activeResidues_thread_[i] + setup.Top().Nres(), 0 ); } } NactiveResidues_ = setup.Top().Nres(); # else activeResidues_.resize( setup.Top().Nres(), 0 ); # endif // Store current Parm CurrentParm_ = setup.TopAddress(); return Action::OK; }
/** Determine what atoms each mask pertains to for the current parm file. */ Action::RetType Action_ReplicateCell::Setup(ActionSetup& setup) { if (setup.Top().SetupIntegerMask( Mask1_ )) return Action::ERR; mprintf("\t%s (%i atoms)\n",Mask1_.MaskString(), Mask1_.Nselected()); if (Mask1_.None()) { mprintf("Warning: One or both masks have no atoms.\n"); return Action::SKIP; } // Set up imaging info for this parm image_.SetupImaging( setup.CoordInfo().TrajBox().Type() ); if (!image_.ImagingEnabled()) { mprintf("Warning: Imaging cannot be performed for topology %s\n", setup.Top().c_str()); return Action::SKIP; } // Create combined topology. if (combinedTop_.Natom() > 0) { // Topology already set up. Check that # atoms matches. if (Mask1_.Nselected() * ncopies_ != combinedTop_.Natom()) { mprintf("Warning: Unit cell can currently only be replicated for" " topologies with same # atoms.\n"); return Action::SKIP; } // Otherwise assume top does not change. } else { // Set up topology and frame. Topology* stripParm = setup.Top().modifyStateByMask( Mask1_ ); if (stripParm == 0) return Action::ERR; for (int cell = 0; cell != ncopies_; cell++) combinedTop_.AppendTop( *stripParm ); combinedTop_.Brief("Combined parm:"); delete stripParm; if (!parmfilename_.empty()) { ParmFile pfile; if (pfile.WriteTopology(combinedTop_, parmfilename_, ParmFile::UNKNOWN_PARM, 0)) { mprinterr("Error: Topology file %s not written.\n", parmfilename_.c_str()); return Action::ERR; } } // Only coordinates for now. FIXME combinedFrame_.SetupFrameM(combinedTop_.Atoms()); // Set up COORDS / output traj if necessary. if (coords_ != 0) coords_->CoordsSetup( combinedTop_, CoordinateInfo() ); if (!trajfilename_.empty()) { if ( outtraj_.PrepareEnsembleTrajWrite(trajfilename_, trajArgs_, &combinedTop_, CoordinateInfo(), setup.Nframes(), TrajectoryFile::UNKNOWN_TRAJ, ensembleNum_) ) return Action::ERR; } } return Action::OK; }
// Action_CheckStructure::Setup() Action::RetType Action_CheckStructure::Setup(ActionSetup& setup) { CurrentParm_ = setup.TopAddress(); if (SeparateSetup( setup.Top(), setup.CoordInfo().TrajBox().Type(),bondcheck_ )) return Action::ERR; // Print imaging info for this parm if (bondcheck_) mprintf("\tChecking %u bonds.\n", bondList_.size()); if (image_.ImagingEnabled()) mprintf("\tImaging on.\n"); else mprintf("\timaging off.\n"); return Action::OK; }
// Action_Outtraj::Setup() Action::RetType Action_Outtraj::Setup(ActionSetup& setup) { if (!isActive_ || associatedParm_->Pindex() != setup.Top().Pindex()) { mprintf("\tOutput trajectory not active for topology '%s'\n", setup.Top().c_str()); return Action::SKIP; } if (!isSetup_) { // TODO: Trajout IsOpen? if (outtraj_.SetupTrajWrite(setup.TopAddress(), setup.CoordInfo(), setup.Nframes())) return Action::ERR; mprintf(" "); //TODO this is a kludge; PrintInfo should be a string. outtraj_.PrintInfo(0); mprintf("\tHas %s\n", outtraj_.Traj().CoordInfo().InfoString().c_str()); isSetup_ = true; } return Action::OK; }
// Action_GridFreeEnergy::setup() Action::RetType Action_GridFreeEnergy::Setup(ActionSetup& setup) { // Setup grid, checks box info. if (GridSetup( setup.Top(), setup.CoordInfo() )) return Action::ERR; // Setup mask if (setup.Top().SetupIntegerMask( mask_ )) return Action::ERR; mask_.MaskInfo(); if (mask_.None()) { mprinterr("Warning: No atoms selected for parm %s\n", setup.Top().c_str()); return Action::SKIP; } return Action::OK; }
// Action_Center::Setup() Action::RetType Action_Center::Setup(ActionSetup& setup) { if ( setup.Top().SetupIntegerMask(Mask_) ) return Action::ERR; Mask_.MaskInfo(); if (Mask_.None()) { mprintf("Warning: Mask contains 0 atoms.\n"); return Action::SKIP; } if (centerMode_ == BOXCTR && setup.CoordInfo().TrajBox().Type()==Box::NOBOX) { mprintf("Warning: Box center specified but no box information.\n"); return Action::SKIP; } return Action::OK; }
// Action_Density::DensitySetup() Action::RetType Action_Density::DensitySetup(ActionSetup& setup) { // Total system density setup image_.SetupImaging( setup.CoordInfo().TrajBox().Type() ); if (!image_.ImagingEnabled()) { mprintf("Warning: No unit cell information, total density cannot be calculated for '%s'\n", setup.Top().c_str()); return Action::SKIP; } // delta_ will hold sum of masses delta_ = 0.0; for (int idx = 0; idx != setup.Top().Natom(); idx++) delta_ += setup.Top()[idx].Mass(); mprintf("\tSum of masses is %g amu\n", delta_); return Action::OK; }
// Action_NativeContacts::Setup() Action::RetType Action_NativeContacts::Setup(ActionSetup& setup) { // Setup potential contact lists for this topology if (SetupContactLists( setup.Top(), Frame())) return Action::SKIP; mprintf("\t%zu potential contact sites for '%s'\n", Mask1_.Nselected(), Mask1_.MaskString()); if (Mask2_.MaskStringSet()) mprintf("\t%zu potential contact sites for '%s'\n", Mask2_.Nselected(), Mask2_.MaskString()); // Set up imaging info for this parm image_.SetupImaging( setup.CoordInfo().TrajBox().Type() ); if (image_.ImagingEnabled()) mprintf("\tImaging enabled.\n"); else mprintf("\tImaging disabled.\n"); CurrentParm_ = setup.TopAddress(); return Action::OK; }
/** Determine what atoms each mask pertains to for the current parm file. * Imaging is checked for in Action::Setup. */ Action::RetType Action_Distance::Setup(ActionSetup& setup) { if (setup.Top().SetupIntegerMask( Mask1_ )) return Action::ERR; if (setup.Top().SetupIntegerMask( Mask2_ )) return Action::ERR; mprintf("\t%s (%i atoms) to %s (%i atoms)",Mask1_.MaskString(), Mask1_.Nselected(), Mask2_.MaskString(),Mask2_.Nselected()); if (Mask1_.None() || Mask2_.None()) { mprintf("\nWarning: One or both masks have no atoms.\n"); return Action::SKIP; } // Set up imaging info for this parm image_.SetupImaging( setup.CoordInfo().TrajBox().Type() ); if (image_.ImagingEnabled()) mprintf(", imaged"); else mprintf(", imaging off"); mprintf(".\n"); return Action::OK; }
Action::RetType Action_Channel::Setup(ActionSetup& setup) { // Initial grid setup if (grid_->Size() == 0) { DataSet_3D& GRID = static_cast<DataSet_3D&>( *grid_ ); Box const& box = setup.CoordInfo().TrajBox(); if (box.Type() == Box::NOBOX) { mprinterr("Error: No box information to set up grid.\n"); return Action::ERR; } else if (box.Type() == Box::ORTHO) { // FIXME: May need to update parm box info or set up on first frame. if (GRID.Allocate_X_C_D(box.Lengths(), box.Center(), dxyz_)) return Action::ERR; } else { Vec3 nxyz = box.Lengths() / dxyz_; if (GRID.Allocate_N_O_Box((size_t)nxyz[0], (size_t)nxyz[1], (size_t)nxyz[2], Vec3(0.0), box)) return Action::ERR; } GRID.GridInfo(); } // Set up masks if (setup.Top().SetupIntegerMask( soluteMask_ ) || setup.Top().SetupIntegerMask( solventMask_) ) return Action::ERR; soluteMask_.MaskInfo(); if (soluteMask_.None()) { mprintf("Warning: No solute atoms selected.\n"); return Action::SKIP; } solventMask_.MaskInfo(); if (solventMask_.None()) { mprintf("Warning: No solvent atoms selected.\n"); return Action::SKIP; } // Set up solute van der Waals. FIXME: Handle case where no LJ params radii_.clear(); for (AtomMask::const_iterator uAtom = soluteMask_.begin(); uAtom != soluteMask_.end(); ++uAtom) radii_.push_back( setup.Top().GetVDWradius( *uAtom ) ); return Action::OK; }
// Action_SymmetricRmsd::Setup() Action::RetType Action_SymmetricRmsd::Setup(ActionSetup& setup) { // Setup target mask. if (setup.Top().SetupIntegerMask( tgtMask_ )) return Action::ERR; tgtMask_.MaskInfo(); if (tgtMask_.None()) { mprintf("Warning: No atoms selected by mask '%s'\n", tgtMask_.MaskString()); return Action::SKIP; } // Allocate space for selected atoms in target frame. This will also // put the correct masses in based on the mask. selectedTgt_.SetupFrameFromMask(tgtMask_, setup.Top().Atoms()); // Setup Symmetric RMSD calc (target mask, symmetric atoms etc) if (SRMSD_.SetupSymmRMSD( setup.Top(), tgtMask_, remap_ )) return Action::ERR; if (remap_) { // Allocate space for remapped frame; same # atoms as original frame remapFrame_.SetupFrameV( setup.Top().Atoms(), setup.CoordInfo() ); targetMap_.resize( setup.Top().Natom() ); } // Reference frame setup if (REF_.SetupRef(setup.Top(), tgtMask_.Nselected(), "symmrmsd")) return Action::ERR; return Action::OK; }
// Action_CreateReservoir::Setup() Action::RetType Action_CreateReservoir::Setup(ActionSetup& setup) { // Check that input parm matches current parm if (original_trajparm_->Pindex() != setup.Top().Pindex()) { mprintf("Info: createreservoir was set up for topology %s\n", original_trajparm_->c_str()); mprintf("Info: skipping topology %s\n", setup.Top().c_str()); return Action::SKIP; } if (!trajIsOpen_) { mprintf("\tCreating reservoir file %s\n", filename_.full()); CoordinateInfo cinfo = setup.CoordInfo(); if (!useVelocity_) cinfo.SetVelocity(false); if (!useForce_) cinfo.SetForce(false); if (reservoir_.InitReservoir(filename_, title_, cinfo, setup.Top().Natom(), (bin_ != 0), reservoirT_, iseed_)) { mprinterr("Error: Could not set up NetCDF reservoir.\n"); return Action::ERR; } trajIsOpen_ = true; nframes_ = 0; } return Action::OK; }
Action::RetType Action_CreateCrd::Setup(ActionSetup& setup) { // Set COORDS topology now if not already set. if (setup.Top().Pindex() == pindex_ && coords_->Top().Natom() == 0) { coords_->CoordsSetup( setup.Top(), setup.CoordInfo() ); // Estimate memory usage mprintf("\tEstimated memory usage (%i frames): %s\n", setup.Nframes(), ByteString(coords_->SizeInBytes(setup.Nframes()), BYTE_DECIMAL).c_str()); } // If # atoms in currentParm does not match coords, warn user. if (setup.Top().Natom() != coords_->Top().Natom()) { if (check_) { mprinterr("Error: # atoms in current topology (%i) != # atoms in coords set \"%s\" (%i)\n", setup.Top().Natom(), coords_->legend(), coords_->Top().Natom()); return Action::ERR; } else { mprintf("Warning: # atoms in current topology (%i) != # atoms in coords set \"%s\" (%i)\n" "Warning: The resulting COORDS data set may have problems.\n", setup.Top().Natom(), coords_->legend(), coords_->Top().Natom()); } } return Action::OK; }
// Action_Vector::Setup() Action::RetType Action_Vector::Setup(ActionSetup& setup) { if (needBoxInfo_) { // Check for box info if (setup.CoordInfo().TrajBox().Type() == Box::NOBOX) { mprinterr("Error: vector box: No box information.\n", setup.Top().c_str()); return Action::ERR; } } if (mask_.MaskStringSet()) { // Setup mask 1 if (setup.Top().SetupIntegerMask(mask_)) return Action::ERR; mask_.MaskInfo(); if (mask_.None()) { mprinterr("Error: First vector mask is empty.\n"); return Action::ERR; } } // Allocate space for CORRPLANE. if (mode_ == CORRPLANE) { if (vcorr_!=0) delete[] vcorr_; vcorr_ = new double[ 3 * mask_.Nselected() ]; } // Setup mask 2 if (mask2_.MaskStringSet()) { if (setup.Top().SetupIntegerMask(mask2_)) return Action::ERR; mask2_.MaskInfo(); if (mask2_.None()) { mprinterr("Error: Second vector mask is empty.\n"); return Action::ERR; } } CurrentParm_ = setup.TopAddress(); return Action::OK; }
/** Called every time the trajectory changes. Set up FrameMask for the new * parmtop and allocate space for selected atoms from the Frame. */ Action::RetType Action_Rmsd::Setup(ActionSetup& setup) { // Target setup if ( setup.Top().SetupIntegerMask( tgtMask_ ) ) return Action::ERR; mprintf("\tTarget mask:"); tgtMask_.BriefMaskInfo(); mprintf("\n"); if ( tgtMask_.None() ) { mprintf("Warning: No atoms in mask '%s'.\n", tgtMask_.MaskString()); return Action::SKIP; } // Allocate space for selected atoms in the frame. This will also put the // correct masses in based on the mask. tgtFrame_.SetupFrameFromMask(tgtMask_, setup.Top().Atoms()); // Reference setup if (REF_.SetupRef(setup.Top(), tgtMask_.Nselected(), "rmsd")) return Action::SKIP; // Per residue rmsd setup if (perres_) { // If RefParm is still NULL probably 'first', set now. if (RefParm_ == 0) RefParm_ = setup.TopAddress(); int err = perResSetup(setup.Top(), *RefParm_); if (err == 1) return Action::SKIP; else if (err == 2) return Action::ERR; } // Warn if PBC and rotating if (rotate_ && setup.CoordInfo().TrajBox().Type() != Box::NOBOX) { mprintf("Warning: Coordinates are being rotated and box coordinates are present.\n" "Warning: Unit cell vectors are NOT rotated; imaging will not be possible\n" "Warning: after the RMS-fit is performed.\n"); } return Action::OK; }
/** Determine what atoms each mask pertains to for the current parm file. * Also determine whether imaging should be performed. */ Action::RetType Action_Radial::Setup(ActionSetup& setup) { if ( setup.Top().SetupIntegerMask( Mask1_ ) ) return Action::ERR; if (Mask1_.None()) { mprintf("Warning: First mask has no atoms.\n"); return Action::SKIP; } if (setup.Top().SetupIntegerMask( Mask2_ ) ) return Action::ERR; if (Mask2_.None()) { mprintf("Warning: Second mask has no atoms.\n"); return Action::SKIP; } image_.SetupImaging( setup.CoordInfo().TrajBox().Type() ); // If not computing center for mask 1 or 2, make the outer loop for distance // calculation correspond to the mask with the most atoms. if (rmode_ == NORMAL || rmode_ == NO_INTRAMOL) { if (Mask1_.Nselected() > Mask2_.Nselected()) { OuterMask_ = Mask1_; InnerMask_ = Mask2_; } else { OuterMask_ = Mask2_; InnerMask_ = Mask1_; } } else if (rmode_ == CENTER1) { OuterMask_ = Mask1_; InnerMask_ = Mask2_; } else if (rmode_ == CENTER2) { OuterMask_ = Mask2_; InnerMask_ = Mask1_; } // If ignoring intra-molecular distances, need to count how many we // are ignoring. if (rmode_ == NO_INTRAMOL) { int ndist = 0; for (AtomMask::const_iterator atom1 = OuterMask_.begin(); atom1 != OuterMask_.end(); ++atom1) for (AtomMask::const_iterator atom2 = InnerMask_.begin(); atom2 != InnerMask_.end(); ++atom2) if ( setup.Top()[*atom1].MolNum() == setup.Top()[*atom2].MolNum() ) ++ndist; if (currentParm_ != 0 && ndist != intramol_distances_) mprintf("Warning: # of intramolecular distances (%i) has changed from the last" " topology (%i).\nWarning: Normalization will not be correct.\n", ndist, intramol_distances_); intramol_distances_ = ndist; currentParm_ = setup.TopAddress(); mprintf("\tIgnoring %i intra-molecular distances.\n", intramol_distances_); } // Check volume information if (useVolume_ && setup.CoordInfo().TrajBox().Type()==Box::NOBOX) { mprintf("Warning: 'volume' specified but no box information for %s, skipping.\n", setup.Top().c_str()); return Action::SKIP; } // Print mask and imaging info for this parm mprintf(" RADIAL: %i atoms in Mask1, %i atoms in Mask2, ", Mask1_.Nselected(), Mask2_.Nselected()); if (image_.ImagingEnabled()) mprintf("Imaging on.\n"); else mprintf("Imaging off.\n"); return Action::OK; }
/** Determine from selected mask atoms which dihedrals will be rotated. */ Action::RetType Action_DihedralScan::Setup(ActionSetup& setup) { DihedralScanType dst; // If range is empty (i.e. no resrange arg given) look through all // solute residues. Range actualRange; if (resRange_.Empty()) actualRange = setup.Top().SoluteResidues(); else actualRange = resRange_; // Search for dihedrals if (dihSearch_.FindDihedrals(setup.Top(), actualRange)) return Action::ERR; // For each found dihedral, set up mask of atoms that will move upon // rotation. Also set up mask of atoms in this residue that will not // move, including atom2. if (debug_>0) mprintf("DEBUG: Dihedrals:\n"); for (DihedralSearch::mask_it dih = dihSearch_.begin(); dih != dihSearch_.end(); ++dih) { dst.checkAtoms.clear(); // Set mask of atoms that will move during dihedral rotation. dst.Rmask = DihedralSearch::MovingAtoms(setup.Top(), dih->A1(), dih->A2()); // If randomly rotating angles, check for atoms that are in the same // residue as A1 but will not move. They need to be checked for clashes // since further rotations will not help them. if (mode_ == RANDOM && check_for_clashes_) { CharMask cMask( dst.Rmask.ConvertToCharMask(), dst.Rmask.Nselected() ); int a1res = setup.Top()[dih->A1()].ResNum(); for (int maskatom = setup.Top().Res(a1res).FirstAtom(); maskatom < setup.Top().Res(a1res).LastAtom(); ++maskatom) if (!cMask.AtomInCharMask(maskatom)) dst.checkAtoms.push_back( maskatom ); dst.checkAtoms.push_back(dih->A1()); // TODO: Does this need to be added first? // Since only the second atom and atoms it is bonded to move during // rotation, base the check on the residue of the second atom. dst.resnum = a1res; } dst.atom0 = dih->A0(); // FIXME: This duplicates info dst.atom1 = dih->A1(); dst.atom2 = dih->A2(); dst.atom3 = dih->A3(); BB_dihedrals_.push_back(dst); // DEBUG: List dihedral info. if (debug_ > 0) { mprintf("\t%s-%s-%s-%s\n", setup.Top().TruncResAtomName(dih->A0()).c_str(), setup.Top().TruncResAtomName(dih->A1()).c_str(), setup.Top().TruncResAtomName(dih->A2()).c_str(), setup.Top().TruncResAtomName(dih->A3()).c_str() ); if (debug_ > 1 && mode_ == RANDOM && check_for_clashes_) { mprintf("\t\tCheckAtoms="); for (std::vector<int>::const_iterator ca = dst.checkAtoms.begin(); ca != dst.checkAtoms.end(); ++ca) mprintf(" %i", *ca + 1); mprintf("\n"); } if (debug_ > 2) { mprintf("\t\t"); dst.Rmask.PrintMaskAtoms("Rmask:"); } } } // Set up CheckStructure for this parm (false = nobondcheck) if (checkStructure_.SeparateSetup(setup.Top(), setup.CoordInfo().TrajBox().Type(), false) != Action::OK) return Action::ERR; // Set the overall max number of rotations to try max_rotations_ = (int) BB_dihedrals_.size(); max_rotations_ *= max_factor_; // Set up simple structure check. First step is coarse; check distances // between a certain atom in each residue (first, COM, CA, some other atom?) // to see if residues are in each others neighborhood. Second step is to // check the atoms in each close residue. if (check_for_clashes_) { ResidueCheckType rct; int res = 0; for (Topology::res_iterator residue = setup.Top().ResStart(); residue != setup.Top().ResEnd(); ++residue) { rct.resnum = res++; rct.start = residue->FirstAtom(); rct.stop = residue->LastAtom(); rct.checkatom = rct.start; ResCheck_.push_back(rct); } } if (!outfilename_.empty() && CurrentParm_ == 0) // FIXME: Correct frames for # of rotations outtraj_.SetupTrajWrite(setup.TopAddress(), setup.CoordInfo(), setup.Nframes()); CurrentParm_ = setup.TopAddress(); return Action::OK; }
/** Determine what atoms each mask pertains to for the current parm file. */ Action::RetType Action_NMRrst::Setup(ActionSetup& setup) { if (!viewrst_.empty() && rsttop_ == 0) rsttop_ = setup.TopAddress(); // --------------------------------------------- // Set up NOEs from file. for (noeDataArray::iterator noe = NOEs_.begin(); noe != NOEs_.end(); ++noe) { if (setup.Top().SetupIntegerMask( noe->dMask1_ )) return Action::ERR; if (setup.Top().SetupIntegerMask( noe->dMask2_ )) return Action::ERR; if (noe->dMask1_.None() || noe->dMask2_.None()) { mprintf("Warning: One or both masks for NOE '%s' have no atoms (%i and %i).\n", noe->dist_->legend(), noe->dMask1_.Nselected(), noe->dMask2_.Nselected()); noe->active_ = false; } else noe->active_ = true; } // --------------------------------------------- // Set up potential NOE sites. if (findNOEs_) { if (setup.Top().SetupCharMask( Mask_ )) return Action::ERR; Mask_.MaskInfo(); if (Mask_.None()) return Action::SKIP; SiteArray potentialSites; // .clear(); AtomMap resMap; resMap.SetDebug( debug_ ); std::vector<bool> selected; Range soluteRes = setup.Top().SoluteResidues(); for (Range::const_iterator res = soluteRes.begin(); res != soluteRes.end(); ++res) { int res_first_atom = setup.Top().Res(*res).FirstAtom(); selected.assign( setup.Top().Res(*res).NumAtoms(), false ); // Find symmetric atom groups. AtomMap::AtomIndexArray symmGroups; if (resMap.SymmetricAtoms(setup.Top(), symmGroups, *res)) return Action::ERR; // DEBUG if (debug_ > 0) { mprintf("DEBUG: Residue %i: symmetric atom groups:\n", *res + 1); for (AtomMap::AtomIndexArray::const_iterator grp = symmGroups.begin(); grp != symmGroups.end(); ++grp) { mprintf("\t\t"); for (AtomMap::Iarray::const_iterator at = grp->begin(); at != grp->end(); ++at) mprintf(" %s", setup.Top().TruncAtomNameNum( *at ).c_str()); mprintf("\n"); } } // Each symmetric hydrogen atom group is a site. for (AtomMap::AtomIndexArray::const_iterator grp = symmGroups.begin(); grp != symmGroups.end(); ++grp) { // NOTE: If first atom is H all should be H. if ( setup.Top()[ grp->front() ].Element() == Atom::HYDROGEN ) { Iarray symmAtomGroup; for (Iarray::const_iterator at = grp->begin(); at != grp->end(); ++at) if (Mask_.AtomInCharMask( *at )) symmAtomGroup.push_back( *at ); if (!symmAtomGroup.empty()) { potentialSites.push_back( Site(*res, symmAtomGroup) ); // Mark symmetric atoms as selected. for (AtomMap::Iarray::const_iterator at = grp->begin(); at != grp->end(); ++at) selected[ *at - res_first_atom ] = true; } } } // All other non-selected hydrogens bonded to same heavy atom are sites. for (int ratom = res_first_atom; ratom != setup.Top().Res(*res).LastAtom(); ++ratom) { if ( setup.Top()[ratom].Element() != Atom::HYDROGEN ) { Iarray heavyAtomGroup; for (Atom::bond_iterator ba = setup.Top()[ratom].bondbegin(); ba != setup.Top()[ratom].bondend(); ++ba) if ( Mask_.AtomInCharMask(*ba) && *ba >= res_first_atom && *ba < setup.Top().Res(*res).LastAtom() ) { if ( !selected[ *ba - res_first_atom ] && setup.Top()[ *ba ].Element() == Atom::HYDROGEN ) heavyAtomGroup.push_back( *ba ); } if (!heavyAtomGroup.empty()) potentialSites.push_back( Site(*res, heavyAtomGroup) ); } } } mprintf("\t%zu potential NOE sites:\n", potentialSites.size()); for (SiteArray::const_iterator site = potentialSites.begin(); site != potentialSites.end(); ++site) { mprintf(" %u\tRes %i:", site - potentialSites.begin(), site->ResNum()+1); for (unsigned int idx = 0; idx != site->Nindices(); ++idx) mprintf(" %s", setup.Top().TruncAtomNameNum( site->Idx(idx) ).c_str()); mprintf("\n"); } if (noeArray_.empty()) { size_t siteArraySize = 0; // Set up all potential NOE pairs. Keep track of size. for (SiteArray::const_iterator site1 = potentialSites.begin(); site1 != potentialSites.end(); ++site1) { for (SiteArray::const_iterator site2 = site1 + 1; site2 != potentialSites.end(); ++site2) { if (site1->ResNum() != site2->ResNum()) { std::string legend = site1->SiteLegend(setup.Top()) + "--" + site2->SiteLegend(setup.Top()); DataSet* ds = 0; if (series_) { ds = masterDSL_->AddSet(DataSet::FLOAT, MetaData(setname_, "foundNOE", noeArray_.size())); if (ds == 0) return Action::ERR; // Construct a data set name. ds->SetLegend(legend); } noeArray_.push_back( NOEtype(*site1, *site2, ds, legend) ); siteArraySize += (2 * sizeof(int) * site1->Nindices()) + (2 * sizeof(int) * site2->Nindices()); } } } numNoePairs_ = noeArray_.size(); size_t siteSize = sizeof(int) + (2 * sizeof(Iarray)) + sizeof(Site); size_t noeSize = (2 * siteSize) + sizeof(DataSet*) + sizeof(double) + sizeof(NOEtype); if (series_) noeSize += sizeof(std::vector<float>); size_t noeArraySize = (noeSize * numNoePairs_) + siteArraySize; if (series_) noeArraySize += (setup.Nframes() * numNoePairs_ * sizeof(float)); mprintf("\t%zu potential NOE pairs. Estimated memory usage is %s\n", numNoePairs_, ByteString(noeArraySize, BYTE_DECIMAL).c_str()); } else if (numNoePairs_ != potentialSites.size()) { mprinterr("Warning: Found NOE matrix has already been set up for %zu potential\n" "Warning: NOEs, but %zu NOEs currently found.\n", numNoePairs_, potentialSites.size()); return Action::SKIP; } } // --------------------------------------------- // Set up NOEs specified on the command line if (!Pairs_.empty()) { if (!specifiedNOEs_.empty()) { mprintf("Warning: Specifying NOEs currently only works with first topology used.\n"); return Action::SKIP; } for (MaskPairArray::iterator mp = Pairs_.begin(); mp != Pairs_.end(); mp++) { if (setup.Top().SetupIntegerMask( mp->first )) return Action::ERR; int res1 = CheckSameResidue(setup.Top(), mp->first); if (res1 < 0) continue; if (setup.Top().SetupIntegerMask( mp->second )) return Action::ERR; int res2 = CheckSameResidue(setup.Top(), mp->second); if (res2 < 0) continue; Site site1( res1, mp->first.Selected() ); Site site2( res2, mp->second.Selected() ); std::string legend = site1.SiteLegend(setup.Top()) + "--" + site2.SiteLegend(setup.Top()); DataSet* ds = 0; if (series_) { ds = masterDSL_->AddSet(DataSet::FLOAT, MetaData(setname_, "specNOE", specifiedNOEs_.size())); if (ds == 0) return Action::ERR; ds->SetLegend(legend); } specifiedNOEs_.push_back( NOEtype(site1, site2, ds, legend) ); } } // Set up imaging info for this parm Image_.SetupImaging( setup.CoordInfo().TrajBox().Type() ); if (Image_.ImagingEnabled()) mprintf("\tImaged.\n"); else mprintf("\tImaging off.\n"); return Action::OK; }
/** Set up solute and solvent masks. If no solvent mask was specified use * solvent information in the current topology. */ Action::RetType Action_Watershell::Setup(ActionSetup& setup) { // Set up solute mask if (setup.Top().SetupIntegerMask( soluteMask_ )) return Action::ERR; soluteMask_.MaskInfo(); if ( soluteMask_.None() ) { mprintf("Warning: No atoms in solute mask [%s].\n",soluteMask_.MaskString()); return Action::SKIP; } if (solventMask_.MaskStringSet()) { // Set up solvent mask if (setup.Top().SetupIntegerMask( solventMask_ )) return Action::ERR; solventMask_.MaskInfo(); } else { // Use all solvent atoms. solventMask_.ResetMask(); // Set number of atoms; needed for CharMask conversion. solventMask_.SetNatoms( setup.Top().Natom() ); for (Topology::mol_iterator mol = setup.Top().MolStart(); mol != setup.Top().MolEnd(); ++mol) if ( mol->IsSolvent() ) solventMask_.AddAtomRange( mol->BeginAtom(), mol->EndAtom() ); mprintf("\tSelecting all solvent atoms (%i total)\n", solventMask_.Nselected()); } if ( solventMask_.None() ) { if ( solventMask_.MaskStringSet() ) mprintf("Warning: No solvent atoms selected by mask [%s]\n", solventMask_.MaskString()); else mprintf("Warning: No solvent atoms in topology %s\n", setup.Top().c_str()); return Action::SKIP; } #ifdef CUDA // Since we are using the 'closest' kernels under the hood, all solvent mols // must have the same size. int first_solvent_mol = setup.Top()[ solventMask_[0] ].MolNum(); NAtoms_ = setup.Top().Mol( first_solvent_mol ).NumAtoms(); for (AtomMask::const_iterator atm = solventMask_.begin(); atm != solventMask_.end(); ++atm) { int mol = setup.Top()[*atm].MolNum(); if (NAtoms_ != setup.Top().Mol( mol ).NumAtoms()) { mprinterr("Error: CUDA version of 'watershell' requires all solvent mols be same size.\n"); return Action::ERR; } } // Determine how many solvent molecules are selected NsolventMolecules_ = 0; CharMask cMask( solventMask_.ConvertToCharMask(), solventMask_.Nselected() ); for (Topology::mol_iterator mol = setup.Top().MolStart(); mol != setup.Top().MolEnd(); ++mol) if ( cMask.AtomsInCharMask( mol->BeginAtom(), mol->EndAtom() ) ) NsolventMolecules_++; // Sanity check if ( (NsolventMolecules_ * NAtoms_) != solventMask_.Nselected() ) { mprinterr("Error: CUDA version of 'watershell' requires all atoms in solvent mols be selected.\n"); return Action::ERR; } // Allocate space for selected solvent atom coords and distances V_atom_coords_.resize( NsolventMolecules_ * NAtoms_ * 3, 0.0 ); V_distances_.resize( NsolventMolecules_ ); #else /* CUDA */ // Allocate space to record status of each solvent molecule. // NOTE: Doing this by residue instead of by molecule does waste some memory, // but it means watershell can be used even if no molecule info present. # ifdef _OPENMP // Each thread needs space to record residue status to avoid clashes for (std::vector<Iarray>::iterator it = shellStatus_thread_.begin(); it != shellStatus_thread_.end(); ++it) it->assign( setup.Top().Nres(), 0 ); # else shellStatus_.assign( setup.Top().Nres(), 0 ); # endif #endif /* CUDA */ // Set up imaging image_.SetupImaging( setup.CoordInfo().TrajBox().Type() ); if (image_.ImagingEnabled()) mprintf("\tImaging is on.\n"); else mprintf("\tImaging is off.\n"); // Allocate temp space for selected solute atom coords. soluteCoords_.resize( soluteMask_.Nselected() * 3 ); // Store current topology CurrentParm_ = setup.TopAddress(); return Action::OK; }
// Action_Diffusion::Setup() Action::RetType Action_Diffusion::Setup(ActionSetup& setup) { # ifdef TIMER Timer time_setup, time_addsets; time_setup.Start(); # endif // Setup atom mask if (setup.Top().SetupIntegerMask( mask_ )) return Action::ERR; mask_.MaskInfo(); if (mask_.None()) { mprintf("Warning: No atoms selected.\n"); return Action::SKIP; } // Check for box if ( setup.CoordInfo().TrajBox().Type() != Box::NOBOX ) { // Currently only works for orthogonal boxes if ( setup.CoordInfo().TrajBox().Type() != Box::ORTHO ) { mprintf("Warning: Imaging currently only works with orthogonal boxes.\n" "Warning: Imaging will be disabled for this command. This may result in\n" "Warning: large jumps if target molecule is imaged. To counter this please\n" "Warning: use the 'unwrap' command prior to 'diffusion'.\n"); hasBox_ = false; } else hasBox_ = true; } else hasBox_ = false; // Allocate the delta array delta_.assign( mask_.Nselected() * 3, 0.0 ); // Reserve space for the previous coordinates array previous_.reserve( mask_.Nselected() * 3 ); // If initial frame already set and current # atoms > # atoms in initial // frame this will probably cause an error. if (!initial_.empty() && setup.Top().Natom() > initial_.Natom()) { mprintf("Warning: # atoms in current parm (%s, %i) > # atoms in initial frame (%i)\n", setup.Top().c_str(), setup.Top().Natom(), initial_.Natom()); mprintf("Warning: This may lead to segmentation faults.\n"); } // Set up sets for individual atoms if necessary if (printIndividual_) { // Create as many spots for sets as needed. All do not have to be used. if (mask_.back() >= (int)atom_x_.size()) { int newSize = mask_.back() + 1; atom_x_.resize( newSize, 0 ); atom_y_.resize( newSize, 0 ); atom_z_.resize( newSize, 0 ); atom_r_.resize( newSize, 0 ); atom_a_.resize( newSize, 0 ); } for (AtomMask::const_iterator at = mask_.begin(); at != mask_.end(); at++) { if (atom_x_[*at] == 0) { # ifdef TIMER time_addsets.Start(); # endif atom_x_[*at] = masterDSL_->AddSet_NoCheck(DataSet::FLOAT, MetaData(dsname_, "aX", *at+1)); atom_y_[*at] = masterDSL_->AddSet_NoCheck(DataSet::FLOAT, MetaData(dsname_, "aY", *at+1)); atom_z_[*at] = masterDSL_->AddSet_NoCheck(DataSet::FLOAT, MetaData(dsname_, "aZ", *at+1)); atom_r_[*at] = masterDSL_->AddSet_NoCheck(DataSet::FLOAT, MetaData(dsname_, "aR", *at+1)); atom_a_[*at] = masterDSL_->AddSet_NoCheck(DataSet::FLOAT, MetaData(dsname_, "aA", *at+1)); # ifdef TIMER time_addsets.Stop(); # endif if (outputx_ != 0) outputx_->AddDataSet(atom_x_[*at]); if (outputy_ != 0) outputy_->AddDataSet(atom_y_[*at]); if (outputz_ != 0) outputz_->AddDataSet(atom_z_[*at]); if (outputr_ != 0) outputr_->AddDataSet(atom_r_[*at]); if (outputa_ != 0) outputa_->AddDataSet(atom_a_[*at]); atom_x_[*at]->SetDim(Dimension::X, Xdim_); atom_y_[*at]->SetDim(Dimension::X, Xdim_); atom_z_[*at]->SetDim(Dimension::X, Xdim_); atom_r_[*at]->SetDim(Dimension::X, Xdim_); atom_a_[*at]->SetDim(Dimension::X, Xdim_); } } } # ifdef TIMER time_setup.Stop(); time_addsets.WriteTiming(3, "Diffusion Add Sets", time_setup.Total()); time_setup.WriteTiming(2, "Diffusion Setup"); # endif return Action::OK; }
// Action_LESsplit::Setup() Action::RetType Action_LESsplit::Setup(ActionSetup& setup) { if ( !setup.Top().LES().HasLES() ) { mprintf("Warning: No LES parameters in '%s', skipping.\n", setup.Top().c_str()); return Action::SKIP; } if (lesParm_ == 0) { // First time setup // Set up masks for all copies lesMasks_.clear(); lesMasks_.resize( setup.Top().LES().Ncopies() ); unsigned int atom = 0; for (LES_Array::const_iterator les = setup.Top().LES().Array().begin(); les != setup.Top().LES().Array().end(); ++les, ++atom) { // Copy 0 is in all copies if ( les->Copy() == 0 ) { for (MaskArray::iterator mask = lesMasks_.begin(); mask != lesMasks_.end(); ++mask) mask->AddAtom( atom ); } else lesMasks_[ les->Copy() - 1 ].AddAtom( atom ); } for (unsigned int i = 0; i < lesMasks_.size(); i++) { mprintf("\t%i atoms in LES copy %u\n", lesMasks_[i].Nselected(), i+1); if ( lesMasks_[i].Nselected() != lesMasks_[0].Nselected() ) { mprinterr("Error: Currently all LES copies MUST have same # atoms.\n"); return Action::ERR; } } // Create topology for first copy lesParm_ = setup.Top().modifyStateByMask( lesMasks_[0] ); if (lesParm_ == 0) return Action::ERR; // Set up frames to hold individual copies lesFrames_.resize( lesMasks_.size() ); lesFrames_.SetupFrames(lesParm_->Atoms(), setup.CoordInfo()); lesPtrs_.resize( lesMasks_.size() ); for (unsigned int i = 0; i != lesMasks_.size(); i++) lesPtrs_[i] = &lesFrames_[i]; if (lesSplit_) { // Set up output ensemble FIXME check overwrites TODO combine init/setup? if (lesTraj_.InitEnsembleWrite(trajfilename_, trajArgs_, lesMasks_.size(), TrajectoryFile::UNKNOWN_TRAJ)) return Action::ERR; if (lesTraj_.SetupEnsembleWrite(lesParm_, setup.CoordInfo(), setup.Nframes())) return Action::ERR; lesTraj_.PrintInfo(0); } if (lesAverage_) { // For average only care about coords. avgFrame_.SetupFrame( lesParm_->Natom() ); if (avgTraj_.PrepareTrajWrite( avgfilename_, trajArgs_, lesParm_, CoordinateInfo(), setup.Nframes(), TrajectoryFile::UNKNOWN_TRAJ )) return Action::ERR; avgTraj_.PrintInfo(0); } } else { if (lesParm_->Pindex() != setup.Top().Pindex()) { mprintf("Warning: Already set up for LES parm '%s'. Skipping '%s'\n", lesParm_->c_str(), setup.Top().c_str()); return Action::SKIP; } } return Action::OK; }
// Action_RandomizeIons::Setup() Action::RetType Action_RandomizeIons::Setup(ActionSetup& setup) { n_solvent_ = setup.Top().Nsolvent(); if (n_solvent_ < 1) { mprinterr("Error: This command only works if solvent information has been specified.\n"); return Action::ERR; } // Set up ion mask if (setup.Top().SetupIntegerMask( ions_ )) return Action::ERR; if ( ions_.None() ) { mprintf("Warning: Ion mask '%s' has no atoms.\n", ions_.MaskString()); return Action::SKIP; } mprintf("\tIon mask is '%s' (%i atoms)\n", ions_.MaskString(), ions_.Nselected()); // Set up the around mask if necessary if (around_.MaskStringSet()) { if (setup.Top().SetupIntegerMask( around_ )) return Action::ERR; if ( around_.None() ) { mprintf("Warning: Around mask '%s' has no atoms.\n", around_.MaskString()); } else { mprintf("\tAround mask is '%s' (%i atoms)\n", around_.MaskString(), around_.Nselected()); } } // Check that each ion is only a single atom residue. // NOTE: Should this be a molecule check instead? If so can then get rid of ResSize for (AtomMask::const_iterator ion = ions_.begin(); ion != ions_.end(); ++ion) { int res = setup.Top()[*ion].ResNum(); if (debug_ > 0) mprintf("\tAtom %i is in residue %i which is %i atoms\n", *ion+1, res+1, setup.Top().Res( res ).NumAtoms() ); if ( setup.Top().Res( res ).NumAtoms() > 1 ) { mprintf("Warning: randomizeions: Ion atom %i belongs to residue %i which\n", *ion + 1, res + 1); mprintf("Warning: contains more than 1 atom (%i)!\n", setup.Top().Res( res ).NumAtoms()); } } // Check the solvent information to make sure that each solvent listed has the // same number of atoms in each molecule; otherwise a uniform trajectory is not // possible and therefore this command will be ignored. // Also save the start and end atom of each solvent molecule. int NsolventAtoms = -1; solventStart_.clear(); solventEnd_.clear(); solventStart_.reserve( n_solvent_ ); solventEnd_.reserve( n_solvent_ ); for (Topology::mol_iterator Mol = setup.Top().MolStart(); Mol != setup.Top().MolEnd(); ++Mol) { if ( Mol->IsSolvent() ) { if (NsolventAtoms == -1) NsolventAtoms = Mol->NumAtoms(); else if ( NsolventAtoms != Mol->NumAtoms() ) { mprinterr("Error: Solvent molecules in %s are not of uniform size.\n", setup.Top().c_str()); mprinterr("Error: First solvent mol = %i atoms, this solvent mol = %i atoms.\n", NsolventAtoms, Mol->NumAtoms()); return Action::ERR; } solventStart_.push_back( Mol->BeginAtom() ); solventEnd_.push_back( Mol->EndAtom() ); } } image_.SetupImaging( setup.CoordInfo().TrajBox().Type() ); // Allocate solvent molecule mask solvent_.resize( n_solvent_ ); return Action::OK; }
// Action_Diffusion::Setup() Action::RetType Action_Diffusion::Setup(ActionSetup& setup) { # ifdef TIMER Timer time_setup, time_addsets; time_setup.Start(); # endif // Setup atom mask if (setup.Top().SetupIntegerMask( mask_ )) return Action::ERR; mask_.MaskInfo(); if (mask_.None()) { mprintf("Warning: No atoms selected.\n"); return Action::SKIP; } // Set up imaging info for this parm image_.SetupImaging( setup.CoordInfo().TrajBox().Type() ); if (image_.ImagingEnabled()) { mprintf("\tImaging enabled.\n"); # ifdef MPI if (trajComm_.Size() > 1) { mprinterr("Error: Imaging for 'diffusion' is not supported in parallel as there is\n" "Error: no way to correct for imaging that has taken place on preceding\n" "Error: MPI ranks. To use 'diffusion' in parallel, the trajectory should\n" "Error: be unwrapped. If this trajectory has already been unwrapped please\n" "Error: specify the 'noimage' keyword.\n"); return Action::ERR; } # endif } else mprintf("\tImaging disabled.\n"); // Allocate the delta array delta_.assign( mask_.Nselected() * 3, 0.0 ); // Reserve space for the previous coordinates array previous_.reserve( mask_.Nselected() * 3 ); // If initial frame already set and current # atoms > # atoms in initial // frame this will probably cause an error. if (!initial_.empty() && setup.Top().Natom() > initial_.Natom()) { mprintf("Warning: # atoms in current parm (%s, %i) > # atoms in initial frame (%i)\n", setup.Top().c_str(), setup.Top().Natom(), initial_.Natom()); mprintf("Warning: This may lead to segmentation faults.\n"); } // Set up sets for individual atoms if necessary if (printIndividual_) { // Create as many spots for sets as needed. All do not have to be used. if (mask_.back() >= (int)atom_x_.size()) { int newSize = mask_.back() + 1; atom_x_.resize( newSize, 0 ); atom_y_.resize( newSize, 0 ); atom_z_.resize( newSize, 0 ); atom_r_.resize( newSize, 0 ); atom_a_.resize( newSize, 0 ); } for (AtomMask::const_iterator at = mask_.begin(); at != mask_.end(); at++) { if (atom_x_[*at] == 0) { # ifdef TIMER time_addsets.Start(); # endif atom_x_[*at] = masterDSL_->AddSet_NoCheck(DataSet::FLOAT, MetaData(dsname_, "aX", *at+1)); atom_y_[*at] = masterDSL_->AddSet_NoCheck(DataSet::FLOAT, MetaData(dsname_, "aY", *at+1)); atom_z_[*at] = masterDSL_->AddSet_NoCheck(DataSet::FLOAT, MetaData(dsname_, "aZ", *at+1)); atom_r_[*at] = masterDSL_->AddSet_NoCheck(DataSet::FLOAT, MetaData(dsname_, "aR", *at+1)); atom_a_[*at] = masterDSL_->AddSet_NoCheck(DataSet::FLOAT, MetaData(dsname_, "aA", *at+1)); # ifdef TIMER time_addsets.Stop(); # endif if (outputx_ != 0) outputx_->AddDataSet(atom_x_[*at]); if (outputy_ != 0) outputy_->AddDataSet(atom_y_[*at]); if (outputz_ != 0) outputz_->AddDataSet(atom_z_[*at]); if (outputr_ != 0) outputr_->AddDataSet(atom_r_[*at]); if (outputa_ != 0) outputa_->AddDataSet(atom_a_[*at]); atom_x_[*at]->SetDim(Dimension::X, Xdim_); atom_y_[*at]->SetDim(Dimension::X, Xdim_); atom_z_[*at]->SetDim(Dimension::X, Xdim_); atom_r_[*at]->SetDim(Dimension::X, Xdim_); atom_a_[*at]->SetDim(Dimension::X, Xdim_); } } } # ifdef TIMER time_setup.Stop(); time_addsets.WriteTiming(3, "Diffusion Add Sets", time_setup.Total()); time_setup.WriteTiming(2, "Diffusion Setup"); # endif return Action::OK; }
// Action_AutoImage::Setup() Action::RetType Action_AutoImage::Setup(ActionSetup& setup) { bool fixedauto = false; bool mobileauto = false; if (setup.Top().Nmol() < 1) { mprintf("Warning: Topology %s does not contain molecule information\n", setup.Top().c_str()); return Action::SKIP; } // Determine Box info Box::BoxType boxType = setup.CoordInfo().TrajBox().Type(); if (boxType == Box::NOBOX) { mprintf("Warning: Topology %s does not contain box information.\n", setup.Top().c_str()); return Action::SKIP; } ortho_ = false; if (boxType == Box::ORTHO && triclinic_ == OFF) ortho_ = true; // If box is originally truncated oct and not forcing triclinic, // turn familiar on. if (boxType == Box::TRUNCOCT && triclinic_ != FORCE && triclinic_ != FAMILIAR) { mprintf("\tOriginal box is truncated octahedron, turning on 'familiar'.\n"); triclinic_ = FAMILIAR; } // Set up anchor region if (!anchor_.empty()) { anchorList_ = SetupAtomRanges( setup.Top(), anchor_ ); } else { anchorList_.clear(); anchorList_.push_back( setup.Top().Mol(0).BeginAtom() ); anchorList_.push_back( setup.Top().Mol(0).EndAtom() ); } if (anchorList_.empty() || anchorList_.size() > 2) { mprinterr("Error: Anchor mask [%s] corresponds to %zu mols, should only be 1.\n", anchor_.c_str(), anchorList_.size() / 2); return Action::ERR; } // Set up mask for centering anchor anchorMask_.ResetMask(); anchorMask_.AddAtomRange( anchorList_[0], anchorList_[1] ); int anchormolnum = setup.Top()[ anchorList_[0] ].MolNum(); mprintf("\tAnchor molecule is %i\n", anchormolnum+1); // Set up fixed region if (!fixed_.empty()) fixedList_ = SetupAtomRanges( setup.Top(), fixed_ ); else { fixedauto = true; fixedList_.clear(); } // Set up mobile region if (!mobile_.empty()) mobileList_ = SetupAtomRanges( setup.Top(), mobile_ ); else { mobileauto = true; mobileList_.clear(); } // Automatic search through molecules for fixed/mobile if (fixedauto || mobileauto) { int molnum = 0; for (Topology::mol_iterator mol = setup.Top().MolStart(); mol != setup.Top().MolEnd(); mol++) { // Skip the anchor molecule if (molnum != anchormolnum) { // Solvent and 1 atom molecules (prob. ions) go in mobile list, // everything else into fixed list. if ( (*mol).IsSolvent() || (*mol).NumAtoms() == 1 ) { if (mobileauto) { mobileList_.push_back( (*mol).BeginAtom() ); mobileList_.push_back( (*mol).EndAtom() ); } } else { if (fixedauto) { fixedList_.push_back( (*mol).BeginAtom() ); fixedList_.push_back( (*mol).EndAtom() ); } } } ++molnum; } } // DEBUG: Print fixed and mobile lists if (!fixedList_.empty()) { mprintf("\tThe following molecules are fixed to anchor:"); for (pairList::const_iterator atom = fixedList_.begin(); atom != fixedList_.end(); atom += 2) mprintf(" %i", setup.Top()[ *atom ].MolNum()+1 ); mprintf("\n"); } mprintf("\t%zu molecules are mobile.\n", mobileList_.size() / 2 ); //mprintf("\tThe following molecules are mobile:\n"); //for (pairList::const_iterator atom = mobileList_.begin(); // atom != mobileList_.end(); atom += 2) // mprintf("\t\t%i\n", setup.Top()[ *atom ].MolNum()+1 ); truncoct_ = (triclinic_==FAMILIAR); return Action::OK; }