Octopus
td_calc.F90
Go to the documentation of this file.
1!! Copyright (C) 2002-2006 M. Marques, A. Castro, A. Rubio, G. Bertsch
2!!
3!! This program is free software; you can redistribute it and/or modify
4!! it under the terms of the GNU General Public License as published by
5!! the Free Software Foundation; either version 2, or (at your option)
6!! any later version.
7!!
8!! This program is distributed in the hope that it will be useful,
9!! but WITHOUT ANY WARRANTY; without even the implied warranty of
10!! MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11!! GNU General Public License for more details.
12!!
13!! You should have received a copy of the GNU General Public License
14!! along with this program; if not, write to the Free Software
15!! Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
16!! 02110-1301, USA.
17!!
18
19#include "global.h"
20
21module td_calc_oct_m
22 use comm_oct_m
23 use debug_oct_m
27 use forces_oct_m
28 use global_oct_m
29 use grid_oct_m
33 use ions_oct_m
34 use iso_c_binding
35 use, intrinsic :: iso_fortran_env
37 use lasers_oct_m
38 use lda_u_oct_m
41 use mesh_oct_m
45 use space_oct_m
49 use xc_oct_m
50
51 implicit none
52
53 private
54 public :: &
58
59contains
60
61 ! ---------------------------------------------------------
71 subroutine td_calc_tacc(namespace, space, gr, ions, ext_partners, st, hm, acc, time)
72 type(namespace_t), intent(in) :: namespace
73 class(space_t), intent(in) :: space
74 type(grid_t), intent(in) :: gr
75 type(ions_t), intent(in) :: ions
76 type(partner_list_t), intent(in) :: ext_partners
77 type(states_elec_t), intent(in) :: st
78 type(hamiltonian_elec_t), intent(in) :: hm
79 real(real64), intent(in) :: time
80 real(real64), contiguous, intent(out) :: acc(:)
81
82 real(real64) :: field(space%dim), x(space%dim)
83 complex(real64), allocatable :: zpsi(:, :), hzpsi(:,:), xzpsi(:,:,:), vnl_xzpsi(:,:)
84 integer :: j, k, ik, ist, idim
85 type(lasers_t), pointer :: lasers
86
87 push_sub(td_calc_tacc)
88
89 ! See #683
90 if (family_is_mgga(hm%xc%family) .or. family_is_hybrid(hm%xc)) then
91 call messages_not_implemented("Dipole acceleration with mGGAs and hybrid functionals")
92 end if
94 if (hm%lda_u_level /= dft_u_none) then
95 call messages_not_implemented("Dipole acceleration with DFT+U")
96 end if
97
98 ! This is due to an ASSERT in X(total_force_from_potential)
99 if (st%symmetrize_density) then
100 call messages_not_implemented("Dipole acceleration with SymmetrizeDensity = yes")
101 end if
102
103 ! The term i<[V_l,p]> + i<[V_nl,p]> may be considered as equal but opposite to the
104 ! force exerted by the electrons on the ions. COMMENT: This has to be thought about.
105 ! Maybe we are forgetting something....
106 call total_force_calculate(space, namespace, gr, ions, hm, st, acc)
107
108 ! Adds the laser contribution : i<[V_laser, p]>
109 ! WARNING: this ignores the possibility of non-electric td external fields.
110 field = m_zero
111 lasers => list_get_lasers(ext_partners)
112 if(associated(lasers)) then
113 do j = 1, lasers%no_lasers
114 call laser_electric_field(lasers%lasers(j), field(1:space%dim), time, 0.001_real64)
115 acc(1:space%dim) = acc(1:space%dim) - st%qtot*field(1:space%dim)
116 end do
117 end if
118
119 if (.not. hm%ep%non_local) then
120 pop_sub(td_calc_tacc)
121 return
122 end if
123
124 ! And now, i<[H,[V_nl,x]]>
125 x = m_zero
126 safe_allocate(zpsi(1:gr%np_part, 1:st%d%dim))
127 safe_allocate(hzpsi(1:gr%np_part, 1:st%d%dim))
128 safe_allocate(xzpsi(1:gr%np_part, 1:st%d%dim, 1:3))
129 safe_allocate(vnl_xzpsi(1:gr%np_part, 1:st%d%dim))
130
131 do ik = st%d%kpt%start, st%d%kpt%end
132 do ist = st%st_start, st%st_end
133
134 call states_elec_get_state(st, gr, ist, ik, zpsi)
135
136 call zhamiltonian_elec_apply_single(hm, namespace, gr, zpsi, hzpsi, ist, ik)
137
138 xzpsi = m_z0
139 do k = 1, gr%np
140 do j = 1, space%dim
141 xzpsi(k, 1:st%d%dim, j) = gr%x(j, k)*zpsi(k, 1:st%d%dim)
142 end do
143 end do
144
145 do j = 1, space%dim
146 call zhamiltonian_elec_apply_single(hm, namespace, gr, xzpsi(:, :, j), vnl_xzpsi, ist, ik, &
148
149 do idim = 1, st%d%dim
150 x(j) = x(j) - 2*st%occ(ist, ik)*real(zmf_dotp(gr, hzpsi(1:gr%np, idim), vnl_xzpsi(:, idim)), real64)
151 end do
152 end do
153
154 xzpsi = m_z0
155 do k = 1, gr%np
156 do j = 1, space%dim
157 xzpsi(k, 1:st%d%dim, j) = gr%x(j, k)*hzpsi(k, 1:st%d%dim)
158 end do
159 end do
160
161 do j = 1, space%dim
162 call zhamiltonian_elec_apply_single(hm, namespace, gr, xzpsi(:, :, j), vnl_xzpsi, ist, ik, &
164
165 do idim = 1, st%d%dim
166 x(j) = x(j) + 2*st%occ(ist, ik)*real(zmf_dotp(gr, zpsi(:, idim), vnl_xzpsi(:, idim)), real64)
167 end do
168 end do
169 end do
170 end do
171 safe_deallocate_a(zpsi)
172 safe_deallocate_a(hzpsi)
173 safe_deallocate_a(xzpsi)
174 safe_deallocate_a(vnl_xzpsi)
175
176 if (st%parallel_in_states) then
177 call comm_allreduce(st%mpi_grp, x)
178 end if
179 acc = acc + x
180
181 pop_sub(td_calc_tacc)
182 end subroutine td_calc_tacc
183
184! ---------------------------------------------------------
190! ---------------------------------------------------------
191 subroutine td_calc_tvel(namespace, gr, st, space, hm, ions, vel)
192 type(namespace_t), intent(in) :: namespace
193 type(grid_t), intent(in) :: gr
194 type(states_elec_t), intent(in) :: st
195 type(space_t), intent(in) :: space
196 type(hamiltonian_elec_t), intent(in) :: hm
197 type(ions_t), intent(in) :: ions
198 real(real64), contiguous, intent(out) :: vel(:)
199
200 real(real64), allocatable :: velocity(:,:,:)
201 integer :: st_start, st_end, ik, ist
202
203 push_sub(td_calc_tvel)
204
205 st_start = st%st_start
206 st_end = st%st_end
207
208 safe_allocate(velocity(1:space%dim, 1:st%nst, 1:st%nik))
209
210 if (hm%ep%requires_generalized_overlap) then
211 call zelec_velocity_me_uspp(namespace, gr, st, space, hm, velocity)
212 vel = m_zero
213 do ik = 1, st%nik
214 do ist = 1, st%nst
215 vel(1:space%dim) = vel(1:space%dim) + st%kweights(ik)*st%occ(ist, ik)*velocity(1:space%dim, ist, ik)
216 end do
217 end do
218 if (st%parallel_in_states .or. st%d%kpt%parallel) call comm_allreduce(st%st_kpt_mpi_grp, vel)
219 else
220 call elec_momentum_me(namespace, gr, st, space, hm, ions, velocity, non_local=.true.)
221 velocity(:, :, 1) = sum(velocity, dim=3)
222 vel = sum(velocity(:, :, 1), dim=2)
223 end if
224
225 safe_deallocate_a(velocity)
226
227 pop_sub(td_calc_tvel)
228 end subroutine td_calc_tvel
229
230! ---------------------------------------------------------
233! ---------------------------------------------------------
234 subroutine td_calc_ionch(mesh, st, ch, Nch)
235 type(mesh_t), intent(in) :: mesh
236 type(states_elec_t), intent(in) :: st
237 integer, intent(in) :: nch
238 real(real64), intent(out) :: ch(0:nch)
239
240 integer :: ik, ist, ii, jj, idim, nid
241 real(real64) :: prod, prod0
242 real(real64), allocatable :: n(:), nnot(:)
243 complex(real64), allocatable :: zpsi(:)
244 !combinations
245 integer :: next
246 type(c_ptr) :: c
247 integer, allocatable :: idx0(:), idx(:), idxref(:)
248
249 push_sub(td_calc_ionch)
250
251 assert(nch == st%nik*st%nst*st%d%dim)
252
253 safe_allocate( n(1: nch))
254 safe_allocate(nnot(1: nch))
255 safe_allocate(zpsi(1:mesh%np))
256
257 n(:) = m_zero
258 nnot(:)= m_zero
259
260
261 ii = 1
262 do ik = 1, st%nik
263 do ist = 1, st%nst
264 do idim = 1, st%d%dim
265
266 if (st%st_start <= ist .and. ist <= st%st_end .and. &
267 st%d%kpt%start <= ik .and. ik <= st%d%kpt%end) then
268 call states_elec_get_state(st, mesh, idim, ist, ik, zpsi)
269 n(ii) = zmf_nrm2(mesh, zpsi)
270 nnot(ii) = max(m_one - n(ii)**2, m_zero)
271 end if
272
273 ii = ii + 1
274
275 end do
276 end do
277 end do
278
279 if (st%parallel_in_states) then
280 call comm_allreduce(st%mpi_grp, n)
281 call comm_allreduce(st%mpi_grp, nnot)
282 end if
283
284 ch(:) = m_zero
285
286 nid = nch - 1
287 safe_allocate(idx(0:nid))
288 safe_allocate(idxref(0:nid))
289 idxref = (/ (ii, ii = 0, nid) /)
290 do ii = 0, nch
291 call loct_combination_init(c, nch, ii)
292 if (ii == 0) then
293 safe_allocate(idx0(0:0))
294 else
295 safe_allocate(idx0(0:ii-1))
296 end if
297 if (debug%info) then
298 call messages_write("P(")
299 call messages_write(ii)
300 call messages_write(") = 0")
301 call messages_new_line()
302 end if
303 ! Loop over combinations
304 do
305 prod = m_one
306 prod0 = m_one
307 if (debug%info) then
308 call messages_write("P(")
309 call messages_write(ii)
310 call messages_write(") += ")
311 end if
312 call loct_get_combination(c, idx0)
313 idx(:) = idxref(:)
314 do jj = 0, ii-1
315 idx(idx0(jj))= -1
316 if (debug%info) then
317 call messages_write(" No(")
318 call messages_write(idx0(jj)+1)
319 call messages_write(") ")
320 end if
321 prod0 = prod0 * nnot(idx0(jj)+1)
322 end do
323
324 do jj = 0, nid
325 if (idx(jj) >= 0) then
326 if (debug%info) then
327 call messages_write(" N(")
328 call messages_write(idx(jj)+1)
329 call messages_write(") ")
330 end if
331 prod = prod * n(idx(jj)+1)
332 end if
333 end do
334
335 if (debug%info) call messages_new_line()
336
337 ch(ii) = ch(ii) + prod*prod0
338
339 call loct_combination_next(c, next)
340 if (next /= 0) exit
341 end do
342 safe_deallocate_a(idx0)
344
345 if (debug%info) call messages_info()
346 end do
347
348 safe_deallocate_a(idx)
349 safe_deallocate_a(idxref)
350
351
352 safe_deallocate_a(n)
353 safe_deallocate_a(nnot)
354 safe_deallocate_a(zpsi)
355
356 pop_sub(td_calc_ionch)
357 end subroutine td_calc_ionch
358
359
360end module td_calc_oct_m
361
362!! Local Variables:
363!! mode: f90
364!! coding: utf-8
365!! End:
Functions to generate combinations.
Definition: loct_math.F90:242
type(debug_t), save, public debug
Definition: debug.F90:133
This module calculates the derivatives (gradients, Laplacians, etc.) of a function.
subroutine, public zelec_velocity_me_uspp(namespace, gr, st, space, hm, velocity)
Ultrasoft/PAW conserved macroscopic current (= dipole velocity), per state.
subroutine, public elec_momentum_me(namespace, gr, st, space, hm, ions, momentum, non_local)
type(lasers_t) function, pointer, public list_get_lasers(partners)
subroutine, public total_force_calculate(space, namespace, gr, ions, hm, st, x)
This computes the total forces on the ions created by the electrons (it excludes the force due to pos...
Definition: forces.F90:172
real(real64), parameter, public m_zero
Definition: global.F90:173
complex(real64), parameter, public m_z0
Definition: global.F90:183
real(real64), parameter, public m_one
Definition: global.F90:174
This module implements the underlying real-space grid.
Definition: grid.F90:96
integer, parameter, public term_non_local_potential
subroutine, public zhamiltonian_elec_apply_single(hm, namespace, mesh, psi, hpsi, ist, ik, terms, set_bc, set_phase)
integer, parameter, public velocity
This module defines classes and functions for interaction partners.
subroutine, public laser_electric_field(laser, field, time, dt)
Returns a vector with the electric field, no matter whether the laser is described directly as an ele...
Definition: lasers.F90:1175
integer, parameter, public dft_u_none
Definition: lda_u.F90:184
subroutine, public loct_get_combination(c, comb)
Definition: loct_math.F90:326
This module defines various routines, operating on mesh functions.
This module defines the meshes, which are used in Octopus.
Definition: mesh.F90:97
subroutine, public messages_not_implemented(feature, namespace)
Definition: messages.F90:1048
subroutine, public messages_new_line()
Definition: messages.F90:1069
subroutine, public messages_info(no_lines, iunit, debug_only, stress, all_nodes, namespace)
Definition: messages.F90:570
/* To use the profiling module, call profiling_in and profiling_out with the label of the region as a...
Definition: profiling.F90:122
This module handles spin dimensions of the states and the k-point distribution.
subroutine, public td_calc_tacc(namespace, space, gr, ions, ext_partners, st, hm, acc, time)
Electronic acceleration (to calculate harmonic spectrum...) It is calculated as:
Definition: td_calc.F90:144
subroutine, public td_calc_tvel(namespace, gr, st, space, hm, ions, vel)
Electronic velocity (to calculate harmonic spectrum...) It is calculated as:
Definition: td_calc.F90:264
subroutine, public td_calc_ionch(mesh, st, ch, Nch)
Multiple ionization probabilities calculated form the KS orbital densities C. Ullrich,...
Definition: td_calc.F90:307
Definition: xc.F90:97
pure logical function, public family_is_mgga(family, only_collinear)
Is the xc function part of the mGGA family.
Definition: xc.F90:687
logical pure function, public family_is_hybrid(xcs)
Returns true if the functional is an hybrid functional.
Definition: xc.F90:721
Description of the grid, containing information on derivatives, stencil, and symmetries.
Definition: grid.F90:148
Describes mesh distribution to nodes.
Definition: mesh.F90:165
The states_elec_t class contains all electronic wave functions.
int true(void)