laserfields
Fortran95 library to describe time-dependent laser pulses
Loading...
Searching...
No Matches
faddeeva.f90
Go to the documentation of this file.
1!!$ Copyright (c) 2012, Johannes Feist
2!!$ licensed under the MIT open source license, see LICENSE file
3!!$ This provides a Fortran interface to the open-source C/C++ codes
4!!$ for computing various error functions and the Dawson integral
5!!$ in the complex plane, based on algorithms for the computation
6!!$ of the Faddeeva function
7!!$ w(z) = exp(-z^2) * erfc(-i*z).
8!!$ The original code by Steven G. Johnson is from http://ab-initio.mit.edu/Faddeeva
9!!$
10!!$ We call it from Fortran with the C bindings introduced in Fortran 2003. This is
11!!$ possible since Steven provides a C interface since 27 November 2012 in addition
12!!$ to the original C++.
13!!$ As default arguments are not supported in calling C functions from Fortran,
14!!$ we provide explicit wrappers with the missing relerr argument.
15!!$
16!!$ Johannes Feist, Universidad Autonoma de Madrid
17
19 use, intrinsic :: iso_c_binding
20 implicit none
21 private
23
24 ! compute w(z) = exp(-z^2) erfc(-iz) [ Faddeeva / scaled complex error func ]
25 interface faddeeva_w
26 module procedure zfaddeeva_w_norelerr
27 function zfaddeeva_w(z,relerr) bind(c,name='Faddeeva_w')
28 use iso_c_binding
29 implicit none
30 complex(c_double) :: zfaddeeva_w
31 complex(c_double), value, intent(in) :: z
32 real(c_double), value, intent(in) :: relerr
33 end function zfaddeeva_w
34 end interface faddeeva_w
35
36 interface
37 ! special-case code for Im[w(x)] of real x
38 function faddeeva_w_im(x) bind(c,name='Faddeeva_w_im')
39 use, intrinsic :: iso_c_binding
40 real(c_double) :: faddeeva_w_im
41 real(c_double), value, intent(in) :: x
42 end function faddeeva_w_im
43 end interface
44
45 ! Various functions that we can compute with the help of w(z)
46
47 ! compute erfcx(z) = exp(z^2) erfc(z)
48 interface erfcx
49 module procedure zerfcx_norelerr
50 function zerfcx(z,relerr) bind(c,name='Faddeeva_erfcx')
51 use, intrinsic :: iso_c_binding
52 implicit none
53 complex(c_double) :: zerfcx
54 complex(c_double), value, intent(in) :: z
55 real(c_double), value, intent(in) :: relerr
56 end function zerfcx
57 function derfcx(x) bind(c,name='Faddeeva_erfcx_re')
58 use, intrinsic :: iso_c_binding
59 implicit none
60 real(c_double) :: derfcx
61 real(c_double), value, intent(in) :: x
62 end function derfcx
63 end interface erfcx
64
65 ! compute erf(z), the error function of complex arguments
66 interface erf
67 module procedure zerf_norelerr
68 function zerf(z,relerr) bind(c,name='Faddeeva_erf')
69 use, intrinsic :: iso_c_binding
70 implicit none
71 complex(c_double) :: zerf
72 complex(c_double), value, intent(in) :: z
73 real(c_double), value, intent(in) :: relerr
74 end function zerf
75 function derf(x) bind(c,name='Faddeeva_erf_re')
76 use, intrinsic :: iso_c_binding
77 implicit none
78 real(c_double) :: derf
79 real(c_double), value, intent(in) :: x
80 end function derf
81 end interface erf
82
83 ! compute erfi(z) = -i erf(iz), the imaginary error function
84 interface erfi
85 module procedure zerfi_norelerr
86 function zerfi(z,relerr) bind(c,name='Faddeeva_erfi')
87 use, intrinsic :: iso_c_binding
88 implicit none
89 complex(c_double) :: zerfi
90 complex(c_double), value, intent(in) :: z
91 real(c_double), value, intent(in) :: relerr
92 end function zerfi
93 function derfi(x) bind(c,name='Faddeeva_erfi_re')
94 use, intrinsic :: iso_c_binding
95 implicit none
96 real(c_double) :: derfi
97 real(c_double), value, intent(in) :: x
98 end function derfi
99 end interface erfi
100
101 ! compute erfc(z) = 1 - erf(z), the complementary error function
102 interface erfc
103 module procedure zerfc_norelerr
104 function zerfc(z,relerr) bind(c,name='Faddeeva_erfc')
105 use, intrinsic :: iso_c_binding
106 implicit none
107 complex(c_double) :: zerfc
108 complex(c_double), value, intent(in) :: z
109 real(c_double), value, intent(in) :: relerr
110 end function zerfc
111 function derfc(x) bind(c,name='Faddeeva_erfc_re')
112 use, intrinsic :: iso_c_binding
113 implicit none
114 real(c_double) :: derfc
115 real(c_double), value, intent(in) :: x
116 end function derfc
117 end interface erfc
118
119 ! compute Dawson(z) = sqrt(pi)/2 * exp(-z^2) * erfi(z)
120 interface dawson
121 module procedure zdawson_norelerr
122 function zdawson(z,relerr) bind(c,name='Faddeeva_Dawson')
123 use, intrinsic :: iso_c_binding
124 implicit none
125 complex(c_double) :: zdawson
126 complex(c_double), value, intent(in) :: z
127 real(c_double), value, intent(in) :: relerr
128 end function zdawson
129 function ddawson(x) bind(c,name='Faddeeva_Dawson_re')
130 use, intrinsic :: iso_c_binding
131 implicit none
132 real(c_double) :: ddawson
133 real(c_double), value, intent(in) :: x
134 end function ddawson
135 end interface dawson
136
137contains
138 function zfaddeeva_w_norelerr(z)
139 complex(c_double) :: zfaddeeva_w_norelerr
140 complex(c_double), intent(in) :: z
141 zfaddeeva_w_norelerr = zfaddeeva_w(z,0.d0)
142 end function zfaddeeva_w_norelerr
143
144 function zerfcx_norelerr(z)
145 complex(c_double) :: zerfcx_norelerr
146 complex(c_double), intent(in) :: z
147 zerfcx_norelerr = zerfcx(z,0.d0)
148 end function zerfcx_norelerr
149
150 function zerf_norelerr(z)
151 complex(c_double) :: zerf_norelerr
152 complex(c_double), intent(in) :: z
153 zerf_norelerr = zerf(z,0.d0)
154 end function zerf_norelerr
155
156 function zerfi_norelerr(z)
157 complex(c_double) :: zerfi_norelerr
158 complex(c_double), intent(in) :: z
159 zerfi_norelerr = zerfi(z,0.d0)
160 end function zerfi_norelerr
161
162 function zerfc_norelerr(z)
163 complex(c_double) :: zerfc_norelerr
164 complex(c_double), intent(in) :: z
165 zerfc_norelerr = zerfc(z,0.d0)
166 end function zerfc_norelerr
167
168 function zdawson_norelerr(z)
169 complex(c_double) :: zdawson_norelerr
170 complex(c_double), intent(in) :: z
171 zdawson_norelerr = zdawson(z,0.d0)
172 end function zdawson_norelerr
173
174end module faddeeva