@@ -44,25 +44,26 @@ DEPENDENCY "@MCPLFLAGS@"
4444SHARE
4545%{
4646#include <mcpl.h>
47+ #include <sys/stat.h>
4748
4849typedef struct {
49- // Prefixed names to avoid the _particle accessor macros
50+ // Prefixed names to avoid the _particle accessor macros
5051 double _x, _y, _z;
5152 double _vx, _vy, _vz;
5253 double _sx, _sy, _sz;
5354 // insert [int, void*, int, double, double, double, unsigned long]
54- // here in order to have matching memory layout with
55+ // here in order to have matching memory layout with
5556 // _struct_particle, e.g., _class_particle
5657 double _t, _p;
5758} mcpl_input_once_particle_t;
5859
59- void mcpl_input_once_translator(const int use_polarisation, const mcpl_particle_t * input, mcpl_input_once_particle_t * output){
60+ void mcpl_input_once_translator(const int use_polarisation, double weight_scale, const mcpl_particle_t * input, mcpl_input_once_particle_t * output){
6061 // position in mm -> m
6162 output->_x = input->position[0] / 100;
6263 output->_y = input->position[1] / 100;
6364 output->_z = input->position[2] / 100;
6465 // ekin in MeV -> meV; then to velocity
65- double nrm = sqrt(input->ekin * 1e9 / VS2E);
66+ double nrm = sqrt(input->ekin * 1e9 / VS2E);
6667 output->_vx = input->direction[0] * nrm;
6768 output->_vy = input->direction[1] * nrm;
6869 output->_vz = input->direction[2] * nrm;
@@ -73,7 +74,13 @@ void mcpl_input_once_translator(const int use_polarisation, const mcpl_particle_
7374 // time in msec -> sec
7475 output->_t = input->time * 1e-3;
7576 // probability, unitless
76- output->_p = input->weight;
77+ output->_p = input->weight * weight_scale;
78+ }
79+
80+ int mcplinputonce_file_exist(char *fn)
81+ {
82+ struct stat buffer;
83+ return (stat (fn, &buffer) == 0);
7784}
7885%}
7986
@@ -89,24 +96,60 @@ uint64_t maximum_index;
8996uint64_t first_particle;
9097int times_replayed;
9198mcpl_input_once_particle_t * particles;
99+ double weight_scale;
100+ char * resolved_filename;
92101%}
93102
94103INITIALIZE
95104%{
105+ {
106+ if ( !filename || !filename[0] ) {
107+ fprintf(stderr,"ERROR(%s): Requires filename parameter.\n",
108+ NAME_CURRENT_COMP);
109+ exit(-1);
110+ }
111+ char * fn_mcpl = mcpl_name_helper( filename, 'M' );
112+ char * fn_mcplgz = mcpl_name_helper( filename, 'G' );
113+ if ( mcplinputonce_file_exist(fn_mcpl) ) {
114+ if ( mcplinputonce_file_exist(fn_mcplgz) ) {
115+ fprintf(stderr,"ERROR(%s): Can not resolve input file unambiguously"
116+ " since both %s and %s exist.\n",NAME_CURRENT_COMP,
117+ fn_mcpl, fn_mcplgz);
118+ exit(-1);
119+ }
120+ resolved_filename = fn_mcpl;
121+ free(fn_mcplgz);
122+ } else {
123+ resolved_filename = fn_mcplgz;
124+ free(fn_mcpl);
125+ }
126+ }
127+
96128 uint64_t particles_per_node;
97129 uint64_t last_particle;
98130 if(Emax<Emin){
99131 fprintf(stderr, "Error(%s): Nonsensical energy interval: E=[%g,%g]. Aborting.\n", NAME_CURRENT_COMP, Emin, Emax);
100132 exit(-1);
101133 }
102- inputfile = mcpl_open_file(filename);
134+ inputfile = mcpl_open_file(resolved_filename);
135+ double mcpl_ray_count = mcpl_hdr_stat_sum( inputfile, "initial_ray_count" );
136+ if ( mcpl_ray_count == -2.0 ) {
137+ //legacy format without ray count:
138+ weight_scale = 1.0;
139+ } else if ( !(mcpl_ray_count>0.0) ) {
140+ fprintf(stderr, "ERROR: Input MCPL file has invalid initial_ray_count"
141+ " (%g). Unable to determine weight scale.\n", mcpl_ray_count );
142+ exit(1);
143+ } else {
144+ weight_scale = 1.0 / mcpl_ray_count;
145+ }
103146 if (!(nparticles = mcpl_hdr_nparticles(inputfile))) {
104147 fprintf(stderr, "Error(%s): MCPL-file reports no present particles. Aborting.\n", NAME_CURRENT_COMP);
105148 exit(-1);
106149 } else {
107150 MPI_MASTER(
108- printf("Message(%s): MCPL file (%s) produced with %s.\n", NAME_CURRENT_COMP, filename , mcpl_hdr_srcname(inputfile));
109- printf("Message(%s): MCPL file (%s) contains %lu particles.\n", NAME_CURRENT_COMP, filename , (long unsigned)nparticles);
151+ printf("Message(%s): MCPL file (%s) produced with %s.\n", NAME_CURRENT_COMP, resolved_filename , mcpl_hdr_srcname(inputfile));
152+ printf("Message(%s): MCPL file (%s) contains %lu particles.\n", NAME_CURRENT_COMP, resolved_filename , (long unsigned)nparticles);
110153 );
111154 }
112155 first_particle = 0;
@@ -125,7 +168,7 @@ INITIALIZE
125168 used_neutrons=0;
126169#ifdef OPENACC
127170 preload=1;
128- printf("OpenACC, preload implicit:\n");
171+ printf("OpenACC, preload implicit:\n");
129172#endif
130173 // Move this node's pointer into the file to its first particle:
131174 // in preparation for pre-loading or first pass through TRACE
@@ -143,7 +186,7 @@ INITIALIZE
143186 particle=mcpl_read(inputfile);
144187 if (particle && particle->pdgcode==2112) {
145188 if (particle->ekin>Emin*1e-9 && particle->ekin<Emax*1e-9 ) {
146- mcpl_input_once_translator(polarisationuse, particle, particles + used_neutrons++);
189+ mcpl_input_once_translator(polarisationuse, weight_scale, particle, particles + used_neutrons++);
147190 }
148191 read_neutrons++;
149192 }
@@ -172,7 +215,7 @@ INITIALIZE
172215TRACE
173216%{
174217 mcpl_input_once_particle_t * ptr = NULL;
175-
218+
176219 if (current_index >= maximum_index){
177220 // go back to the start of this worker's particles, rather than accessing out-of-range data
178221 #pragma acc atomic write
@@ -200,7 +243,7 @@ TRACE
200243 if ( particle->ekin<Emin*1e-9 || particle->ekin>Emax*1e-9 ) {
201244 ABSORB;
202245 }
203- mcpl_input_once_translator(polarisationuse, particle, ptr);
246+ mcpl_input_once_translator(polarisationuse, weight_scale, particle, ptr);
204247 // And how many of the read neutrons actually get used
205248 if (!times_replayed) used_neutrons++;
206249 } else {
@@ -231,10 +274,10 @@ TRACE
231274 sz = ptr->_sz;
232275 t = ptr->_t;
233276 p = ptr->_p;
234-
277+
235278 // done with the mcpl_input_once_particle_t pointer -- free it if not pointing into the particles list
236279 if (!preload && ptr != NULL) free(ptr);
237-
280+
238281 if (always_smear || times_replayed){
239282 // fuzz the input
240283 if (pos_smear) {
@@ -310,13 +353,14 @@ if (mpi_node_rank == 0){
310353 }
311354 fprintf(stderr,
312355 "Warning (%s): You requested %llu neutrons from a file which contains %llu particles in general%s."
313- " T%shis component emitted %llu neutrons in total. Please examine the recorded intensities carefully.\n",
356+ " T%shis component emitted %llu neutrons in total. Please examine the recorded intensities carefully.\n",
314357 NAME_CURRENT_COMP, requested_neutrons, nparticles, bad_particle_message, mpi_nodes_message, emitted_neutrons
315358 );
316359 }
317360#if defined (USE_MPI)
318361}
319362#endif
363+ free(resolved_filename);
320364%}
321365
322366MCDISPLAY
@@ -325,10 +369,9 @@ MCDISPLAY
325369 /*M*/
326370 multiline(5,-0.085,-0.085,0.0, -0.085,0.085,0.0, -0.045,-0.085,0.0, -0.005,0.085,0.0, -0.005,-0.085,0.0);
327371 /*I*/
328- line(0.045,-0.085,0, 0.045, 0.085,0);
329- line(0.005, 0.085,0, 0.085, 0.085,0);
330- line(0.005,-0.085,0, 0.085,-0.085,0);
372+ line(0.045,-0.085,0, 0.045, 0.085,0);
373+ line(0.005, 0.085,0, 0.085, 0.085,0);
374+ line(0.005,-0.085,0, 0.085,-0.085,0);
331375%}
332376
333377END
334-
0 commit comments