LALSimulation  5.4.0.1-fe68b98
LALSimIMRSpinPrecEOBWfGen.c
Go to the documentation of this file.
1 #ifndef _LALSIMIMRSPINPRECEOBWFGEN_C
2 #define _LALSIMIMRSPINPRECEOBWFGEN_C
3 
4 /**************************************
5  **************************************
6  ** OPTV3:
7  ** This function outputs hp2, hp1, h0, hm1, and hm2
8  ** which are the h modes for l=2; m = 2, 1, ..., -2
9  ** It is Organized into 7 steps:
10  ** (1) the Hamiltonian
11  ** (2) seobCoeffs
12  ** (3) dvalues
13  ** (4) omega
14  ** (5) hCoeffs
15  ** (6) polarDynamics
16  ** (7) hLM
17  **************************************
18  **************************************/
20  COMPLEX16 * hp2, /**<< OUTPUT: h; m = 2 mode */
21  COMPLEX16 * hp1, /**<< OUTPUT: h; m = 1 mode */
22  COMPLEX16 * h0, /**<< OUTPUT: h; m = 0 mode */
23  COMPLEX16 * hm1, /**<< OUTPUT: h; m = -1 mode */
24  COMPLEX16 * hm2, /**<< OUTPUT: h; m = -2 mode */
25  SpinEOBParams * seobParams, /**<< EOB Parameters */
26  REAL8Vector * values /**<< Dynamical variables */
27  ){
28  COMPLEX16 hLM, hNQC;
29  REAL8 ham, omega, v, magR2, s1dotLN, s2dotLN, chiS, chiA, tplspin;
30  REAL8 rcrossrdot[3], rcrossp[3];
31  REAL8 a2 = 0.0;
32  REAL8 m1 = seobParams->eobParams->m1;
33  REAL8 m2 = seobParams->eobParams->m2;
34 
35  REAL8 dvaluesData[14] = {0.};
36  REAL8 polarDynamicsData[4] = {0.};
37  REAL8Vector dvalues;
38  REAL8Vector polarDynamics;
39  dvalues.length = 14;
40  polarDynamics.length = 4;
41  polarDynamics.data = polarDynamicsData;
42  dvalues.data = dvaluesData;
43 
44  /** OPTV3: (1): the Hamiltonian **/
45  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3099-3102*/
46  for(int i=0; i<3; i++){
47  seobParams->sigmaKerr->data[i] = values->data[i+6] + values->data[i+9];
48  seobParams->sigmaStar->data[i] = (m2/m1)*values->data[i+6] + (m1/m2)*values->data[i+9];
49  a2 += seobParams->sigmaKerr->data[i]*seobParams->sigmaKerr->data[i];
50  }
51 
52  /* Calculate the value of the Hamiltonian */
53  {
54 
55  REAL8 rCartData[3], pCartData[3], s1CartData[3], s2CartData[3];
56 
57  REAL8Vector rCartVec;
58  REAL8Vector pCartVec;
59  REAL8Vector s1CartVec;
60  REAL8Vector s2CartVec;
61 
62  rCartVec.length = pCartVec.length = s1CartVec.length = s2CartVec.length = 3;
63 
64  rCartVec.data = rCartData;
65  pCartVec.data = pCartData;
66  s1CartVec.data = s1CartData;
67  s2CartVec.data = s2CartData;
68 
69  memcpy(rCartVec.data, values->data, 3*sizeof(REAL8));
70  memcpy(pCartVec.data, values->data+3, 3*sizeof(REAL8));
71  memcpy(s1CartVec.data, values->data+6, 3*sizeof(REAL8));
72  memcpy(s2CartVec.data, values->data+9, 3*sizeof(REAL8));
73 
74  REAL8Vector * rCart = &rCartVec;
75  REAL8Vector * pCart = &pCartVec;
76  REAL8Vector * s1Cart = &s1CartVec;
77  REAL8Vector * s2Cart = &s2CartVec;
78 
79  ham = XLALSimIMRSpinPrecEOBHamiltonian( seobParams->eobParams->eta, rCart, pCart, s1Cart, s2Cart, seobParams->sigmaKerr, seobParams->sigmaStar, seobParams->tortoise, seobParams->seobCoeffs );
80  }
81  /** OPTV3: (2): hCoeffs**/
82  seobParams->a = sqrt(a2); /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3102*/
83 
84  // OPTV3: SpinAlignedEOBversion = 2
85  XLALSimIMRCalculateSpinEOBHCoeffs( seobParams->seobCoeffs, seobParams->eobParams->eta, seobParams->a, 2); /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3127*/
86 
87  /** OPTV3: (3): dValues**/
88  memset( dvalues.data, 0, 14*sizeof(REAL8));
89  XLALSpinPrecHcapRvecDerivative_exact(0.0, values->data, dvalues.data, seobParams); /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3006*/
90 
91  /** OPTV3: (4): omega **/
92 
93  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3017-3020*/
94  /* Calculate omega */
95  cross_product(values->data,dvalues.data,rcrossrdot);
96  magR2 = inner_product(values->data, values->data);
97  omega = sqrt(inner_product(rcrossrdot,rcrossrdot))/magR2;
98  v = cbrt( omega );
99 
100  /** OPTV3: (5): hCoeffs **/
101 
102  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3107-3111*/
103  /* Update Hamiltonian coefficients as per |Skerr| */
104  s1dotLN = inner_product(values->data+6, rcrossrdot)/(m1*m2);
105  s2dotLN = inner_product(values->data+9, rcrossrdot)/(m1*m2);
106  chiS = 0.5 * (s1dotLN + s2dotLN);
107  chiA = 0.5 * (s1dotLN - s2dotLN);
108 
109  // OPTV3: Because SpinAlignedEOBVersion = 2
110  tplspin = (1.-2.*seobParams->eobParams->eta) * chiS + (m1 - m2)/(m1 + m2) * chiA; /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3119*/
111 
112  /* Update hlm coefficients */
113  // OPTV3: SpinAlignedEOBversion = 2
114  XLALSimIMREOBCalcSpinPrecFacWaveformCoefficients( seobParams->eobParams->hCoeffs, m1, m2, seobParams->eobParams->eta, tplspin, chiS, chiA, 3 ); /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3133*/
115 
116  /** OPTV3: (6): polarDynamics **/
117  /* Calculate the polar data */
118  /* Calculate the orbital angular momentum */
119  cross_product( values->data, values->data+3, rcrossp );
120 
121  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3150-3153*/
122  polarDynamics.data[0] = sqrt(magR2);
123  polarDynamics.data[1] = values->data[13] + values->data[12]; // OPTV3: phiMod.data[i] + phiDMod.data[i];
124  polarDynamics.data[2] = inner_product(values->data, values->data+3) / polarDynamics.data[0];
125  polarDynamics.data[3] = sqrt(inner_product(rcrossp, rcrossp));
126 
127  /** OPTV3: (7) hLM **/
128 
129  XLALSimIMRSpinEOBGetPrecSpinFactorizedWaveform_exact( &hLM, &polarDynamics, values, v, ham, 2, 2, seobParams ); /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3155*/
130  XLALSimIMRSpinEOBNonQCCorrection( &hNQC, values, omega, seobParams->nqcCoeffs ); /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3160*/
131 
132  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3165-3167*/
133  hLM *= hNQC;
134  *hp2= hLM;
135  *hm2= conjl(hLM);
136 
137  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3178*/
138  XLALSimIMRSpinEOBGetPrecSpinFactorizedWaveform_exact( &hLM, &polarDynamics, values, v, ham, 2, 1, seobParams );
139 
140  /*OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3183-3185*/
141  *hp1 = hLM;
142  *hm1 = conjl(hLM);
143  *h0 = 0.0;
144 }
145 
147  SpinEOBParams * seobParams, /**<< EOB Parameters */
148  REAL8Vector * values, /**<< Dynamical variables */
149  REAL8 aI2P, /**<< alpha Euler angle from inertial to precessing frame */
150  REAL8 bI2P, /**<< beta Euler angle from inertial to precessing frame */
151  REAL8 gI2P, /**<< gamma Euler angle from inertial to precessing frame */
152  REAL8 alJtoI, /**<< alpha Euler angle from final-J frame to Inertial frame*/
153  REAL8 betJtoI, /**<< beta Euler angle from final-J frame to Inertial frame*/
154  REAL8 gamJtoI, /**<< gamma Euler angle from final-J frame to Inertial frame*/
155  REAL8 JframeEx[3], /**<< x-axis of the total-angular-momentum frame */
156  REAL8 JframeEy[3], /**<< y-axis of the total-angular-momentum frame */
157  REAL8 JframeEz[3], /**<< z-axis of the total-angular-momentum frame */
158  COMPLEX16 Y[5], /**<< Spherical Harmonics */
159  REAL8 * hplus, /**<< OUTPUT: h_+ */
160  REAL8 * hcross /**<< OUTPUT: h_x */
161  ){
162  COMPLEX16 hTSp2, hTSp1, hTS0, hTSm1, hTSm2;
163  REAL8 aP2J, bP2J, gP2J;
164  REAL8 LNhx, LNhy, LNhz;
165  COMPLEX16 hxx[5], hresult[5], hresult2[5];
166  REAL8 rcrossrdot[3], magrcrossrdot;
167  REAL8 rdot[3] = {0.,0.,0.};
168 
169  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3311*/
170  XLALEOBSpinPrecCalcHModes(&hTSp2, &hTSp1, &hTS0, &hTSm1, &hTSm2, seobParams,values);
171  /** OPTV3: rotate by alpha, beta, gamma */
172 
173  /* First prepare the rotation angles */
174  hxx[0]= hTSm2; hxx[1]=hTSm1; hxx[2]=hTS0; hxx[3]=hTSp1, hxx[4]=hTSp2;
175 
176  /* Calculate dr/dt */
177  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3006, 3311*/
178  XLALSpinPrecHcapRvecDerivative_exact(0.0, values->data, rdot, seobParams);
179 
180  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3030, 3323*/
181  cross_product(values->data,rdot,rcrossrdot);
182 
183  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3033*/
184  magrcrossrdot = sqrt(inner_product(rcrossrdot,rcrossrdot));
185 
186  LNhx = rcrossrdot[0]/magrcrossrdot;
187  LNhy = rcrossrdot[1]/magrcrossrdot;
188  LNhz = rcrossrdot[2]/magrcrossrdot;
189 
190  /*Rounding LNhz creates the possible issue of causing the input for the acos() call in EulerAnglesP2J
191  to be out of the [-1,1] interval required by the function, so it has been commented out.
192  The other two rounding statements are being removed because they do not appear in the current version
193  of the unoptimized code. -Tom Adams*/
194 // if (fabs(LNhx) < 1.e-7)
195 // LNhx = 0.0;
196 // if (fabs(LNhy) < 1.e-7)
197 // LNhy = 0.0;
198 // if (fabs(LNhz-1.0) < 1.e-7)
199 // LNhz = 1.0;
200 
201  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3342-3358, 3375-3377*/
202  EulerAnglesP2J(&aP2J,&bP2J,&gP2J,aI2P, bI2P, gI2P, LNhx, LNhy, LNhz, JframeEx, JframeEy, JframeEz );
203  aP2J = -aP2J;
204  gP2J = -gP2J;
205 
206  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 3570,3602*/
207  /* OPTV3: From XLALSimInspiralPrecessionRotateModes; LALSimInspiralPrecess.c; line(s): 62-66*/
208  COMPLEX16 W[5][5];
209  int l = 2;
210  for(int m=0; m<2*l+1; m++){
211  hresult[m]=0.+0.*I;
212  for(int mp=0; mp<2*l+1; mp++){
213  W[m][mp]=XLALWignerDMatrix( l, mp-l, m-l, aP2J , bP2J , gP2J);
214  hresult[m] += hxx[mp] * W[m][mp];
215 // hresult[m] += hxx[mp] * XLALWignerDMatrix( l, mp-l, m-l, aP2J , bP2J , gP2J);
216 // printf("[%.4e|%.4e]= hresult[%d] += hxx[%d] * W[%d][%d] = [%.4e|%.4e] * [%.4e|%.4e]\n",cabs(hresult[m]),carg(hresult[m]),m,mp,m,mp, cabs(hxx[mp]), carg(hxx[mp]), cabs(W[m][mp]),carg(W[m][mp]));
217  }
218  }
219  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; 3966*/
220  /* OPTV3: From XLALSimInspiralPrecessionRotateModes; LALSimInspiralPrecess.c; 62-66*/
221  for(int m=0; m<2*l+1; m++){
222  hresult2[m]=0.+0.*I;
223  for(int mp=0; mp<2*l+1; mp++)
224  hresult2[m] += hresult[mp] * XLALWignerDMatrix( l, mp-l, m-l, alJtoI , betJtoI , gamJtoI);
225  }
226  /* OPTV3: From XLALSimIMRSpinEOBWaveformAll; LALSimIMRSpinPrecEOB.c; line(s): 4022-4028*/
227  COMPLEX16 x11 = 0.0+0.0*I;
228  for (int i=0; i<2*l+1; i++) x11 += Y[i]*hresult2[i];
229  /** OPTV3: Now, evaluate the real & imaginary parts to get hplus & hcross */
230  *hplus = creal(x11);
231  *hcross = cimag(x11);
232 }
233 
235  COMPLEX16 * hTSm2, /**<< OUTPUT: Complex h array, mode m=2, length=retLen */
236  COMPLEX16 * hTSm1, /**<< OUTPUT: Complex h array, mode m=1, length=retLen */
237  COMPLEX16 * hTS0, /**<< OUTPUT: Complex h array, mode m=0, length=retLen */
238  COMPLEX16 * hTSp1, /**<< OUTPUT: Complex h array, mode m=-1, length=retLen */
239  COMPLEX16 * hTSp2, /**<< OUTPUT: Complex h array, mode m=-2, length=retLen */
240  int retLen, /**<< returned length from ODE solution */
241  REAL8Array * dynamics, /**<< Dynamical Variables */
242  SpinEOBParams * seobParams /**<< EOB Parameters */
243  ){
244 
245  REAL8 valuesdata[14] = {0.};
246  REAL8Vector values;
247  values.length=14;
248  values.data= valuesdata;
249 
250  for(int t = 0; t<retLen; t++){
251  for (int i=1; i<=14; i++)
252  values.data[i-1]=dynamics->data[t+i*retLen];
253  XLALEOBSpinPrecCalcHModes(hTSp2+t,hTSp1+t,hTS0+t,hTSm1+t,hTSm2+t,seobParams,&values);
254  }
255 }
256 
258  REAL8Vector * h, /**<< OUTPUT: Vector containing time, hplus, and hcross */
259  int retLen, /**<< Length of ODE solution */
260  REAL8Vector * AlphaI2PVec, /**<< Vector of Euler angle alpha, from Inertial to precessing frame, across time */
261  REAL8Vector * BetaI2PVec, /**<< Vector of Euler angle beta, from Inertial to precessing frame, across time */
262  REAL8Vector * GammaI2PVec, /**<< Vector of Euler angle gamma, from Inertial to precessing frame, across time */
263  REAL8 Jx[3], /**<< x-axis of the total-angular-momentum frame */
264  REAL8 Jy[3], /**<< y-axis of the total-angular-momentum frame */
265  REAL8 Jz[3], /**<< z-axis of the total-angular-momentum frame */
266  COMPLEX16 Y[5], /**<< Spherical Harmonics */
267  REAL8Array * dynamics, /**<< Dynamical Variables */
268  SpinEOBParams * seobParams /**<< EOB Parameters */
269  ){
270  REAL8 alJtoI = -atan2(Jy[2], -Jx[2]);
271  REAL8 betJtoI = acos(Jz[2]);
272  REAL8 gamJtoI = -atan2(Jz[1], -Jz[0]);
273 
274  REAL8 valuesdata[14] = {0.};
275  REAL8Vector values;
276  values.length=14;
277  values.data= valuesdata;
278  for(int t = 0; t<retLen; t++){
279  for (int i=1; i<=14; i++)
280  values.data[i-1]=dynamics->data[t+i*retLen];
281  h->data[t]=dynamics->data[t];
282  XLALEOBSpinPrecCalcHplusHcross(seobParams,&values,AlphaI2PVec->data[t],BetaI2PVec->data[t],GammaI2PVec->data[t], alJtoI,betJtoI,gamJtoI,Jx,Jy,Jz,Y,h->data+t+retLen,h->data+t+2*retLen);
283  }
284 }
285 #endif // _LALSIMIMRSPINPRECEOBWFGEN_C
static UNUSED int XLALSimIMRSpinEOBNonQCCorrection(COMPLEX16 *restrict nqc, REAL8Vector *restrict values, const REAL8 omega, EOBNonQCCoeffs *restrict coeffs)
This function calculates the non-quasicircular correction to apply to the waveform.
static int XLALSimIMREOBCalcSpinPrecFacWaveformCoefficients(FacWaveformCoeffs *const coeffs, const REAL8 m1, const REAL8 m2, const REAL8 eta, const REAL8 a, const REAL8 chiS, const REAL8 chiA, const UINT4 SpinAlignedEOBversion)
Waveform expressions are given by Taracchini et al.
static INT4 XLALSimIMRSpinEOBGetPrecSpinFactorizedWaveform_exact(COMPLEX16 *restrict hlm, REAL8Vector *restrict values, REAL8Vector *restrict cartvalues, const REAL8 v, const REAL8 Hreal, const INT4 l, const INT4 m, SpinEOBParams *restrict params)
This function calculates hlm mode factorized-resummed waveform for given dynamical variables.
static int XLALSimIMRCalculateSpinEOBHCoeffs(SpinEOBHCoeffs *coeffs, const REAL8 eta, const REAL8 a, const UINT4 SpinAlignedEOBversion)
This function is used to calculate some coefficients which will be used in the spinning EOB Hamiltoni...
static REAL8 XLALSimIMRSpinPrecEOBHamiltonian(const REAL8 eta, REAL8Vector *restrict x, REAL8Vector *restrict p, REAL8Vector *restrict s1Vec, REAL8Vector *restrict s2Vec, REAL8Vector *restrict sigmaKerr, REAL8Vector *restrict sigmaStar, int tortoise, SpinEOBHCoeffs *coeffs)
static REAL8 * cross_product(const REAL8 values1[], const REAL8 values2[], REAL8 result[])
static REAL8 inner_product(const REAL8 values1[], const REAL8 values2[])
Functions to compute the inner product and cross products between vectors.
static UNUSED void EulerAnglesP2J(REAL8 *aP2J, REAL8 *bP2J, REAL8 *gP2J, const REAL8 aI2P, const REAL8 bI2P, const REAL8 gI2P, const REAL8 LNhx, const REAL8 LNhy, const REAL8 LNhz, const REAL8 JframeEx[], const REAL8 JframeEy[], const REAL8 JframeEz[])
Given Euler angles to go from initial inertial frame to precessing frama and the LNhat vector,...
static void XLALEOBSpinPrecGenerateHTSModesFromEOMSoln(COMPLEX16 *hTSm2, COMPLEX16 *hTSm1, COMPLEX16 *hTS0, COMPLEX16 *hTSp1, COMPLEX16 *hTSp2, int retLen, REAL8Array *dynamics, SpinEOBParams *seobParams)
static void XLALEOBSpinPrecCalcHplusHcross(SpinEOBParams *seobParams, REAL8Vector *values, REAL8 aI2P, REAL8 bI2P, REAL8 gI2P, REAL8 alJtoI, REAL8 betJtoI, REAL8 gamJtoI, REAL8 JframeEx[3], REAL8 JframeEy[3], REAL8 JframeEz[3], COMPLEX16 Y[5], REAL8 *hplus, REAL8 *hcross)
static void XLALEOBSpinPrecGenerateHplusHcrossTSFromEOMSoln(REAL8Vector *h, int retLen, REAL8Vector *AlphaI2PVec, REAL8Vector *BetaI2PVec, REAL8Vector *GammaI2PVec, REAL8 Jx[3], REAL8 Jy[3], REAL8 Jz[3], COMPLEX16 Y[5], REAL8Array *dynamics, SpinEOBParams *seobParams)
static void XLALEOBSpinPrecCalcHModes(COMPLEX16 *hp2, COMPLEX16 *hp1, COMPLEX16 *h0, COMPLEX16 *hm1, COMPLEX16 *hm2, SpinEOBParams *seobParams, REAL8Vector *values)
static int XLALSpinPrecHcapRvecDerivative_exact(double UNUSED t, const REAL8 values[], REAL8 dvalues[], void *funcParams)
Function to calculate exact derivatives of the spin EOB Hamiltonian, to get , as decribed in Eqs.
int l
Definition: bh_qnmode.c:135
double i
Definition: bh_ringdown.c:118
const double a2
double complex COMPLEX16
double REAL8
static const INT4 m
COMPLEX16 XLALWignerDMatrix(int l, int mp, int m, double alpha, double beta, double gam)
FacWaveformCoeffs * hCoeffs
REAL8 * data
REAL8 * data
Parameters for the spinning EOB model.
SpinEOBHCoeffs * seobCoeffs
REAL8Vector * sigmaStar
EOBNonQCCoeffs * nqcCoeffs
EOBParams * eobParams
REAL8Vector * sigmaKerr