Main Page   Namespace List   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members   File Members   Related Pages  

Timestep.C

Go to the documentation of this file.
00001 /***************************************************************************
00002  *cr                                                                       
00003  *cr            (C) Copyright 1995-2011 The Board of Trustees of the           
00004  *cr                        University of Illinois                       
00005  *cr                         All Rights Reserved                        
00006  *cr                                                                   
00007  ***************************************************************************/
00008 
00009 /***************************************************************************
00010  * RCS INFORMATION:
00011  *
00012  *      $RCSfile: Timestep.C,v $
00013  *      $Author: johns $        $Locker:  $             $State: Exp $
00014  *      $Revision: 1.64 $       $Date: 2011/05/19 05:17:52 $
00015  *
00016  ***************************************************************************
00017  * DESCRIPTION:
00018  *
00019  * The Timestep class, which stores coordinates, energies, etc. for a
00020  * single timestep.
00021  *
00022  * Note: As more data is stored for each step, it should go in here.  For
00023  * example, H-Bonds could be calculated each step.
00024  ***************************************************************************/
00025 
00026 #include <math.h>
00027 #include "Timestep.h"
00028 #include "Inform.h"
00029 #include "utilities.h"
00030 
00031 /* Set the maximum direct I/O aligned block size we are willing to support */
00032 #define TS_MAX_BLOCKIO 4096
00033 
00034 /* allocate memory and return a pointer that is aligned on a given   */
00035 /* byte boundary, to be used for page- or sector-aligned I/O buffers */
00036 /* We use this since posix_memalign() is not widely available...     */
00037 #if 1 /* sizeof(unsigned long) == sizeof(void*) */
00038 #define myintptrtype unsigned long
00039 #elif 1   /* sizeof(size_t) == sizeof(void*) */
00040 #define myintptrtype size_t
00041 #else
00042 #define myintptrtype uintptr_t  /* C99 */
00043 #endif
00044 static void *alloc_aligned_ptr(size_t sz, size_t blocksz, void **unalignedptr) {
00045   // pad the allocation to an even multiple of the block size
00046   size_t padsz = (sz + (blocksz - 1)) & (~(blocksz - 1));
00047   void * ptr = malloc(padsz + blocksz + blocksz);
00048   *unalignedptr = ptr;
00049   return (void *) ((((myintptrtype) ptr) + (blocksz-1)) & (~(blocksz-1)));
00050 }
00051 
00052 
00054 Timestep::Timestep(int n) {
00055   for(int i=0; i < TSENERGIES; energy[i++] = 0.0);
00056   num = n;
00057 #if defined(TS_MAX_BLOCKIO)
00058   pos = (float *) alloc_aligned_ptr(3*num*sizeof(float), 
00059                                     TS_MAX_BLOCKIO, (void**) &pos_ptr);
00060 #else
00061   pos_ptr = new float[3 * num]
00062   pos=pos_ptr;
00063 #endif
00064   vel = NULL;
00065   force = NULL;
00066   user  = NULL;
00067   user2 = NULL;
00068   user3 = NULL;
00069   user4 = NULL;
00070   qm_timestep = NULL;
00071   a_length = b_length = c_length = 0;
00072   alpha = beta = gamma = 90;
00073   timesteps=0;
00074   physical_time=0;
00075 }
00076 
00077 
00079 Timestep::Timestep(const Timestep& ts) {
00080   num = ts.num;
00081 
00082 #if defined(TS_MAX_BLOCKIO)
00083   // If we supprot block-based direct I/O, we must use memory buffers
00084   // that are padded to a full block size, and  
00085   pos = (float *) alloc_aligned_ptr(3*num*sizeof(float), 
00086                                     TS_MAX_BLOCKIO, (void**) &pos_ptr);
00087 #else
00088   pos_ptr = new float[3 * num]
00089   pos=pos_ptr;
00090 #endif
00091   memcpy(pos, ts.pos, 3 * num * sizeof(float));
00092 
00093   if (ts.force) {
00094     force = new float[3 * num];
00095     memcpy(force, ts.force, 3 * num * sizeof(float));
00096   } else {
00097     force = NULL;
00098   }
00099 
00100   if (ts.vel) {
00101     vel = new float[3 * num];
00102     memcpy(vel, ts.vel, 3 * num * sizeof(float));
00103   } else {
00104     vel = NULL;
00105   }
00106 
00107   if (ts.user) {
00108     user = new float[num];
00109     memcpy(user, ts.user, num*sizeof(float));
00110   } else {
00111     user = NULL;
00112   }
00113 
00114   if (ts.user2) {
00115     user2 = new float[num];
00116     memcpy(user2, ts.user2, num*sizeof(float));
00117   } else {
00118     user2 = NULL;
00119   }
00120 
00121   if (ts.user3) {
00122     user3 = new float[num];
00123     memcpy(user3, ts.user3, num*sizeof(float));
00124   } else {
00125     user3 = NULL;
00126   }
00127 
00128   if (ts.user4) {
00129     user4 = new float[num];
00130     memcpy(user4, ts.user4, num*sizeof(float));
00131   } else {
00132     user4 = NULL;
00133   }
00134 
00135   if (ts.qm_timestep) {
00136     qm_timestep = new QMTimestep(*(ts.qm_timestep));
00137   } else {
00138     qm_timestep = NULL;
00139   }
00140 
00141   memcpy(energy, ts.energy, sizeof(ts.energy));
00142   a_length = ts.a_length;
00143   b_length = ts.b_length;
00144   c_length = ts.c_length;
00145   alpha = ts.alpha;
00146   beta = ts.beta;
00147   gamma = ts.gamma;
00148   timesteps=ts.timesteps;
00149   physical_time=ts.physical_time;
00150 }
00151 
00152 
00154 Timestep::~Timestep() {
00155   delete [] force;
00156   delete [] vel;
00157 #if defined(TS_MAX_BLOCKIO)
00158   if (pos_ptr)
00159     free(pos_ptr);
00160 #else
00161   delete [] pos_ptr;
00162 #endif
00163   delete [] user;
00164   delete [] user2;
00165   delete [] user3;
00166   delete [] user4;
00167   if (qm_timestep) 
00168     delete qm_timestep;
00169 }
00170 
00171 // reset coords and related items to 0
00172 void Timestep::zero_values() {
00173   if (num <= 0) 
00174     return;
00175     
00176   memset(pos,0,3*num*sizeof(float));
00177    
00178   for(int i=0; i < TSENERGIES; energy[i++] = 0.0);
00179   timesteps=0;
00180 }
00181 
00182 void Timestep::get_transform_vectors(float A[3], float B[3], float C[3]) const
00183 {
00184   // notes: a, b, c are side lengths of the unit cell
00185   // alpha = angle between b and c
00186   //  beta = angle between a and c
00187   // gamma = angle between a and b
00188 
00189   // convert from degrees to radians
00190   double cosBC = cos(DEGTORAD(alpha));
00191   double cosAC = cos(DEGTORAD(beta));
00192   double cosAB = cos(DEGTORAD(gamma));
00193   double sinAB = sin(DEGTORAD(gamma));
00194 
00195   // A will lie along the positive x axis.
00196   // B will lie in the x-y plane
00197   // The origin will be (0,0,0).
00198   float Ax = (float) (a_length);
00199   float Bx = (float) (b_length * cosAB);
00200   float By = (float) (b_length * sinAB);
00201 
00202   float Cx=0, Cy=0, Cz=0;
00203   // If sinAB is zero, then we can't determine C uniquely since it's defined
00204   // in terms of the angle between A and B.
00205   if (sinAB > 0) {
00206     Cx = (float) cosAC;
00207     Cy = (float) ((cosBC - cosAC * cosAB) / sinAB);
00208     Cz = sqrtf(1.0f - Cx*Cx - Cy*Cy);
00209   }
00210   Cx *= c_length;
00211   Cy *= c_length;
00212   Cz *= c_length;
00213   vec_zero(A); A[0] = Ax;
00214   vec_zero(B); B[0] = Bx; B[1] = By;
00215   vec_zero(C); C[0] = Cx; C[1] = Cy; C[2] = Cz;
00216 }
00217 
00218 void Timestep::get_transforms(Matrix4 &a, Matrix4 &b, Matrix4 &c) const {
00219   float A[3], B[3], C[3];
00220   get_transform_vectors(A, B, C);
00221   a.translate(A);
00222   b.translate(B);
00223   c.translate(C);
00224 }
00225 
00226 void Timestep::get_transform_from_cell(const int *cell, Matrix4 &mat) const {
00227   float A[3], B[3], C[3];
00228   get_transform_vectors(A, B, C);
00229   float Ax=A[0];
00230   float Bx=B[0];
00231   float By=B[1];
00232   float Cx=C[0];
00233   float Cy=C[1];
00234   float Cz=C[2];
00235   mat.identity();
00236   mat.mat[12] = cell[0]*Ax + cell[1]*Bx + cell[2]*Cx;
00237   mat.mat[13] =              cell[1]*By + cell[2]*Cy;            
00238   mat.mat[14] =                           cell[2]*Cz;
00239 }
00240 

Generated on Sat May 26 01:48:32 2012 for VMD (current) by doxygen1.2.14 written by Dimitri van Heesch, © 1997-2002