File: Pol_monitor.comp

package info (click to toggle)
mccode 3.5.19%2Bds5-2
  • links: PTS, VCS
  • area: main
  • in suites: sid, trixie
  • size: 1,113,256 kB
  • sloc: ansic: 40,697; python: 25,137; yacc: 8,438; sh: 5,405; javascript: 4,596; lex: 1,632; cpp: 742; perl: 296; lisp: 273; makefile: 226; fortran: 132
file content (147 lines) | stat: -rw-r--r-- 3,391 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
/**************************************************************************
*
* McStas, neutron ray-tracing package
*         Copyright 1997-2006, All rights reserved
*         Risoe National Laboratory, Roskilde, Denmark
*         Institut Laue Langevin, Grenoble, France
*
* Component: Pol_monitor
*
* %I
* Written by: Peter Christiansen
* Modified by  Erik B Knudsen
* Date: July 2006
* Origin: Risoe
*
* Polarisation sensitive monitor.
*
* %D A square single monitor that measures the projection of the
* polarisation along a given normalized m-vector (mx, my, mz).
* The measured quantity is: sx*mx+sy*my+mz*sz
*
* Example: Pol_monitor(xwidth=0.1, yheight=0.1, nchan=11, mx=0, my=1, mz=0)
*
* %P
* INPUT PARAMETERS:
*
* xwidth: [m]           Width of detector
* yheight: [m]          Height of detector
* mx: [1]               X-component of monitor vector (can be negative)
* my: [1]               Y-component of monitor vector (can be negative)
* mz: [1]               Z-component of monitor vector (can be negative)
* restore_neutron: [1]  If set, the monitor does not influence the neutron state
* nowritefile: [1]      If set, monitor will skip writing to disk
*
* CALCULATED PARAMETERS:
*
* Pol_N: []             Array of neutron counts
* Pol_p: []             Array of neutron weight counts
* Pol_p2: []            Array of second moments
*
* %E
*************************************************************************/
DEFINE COMPONENT Pol_monitor



SETTING PARAMETERS (xwidth=0.1, yheight=0.1, int restore_neutron=0, mx=0, my=0, mz=0, int nowritefile=0)


/* Neutron parameters: (x,y,z,vx,vy,vz,t,sx,sy,sz,p) */

DECLARE
%{
  double Pol_N;
  double Pol_p;
  double Pol_p2;
  double Psum;
  char titlestring[128];
%}

INITIALIZE
%{
  // Check that input parameteters makes sense
  if (mx==0 && my==0 && mz==0) {
    fprintf(stderr, "Pol_monitor: %s: NULL vector defined!\n"
      "ERROR      (mx, my, mz). Exiting",
      NAME_CURRENT_COMP);
    exit(1);
  }

  if ((xwidth<=0) || (yheight <= 0)) {
    fprintf(stderr, "Pol_monitor: %s: Null detection area !\n"
      "ERROR      (xwidth,yheight). Exiting",
      NAME_CURRENT_COMP);
    exit(1);
  }
  sprintf(titlestring, "Polarisation monitor m=(%g %g %g) %s", mx, my, mz, NAME_CURRENT_COMP);

  // Initialize variables

  NORM(mx, my, mz);
  Psum=0;
  Pol_N = 0;
  Pol_p = 0;
  Pol_p2 = 0;
%}

TRACE
%{
  double pol_proj;

  PROP_Z0;
  if (inside_rectangle(x, y, xwidth, yheight)){

    pol_proj = scalar_prod(mx, my, mz, sx, sy, sz);

    if(fabs(pol_proj)>1) {
        if (fabs(pol_proj)<1+FLT_EPSILON){
            pol_proj=1;
        }else{
            ABSORB;
        }
    }
    double p2 = p*p;
    double pp = pol_proj*p;
    double p2p = pol_proj*pol_proj*p;
    #pragma acc atomic
    Pol_N = Pol_N+1;

    #pragma acc atomic
    Psum = Psum+p;

    #pragma acc atomic
    Pol_p = Pol_p+pp;

    #pragma acc atomic
    Pol_p2 = Pol_p2+p2p;
    
    SCATTER;
  }
  if (restore_neutron) {
    RESTORE_NEUTRON(INDEX_CURRENT_COMP, x, y, z, vx, vy, vz, t, sx, sy, sz, p);
  }
%}

SAVE
%{
    if (!nowritefile) {
  if (Psum && Pol_N){
      Pol_p  /= Psum;
#ifdef USE_MPI
      Pol_p /= mpi_node_count;
#endif
      Pol_p2 /= Psum;
      Pol_p2 -= Pol_p*Pol_p;
      Pol_p2 /= Pol_N;
  }
  DETECTOR_OUT_0D(titlestring, Pol_N, Pol_p, Pol_p2);
    }
%}

MCDISPLAY
%{
  rectangle("xy", 0, 0, 0, xwidth, yheight);
%}

END