7#include "../../offload.h"
38 GPU_DATA_IS_MAPPED(h[0:p->
n_mrk])
39 GPU_PARALLEL_LOOP_ALL_LEVELS
40 for(
int i = 0; i < p->
n_mrk; i++) {
54 real posrpz[3] = {p->
r[i], p->
phi[i], p->
z[i]};
55 real posxyz0[3],posxyz[3];
60 posxyz[0] = posxyz0[0] + pxyz[0] * h[i] / (2.0 * gamma * mass);
61 posxyz[1] = posxyz0[1] + pxyz[1] * h[i] / (2.0 * gamma * mass);
62 posxyz[2] = posxyz0[2] + pxyz[2] * h[i] / (2.0 * gamma * mass);
70 t0 + h[i]/2.0, Bdata);
74 t0 + h[i]/2.0, Edata, Bdata);
90 pminus[0] = pxyz[0] / (mass *
CONST_C) + sigma * Exyz[0];
91 pminus[1] = pxyz[1] / (mass *
CONST_C) + sigma * Exyz[1];
92 pminus[2] = pxyz[2] / (mass *
CONST_C) + sigma * Exyz[2];
99 real Bhat[9] = { 0, Bxyz[2], -Bxyz[1],
100 -Bxyz[2], 0, Bxyz[0],
101 Bxyz[1], -Bxyz[0], 0};
105 real B2 = Bxyz[0]*Bxyz[0] + Bxyz[1]*Bxyz[1] + Bxyz[2]*Bxyz[2];
108 for(
int j=0; j<9; j++) {
109 A[j] = (Bhat[j] + d*Bhat2[j]) * (2.0*d/(1.0+d2*B2));
117 pfinal[0] = pminus[0] + pplus[0] + sigma*Exyz[0];
118 pfinal[1] = pminus[1] + pplus[1] + sigma*Exyz[1];
119 pfinal[2] = pminus[2] + pplus[2] + sigma*Exyz[2];
121 pxyz[0] = pfinal[0] * mass *
CONST_C;
122 pxyz[1] = pfinal[1] * mass *
CONST_C;
123 pxyz[2] = pfinal[2] * mass *
CONST_C;
127 fposxyz[0] = posxyz[0] + h[i] * pxyz[0] / (2.0 * gamma * mass);
128 fposxyz[1] = posxyz[1] + h[i] * pxyz[1] / (2.0 * gamma * mass);
129 fposxyz[2] = posxyz[2] + h[i] * pxyz[2] / (2.0 * gamma * mass);
133 p->
r[i] = sqrt(fposxyz[0]*fposxyz[0]+fposxyz[1]*fposxyz[1]);
137 posxyz0[0] * fposxyz[1] - posxyz0[1] * fposxyz[0],
138 posxyz0[0] * fposxyz[0] + posxyz0[1] * fposxyz[1] );
139 p->
z[i] = fposxyz[2];
143 p->
p_r[i] = pxyz[0] * cosp + pxyz[1] * sinp;
144 p->
p_phi[i] = -pxyz[0] * sinp + pxyz[1] * cosp;
165 p->
B_r[i] = BdBrpz[0];
170 p->
B_phi[i] = BdBrpz[4];
175 p->
B_z[i] = BdBrpz[8];
178 p->
B_z_dz[i] = BdBrpz[11];
185 p->
theta[i] += atan2( (R0-axisrz[0]) * (p->
z[i]-axisrz[1])
186 - (z0-axisrz[1]) * (p->
r[i]-axisrz[0]),
187 (R0-axisrz[0]) * (p->
r[i]-axisrz[0])
188 + (z0-axisrz[1]) * (p->
z[i]-axisrz[1]) );
195 real t_ald = phys_ald_force_chartime(
196 p->
charge[i], p->
mass[i], Bnorm, gamma) * aldforce;
197 real pparbhatperB = (
199 + p->
p_z[i]*p->
B_z[i] ) / ( Bnorm * Bnorm * pnorm );
201 p->
p_r[i] - pparbhatperB * p->
B_r[i],
203 p->
p_z[i] - pparbhatperB * p->
B_z[i] };
204 real C = ( pperpvec[0]*pperpvec[0] + pperpvec[1]*pperpvec[1]
205 + pperpvec[2]*pperpvec[2] )
207 p->
p_r[i] -= t_ald * ( pperpvec[0] + C * p->
p_r[i] );
208 p->
p_phi[i] -= t_ald * ( pperpvec[1] + C * p->
p_phi[i] );
209 p->
p_z[i] -= t_ald * ( pperpvec[2] + C * p->
p_z[i] );
240 #pragma omp simd aligned(h : 64)
241 for(i = 0; i <
NSIMD; i++) {
255 real posrpz[3] = {p->
r[i], p->
phi[i], p->
z[i]};
256 real posxyz0[3],posxyz[3];
261 posxyz[0] = posxyz0[0] + pxyz[0] * h[i] / (2 * gamma * mass);
262 posxyz[1] = posxyz0[1] + pxyz[1] * h[i] / (2 * gamma * mass);
263 posxyz[2] = posxyz0[2] + pxyz[2] * h[i] / (2 * gamma * mass);
275 t0 + h[i]/2, Edata, Bdata);
282 pert, posrpz[0], posrpz[1], posrpz[2], t0 + h[i]/2,
305 pminus[0] = pxyz[0] / (mass *
CONST_C) + sigma * Exyz[0];
306 pminus[1] = pxyz[1] / (mass *
CONST_C) + sigma * Exyz[1];
307 pminus[2] = pxyz[2] / (mass *
CONST_C) + sigma * Exyz[2];
311 sqrt( 1 +
math_dot(pminus,pminus) );
314 real Bhat[9] = { 0, Bxyz[2], -Bxyz[1],
315 -Bxyz[2], 0, Bxyz[0],
316 Bxyz[1], -Bxyz[0], 0};
320 real B2 = Bxyz[0]*Bxyz[0] + Bxyz[1]*Bxyz[1] + Bxyz[2]*Bxyz[2];
323 for(
int j=0; j<9; j++) {
324 A[j] = (Bhat[j] + d*Bhat2[j]) * (2.0*d/(1+d2*B2));
332 pfinal[0] = pminus[0] + pplus[0] + sigma*Exyz[0];
333 pfinal[1] = pminus[1] + pplus[1] + sigma*Exyz[1];
334 pfinal[2] = pminus[2] + pplus[2] + sigma*Exyz[2];
336 pxyz[0] = pfinal[0] * mass *
CONST_C;
337 pxyz[1] = pfinal[1] * mass *
CONST_C;
338 pxyz[2] = pfinal[2] * mass *
CONST_C;
342 fposxyz[0] = posxyz[0] + h[i] * pxyz[0] / (2 * gamma * mass);
343 fposxyz[1] = posxyz[1] + h[i] * pxyz[1] / (2 * gamma * mass);
344 fposxyz[2] = posxyz[2] + h[i] * pxyz[2] / (2 * gamma * mass);
348 p->
r[i] = sqrt(fposxyz[0]*fposxyz[0]+fposxyz[1]*fposxyz[1]);
352 posxyz0[0] * fposxyz[1] - posxyz0[1] * fposxyz[0],
353 posxyz0[0] * fposxyz[0] + posxyz0[1] * fposxyz[1] );
354 p->
z[i] = fposxyz[2];
358 p->
p_r[i] = pxyz[0] * cosp + pxyz[1] * sinp;
359 p->
p_phi[i] = -pxyz[0] * sinp + pxyz[1] * cosp;
380 p->
B_r[i] = BdBrpz[0];
385 p->
B_phi[i] = BdBrpz[4];
390 p->
B_z[i] = BdBrpz[8];
393 p->
B_z_dz[i] = BdBrpz[11];
400 p->
theta[i] += atan2( (R0-axisrz[0]) * (p->
z[i]-axisrz[1])
401 - (z0-axisrz[1]) * (p->
r[i]-axisrz[0]),
402 (R0-axisrz[0]) * (p->
r[i]-axisrz[0])
403 + (z0-axisrz[1]) * (p->
z[i]-axisrz[1]) );
a5err B_field_eval_rho(real rho[2], real psi, B_field_data *Bdata)
Evaluate normalized poloidal flux rho and its psi derivative.
a5err B_field_eval_psi(real *psi, real r, real phi, real z, real t, B_field_data *Bdata)
Evaluate poloidal flux psi.
a5err B_field_eval_B_dB(real B_dB[15], real r, real phi, real z, real t, B_field_data *Bdata)
Evaluate magnetic field and its derivatives.
a5err B_field_get_axis_rz(real rz[2], B_field_data *Bdata, real phi)
Return magnetic axis Rz-coordinates.
a5err B_field_eval_B(real B[3], real r, real phi, real z, real t, B_field_data *Bdata)
Evaluate magnetic field.
Header file for B_field.c.
a5err E_field_eval_E(real E[3], real r, real phi, real z, real t, E_field_data *Edata, B_field_data *Bdata)
Evaluate electric field.
Header file for E_field.c.
Main header file for ASCOT5.
#define NSIMD
Number of particles simulated simultaneously in a particle group operations.
Header file for boozer.c.
Header file containing physical and mathematical constants.
#define CONST_C
Speed of light [m/s].
#define CONST_C2
Speed of light squared [m^2/s^2].
unsigned long int a5err
Simulation error flag.
void math_matmul(real *matA, real *matB, int d1, int d2, int d3, real *matC)
Matrix multiplication.
#define math_dot(a, b)
Calculate dot product a[3] dot b[3].
#define math_xyz2rpz(xyz, rpz)
Convert cartesian coordinates xyz to cylindrical coordinates rpz.
#define math_vec_rpz2xyz(vrpz, vxyz, phi)
Transform vector from cylindrical to cartesian basis: vrpz -> vxyz, phi is the toroidal angle in radi...
#define math_rpz2xyz(rpz, xyz)
Convert cylindrical coordinates rpz to cartesian coordinates xyz.
#define math_normc(a1, a2, a3)
Calculate norm of 3D vector from its components a1, a2, a3.
#define math_norm(a)
Calculate norm of 3D vector a.
a5err mhd_perturbations(real pert_field[7], real r, real phi, real z, real t, int pertonly, int includemode, boozer_data *boozerdata, mhd_data *mhddata, B_field_data *Bdata)
Evaluate perturbed fields Btilde, Etilde and potential Phi explicitly.
#define MHD_INCLUDE_ALL
includemode parameter to include all modes (default)
Header file for particle.c.
Methods to evaluate elementary physical quantities.
#define physlib_gamma_pnorm(m, p)
Evaluate Lorentz factor from momentum norm.
void step_fo_vpa(particle_simd_fo *p, real *h, B_field_data *Bdata, E_field_data *Edata, int aldforce)
Integrate a full orbit step for a struct of particles with VPA.
void step_fo_vpa_mhd(particle_simd_fo *p, real *h, B_field_data *Bdata, E_field_data *Edata, boozer_data *boozer, mhd_data *mhd, int aldforce)
Integrate a full orbit step with VPA and MHd modes present.
Header file for step_fo_vpa.c.
Magnetic field simulation data.
Electric field simulation data.
Data for mapping between the cylindrical and Boozer coordinates.
Struct representing NSIMD particle markers.