18#include "hdf5io/hdf5_dist.h"
34 int iphi,
int iz,
real* ppara,
real* pperp);
59 real* prod1_offload_array,
real* prod2_offload_array) {
63 strcpy(sim->
qid, qid);
65 int mpi_rank = 0, mpi_root = 0;
68 "Tag %s\nBranch %s\n\n", GIT_VERSION, GIT_BRANCH);
71 dist_5D_init(&prod1, prod1_offload_data, prod1_offload_array);
72 dist_5D_init(&prod2, prod2_offload_data, prod2_offload_array);
82 "\nInitializing output failed.\n"
83 "See stderr for details.\n");
88 real m1, q1, m2, q2, mprod1, qprod1, mprod2, qprod2, Q;
90 reaction, &m1, &q1, &m2, &q2, &mprod1, &qprod1, &mprod2, &qprod2, &Q);
92 int n_r=0, n_phi=0, n_z=0;
93 if(react1->
type == 1) {
98 else if(react1->
type == 2) {
104 #pragma omp parallel for
105 for(
int iR = 0; iR < n_r; iR++) {
116 for(
int iphi = 0; iphi < n_phi; iphi++) {
117 for(
int iz = 0; iz < n_z; iz++) {
120 if(density1 > 0 && density2 > 0) {
122 react1, react2, m1, m2, n, iR, iphi, iz,
123 ppara1, pperp1, ppara2, pperp2);
124 for(
int i = 0; i < n; i++) {
127 i, m1, m2, mprod1, mprod2, Q,
128 ppara1, pperp1, ppara2, pperp2, &vcom2,
129 pparaprod1, pperpprod1, pparaprod2, pperpprod2);
130 real E = 0.5 * ( m1 * m2 ) / ( m1 + m2 ) * vcom2;
132 real weight = density1 * density2 * sqrt(vcom2)
141 if( 0 <= ippara && ippara < prod1.
n_ppara &&
142 0 <= ipperp && ipperp < prod1.
n_pperp) {
144 iR, iphi, iz, ippara, ipperp, 0, 0,
156 if( 0 <= ippara && ippara < prod2.
n_ppara &&
157 0 <= ipperp && ipperp < prod2.
n_pperp) {
159 iR, iphi, iz, ippara, ipperp, 0, 0,
185 int c1 = (int)rint(q1 /
CONST_E);
186 int c2 = (int)rint(q2 /
CONST_E);
187 int cprod1 = (int)rint(qprod1 /
CONST_E);
188 int cprod2 = (int)rint(qprod2 /
CONST_E);
196 sprintf(path,
"/results/afsi_%s/reaction", sim->
qid);
197 hid_t reactiondata = H5Gcreate2(f, path, H5P_DEFAULT, H5P_DEFAULT,
199 if(reactiondata < 0) {
200 print_err(
"Failed to write reaction data.\n");
205 if(H5LTmake_dataset_double(reactiondata,
"m1", 1, &size, &m1)) {
206 print_err(
"Failed to write reaction data.\n");
209 if(H5LTmake_dataset_double(reactiondata,
"m2", 1, &size, &m2)) {
210 print_err(
"Failed to write reaction data.\n");
213 if(H5LTmake_dataset_double(reactiondata,
"mprod1", 1, &size, &mprod1)) {
214 print_err(
"Failed to write reaction data.\n");
217 if(H5LTmake_dataset_double(reactiondata,
"mprod2", 1, &size, &mprod2)) {
218 print_err(
"Failed to write reaction data.\n");
221 if(H5LTmake_dataset_double(reactiondata,
"q", 1, &size, &q)) {
222 print_err(
"Failed to write reaction data.\n");
225 if(H5LTmake_dataset_int(reactiondata,
"q1", 1, &size, &c1)) {
226 print_err(
"Failed to write reaction data.\n");
229 if(H5LTmake_dataset_int(reactiondata,
"q2", 1, &size, &c2)) {
230 print_err(
"Failed to write reaction data.\n");
233 if(H5LTmake_dataset_int(reactiondata,
"qprod1", 1, &size, &cprod1)) {
234 print_err(
"Failed to write reaction data.\n");
237 if(H5LTmake_dataset_int(reactiondata,
"qprod2", 1, &size, &cprod2)) {
238 print_err(
"Failed to write reaction data.\n");
241 if(H5Gclose(reactiondata)) {
242 print_err(
"Failed to write reaction data.\n");
246 sprintf(path,
"/results/afsi_%s/prod1dist5d", sim->
qid);
248 print_err(
"Warning: 5D distribution could not be written.\n");
250 sprintf(path,
"/results/afsi_%s/prod2dist5d", sim->
qid);
252 print_err(
"Warning: 5D distribution could not be written.\n");
255 print_err(
"Failed to close the file.\n");
282 if(react1->
type == 1) {
285 else if(react1->
type == 2) {
287 react1->
dist_thermal, m1, n, iR, iphi, iz, ppara1, pperp1);
290 if(react2->
type == 1) {
293 else if(react2->
type == 2) {
295 react2->
dist_thermal, m2, n, iR, iphi, iz, ppara2, pperp2);
326 real v1x = cos(rn1) * pperp1[i] / m1;
327 real v1y = sin(rn1) * pperp1[i] / m1;
328 real v1z = ppara1[i] / m1;
330 real v2x = cos(rn2) * pperp2[i] / m2;
331 real v2y = sin(rn2) * pperp2[i] / m2;
332 real v2z = ppara2[i] / m2;
334 *vcom2 = (v1x - v2x) * (v1x - v2x)
335 + (v1y - v2y) * (v1y - v2y)
336 + (v1z - v2z) * (v1z - v2z);
340 v_cm[0] = ( m1 * v1x + m2 * v2x ) / ( m1 + m2 );
341 v_cm[1] = ( m1 * v1y + m2 * v2y ) / ( m1 + m2 );
342 v_cm[2] = ( m1 * v1z + m2 * v2z ) / ( m1 + m2 );
346 + 0.5 * m1 * ( (v1x - v_cm[0])*(v1x - v_cm[0])
347 + (v1y - v_cm[1])*(v1y - v_cm[1])
348 + (v1z - v_cm[2])*(v1z - v_cm[2]) )
349 + 0.5 * m2 * ( (v2x - v_cm[0])*(v2x - v_cm[0])
350 + (v2y - v_cm[1])*(v2y - v_cm[1])
351 + (v2z - v_cm[2])*(v2z - v_cm[2]) );
357 real theta = acos( 2 * ( rn2 - 0.5 ) );
358 real vnorm = sqrt( 2.0 * ekin / ( mprod2 * ( 1.0 + mprod2 / mprod1 ) ) );
361 v2_cm[0] = vnorm * sin(theta) * cos(phi);
362 v2_cm[1] = vnorm * sin(theta) * sin(phi);
363 v2_cm[2] = vnorm * cos(theta);
366 real vprod1[3], vprod2[3];
367 vprod1[0] = -(mprod2/mprod1) * v2_cm[0] + v_cm[0];
368 vprod1[1] = -(mprod2/mprod1) * v2_cm[1] + v_cm[1];
369 vprod1[2] = -(mprod2/mprod1) * v2_cm[2] + v_cm[2];
370 vprod2[0] = v2_cm[0] + v_cm[0];
371 vprod2[1] = v2_cm[1] + v_cm[1];
372 vprod2[2] = v2_cm[2] + v_cm[2];
375 pparaprod1[i] = vprod1[2] * mprod1;
376 pperpprod1[i] = sqrt( vprod1[0]*vprod1[0] + vprod1[1]*vprod1[1] ) * mprod1;
377 pparaprod2[i] = vprod2[2] * mprod2;
378 pperpprod2[i] = sqrt( vprod2[0]*vprod2[0] + vprod2[1]*vprod2[1] ) * mprod2;
396 for(
int ippara = 0; ippara < dist->
n_ppara; ippara++) {
397 for(
int ipperp = 0; ipperp < dist->
n_pperp; ipperp++) {
398 if(ippara == 0 && ipperp == 0) {
404 cumdist[ippara*dist->
n_pperp+ipperp] =
405 cumdist[ippara*dist->
n_pperp+ipperp-1]
407 iR, iphi, iz, ippara, ipperp, 0, 0, dist->
step_6,
413 for(
int ippara = 0; ippara < dist->
n_ppara; ippara++) {
414 for(
int ipperp = 0; ipperp < dist->
n_pperp; ipperp++) {
415 cumdist[ippara*dist->
n_pperp+ipperp] /=
420 for(
int i = 0; i < n; i++) {
452 int iphi,
int iz,
real* ppara,
real* pperp) {
453 int ind = iR * (data->
n_phi * data->
n_z) + iphi * data->
n_z + iz;
456 for(
int i = 0; i < n; i++) {
457 real r1, r2, r3, r4, E;
462 E = -temp * ( log(r1) + log(r2) * r3 * r3 );
465 pperp[i] = sqrt( ( 1 - r4*r4 ) * 2 * E * mass);
466 ppara[i] = r4 * sqrt(2 * E * mass);
480 if(dist->
type == 1) {
487 iR, iphi, iz, ippara, ipperp, 0, 0,
496 else if(dist->
type == 2) {
517 if(dist->
type == 1) {
523 else if(dist->
type == 2) {
539 printf(
"%d %le %le\n", dist1->
n_r, dist1->
min_r, dist1->
max_r);
541 printf(
"%d %le %le\n", dist1->
n_z, dist1->
min_z, dist1->
max_z);
545 printf(
"%d %le %le\n", dist1->
n_q, dist1->
min_q, dist1->
max_q);
551 for(
int i = 0; i < ncell; i++) {
555 printf(
"%le\n", sum);
574 real temperature = 1e3;
586 for(
int i = 0; i < n; i++) {
587 printf(
"%le %le\n", ppara[i], pperp[i]);
void afsi_sample_thermal(afsi_thermal_data *data, real mass, int n, int iR, int iphi, int iz, real *ppara, real *pperp)
Sample ppara and pperp from a thermal (Maxwellian) population.
void afsi_test_thermal()
Test thermal source.
real afsi_get_volume(afsi_data *dist, int iR)
Get physical volume of a distribution cell.
void afsi_sample_5D(dist_5D_data *dist, int n, int iR, int iphi, int iz, real *ppara, real *pperp)
Sample ppara and pperp from a 5D distribution.
void afsi_compute_product_momenta(int i, real m1, real m2, real mprod1, real mprod2, real Q, real *ppara1, real *pperp1, real *ppara2, real *pperp2, real *vcom2, real *pparaprod1, real *pperpprod1, real *pparaprod2, real *pperpprod2)
Compute momenta of reaction products.
real afsi_get_density(afsi_data *dist, int iR, int iphi, int iz)
Get particle density.
void afsi_sample_reactant_momenta(afsi_data *react1, afsi_data *react2, real m1, real m2, int n, int iR, int iphi, int iz, real *ppara1, real *pperp1, real *ppara2, real *pperp2)
Sample velocities from reactant distributions.
void afsi_run(sim_offload_data *sim, Reaction reaction, int n, afsi_data *react1, afsi_data *react2, real mult, dist_5D_offload_data *prod1_offload_data, dist_5D_offload_data *prod2_offload_data, real *prod1_offload_array, real *prod2_offload_array)
Calculate fusion source from two arbitrary ion distributions.
void afsi_test_dist(dist_5D_data *dist1)
Test distribution.
Main header file for ASCOT5.
void boschhale_reaction(Reaction reaction, real *m1, real *q1, real *m2, real *q2, real *mprod1, real *qprod1, real *mprod2, real *qprod2, real *Q)
Get masses and charges of particles participating in the reaction and the released energy.
real boschhale_sigma(Reaction reaction, real E)
Estimate cross-section for a given fusion reaction.
Header file for boschdale.c.
Reaction
Available reactions.
Header file containing physical and mathematical constants.
#define CONST_U
Atomic mass unit in kilograms [kg]
#define CONST_E
Elementary charge [C]
void dist_5D_init(dist_5D_data *dist_data, dist_5D_offload_data *offload_data, real *offload_array)
Initializes distribution from offload data.
size_t dist_5D_index(int i_r, int i_phi, int i_z, int i_ppara, int i_pperp, int i_time, int i_q, size_t step_6, size_t step_5, size_t step_4, size_t step_3, size_t step_2, size_t step_1)
Function for calculating the index in the histogram array.
Header file for dist_5D.c.
int hdf5_dist_write_5D(hid_t f, char *path, dist_5D_offload_data *dist, real *hist)
Write 5D distribution to an existing result group.
herr_t hdf5_close(hid_t file_id)
Close access to given hdf5 file identifier. A negative value is returned on failure.
hid_t hdf5_open(const char *filename)
Open a hdf5 file for reading and writing. A negative value is returned on failure.
Header file for hdf5_helpers.h.
int hdf5_interface_init_results(sim_offload_data *sim, char *qid, char *run)
Initialize run group.
void hdf5_generate_qid(char *qid)
Generate an identification number for a run.
Header file for hdf5_interface.c.
Macros for printing console output.
#define print_out0(v, rank, root,...)
Print to standard output only for root process.
#define print_err(...)
Print to standard error.
Header file for random.c.
#define random_uniform(data)
#define random_init(data, seed)
void simulate_init_offload(sim_offload_data *sim)
Initializes simulation settings.
void sim_init(sim_data *sim, sim_offload_data *offload_data)
Initialize simulation data struct on target.
Header file for simulate.c.
Wrapper around input data structures.
afsi_thermal_data * dist_thermal
Structure for passing in 2D thermal temperature and density.
Histogram parameters on target.
Histogram parameters that will be offloaded to target.
Simulation offload struct.