Octopus
propagator_expmid.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
22 use debug_oct_m
25 use grid_oct_m
27 use global_oct_m
31 use ions_oct_m
33 use lda_u_oct_m
36 use parser_oct_m
40 use space_oct_m
43 use v_ks_oct_m
44 use xc_oct_m
45
46 implicit none
47
48 private
49
50 public :: &
53
54contains
55
56 ! ---------------------------------------------------------
58 subroutine exponential_midpoint(hm, namespace, space, gr, st, tr, time, dt, ions_dyn, ions, ext_partners, mc)
59 type(hamiltonian_elec_t), target, intent(inout) :: hm
60 type(namespace_t), intent(in) :: namespace
61 type(electron_space_t), intent(in) :: space
62 type(grid_t), target, intent(inout) :: gr
63 type(states_elec_t), target, intent(inout) :: st
64 type(propagator_base_t), target, intent(inout) :: tr
65 real(real64), intent(in) :: time
66 real(real64), intent(in) :: dt
67 type(ion_dynamics_t), intent(inout) :: ions_dyn
68 type(ions_t), intent(inout) :: ions
69 type(partner_list_t), intent(in) :: ext_partners
70 type(multicomm_t), intent(inout) :: mc
71
72 type(gauge_field_t), pointer :: gfield
73
74 push_sub(propagator_dt.exponential_midpoint)
75
76 call hm%ks_pot%interpolate_potentials(tr%vks_old, 3, time, dt, time - dt/m_two)
77
78 !move the ions to time 'time - dt/2'
79 call propagation_ops_elec_move_ions(tr%propagation_ops_elec, gr, hm, st, namespace, space, ions_dyn, ions, &
80 ext_partners, mc, time - m_half*dt, m_half*dt, save_pos = .true.)
81
82 gfield => list_get_gauge_field(ext_partners)
83 if(associated(gfield)) then
84 call propagation_ops_elec_propagate_gauge_field(tr%propagation_ops_elec, gfield, &
85 m_half*dt, time, save_gf = .true.)
86 end if
87
88 call propagation_ops_elec_update_hamiltonian(namespace, space, st, gr, hm, ext_partners, time - dt*m_half)
89
90 call propagation_ops_elec_fuse_density_exp_apply(tr%te, namespace, st, gr, hm, dt)
91
92 !restore to time 'time - dt'
93 call propagation_ops_elec_restore_ions(tr%propagation_ops_elec, ions_dyn, ions)
94
95 if(associated(gfield)) then
96 call propagation_ops_elec_restore_gauge_field(tr%propagation_ops_elec, namespace, space, hm, gr, ext_partners)
97 end if
98
99 pop_sub(propagator_dt.exponential_midpoint)
100 end subroutine exponential_midpoint
101
102 ! ---------------------------------------------------------
107 subroutine exponential_midpoint_predictor(hm, ks, namespace, space, gr, st, tr, time, dt, ions_dyn, ions, ext_partners, mc)
108 type(hamiltonian_elec_t), target, intent(inout) :: hm
109 type(v_ks_t), intent(inout) :: ks
110 type(namespace_t), intent(in) :: namespace
111 type(electron_space_t), intent(in) :: space
112 type(grid_t), target, intent(inout) :: gr
113 type(states_elec_t), target, intent(inout) :: st
114 type(propagator_base_t), target, intent(inout) :: tr
115 real(real64), intent(in) :: time
116 real(real64), intent(in) :: dt
117 type(ion_dynamics_t), intent(inout) :: ions_dyn
118 type(ions_t), intent(inout) :: ions
119 type(partner_list_t), intent(in) :: ext_partners
120 type(multicomm_t), intent(inout) :: mc
121
122 type(gauge_field_t), pointer :: gfield
123 type(states_elec_t) :: st0
124
125 push_sub(propagator_dt.exponential_midpoint_predictor)
126
127 if (hm%theory_level /= independent_particles) then
128 ! store copy of initial states
129 call states_elec_copy(st0, st)
130
131 ! get states, density and potential at time - dt/2
132 call propagation_ops_elec_fuse_density_exp_apply(tr%te, namespace, st, gr, hm, m_half*dt)
133
134 ! compute potential, also with states being predicted at time - dt/2 to get orbital-dependent
135 ! features correct (e.g. MGGA)
136 call v_ks_calc(ks, namespace, space, hm, st, ions, ext_partners, &
137 calc_current = .false., calc_energy = .false., calc_eigenval = .false.)
138
139 ! restore initial states to apply H(time - dt/2)
140 call states_elec_group_copy(st0%d, st0%group, st%group)
141 call states_elec_end(st0)
142 end if
143
144 ! move the ions to time time - dt/2
145 call propagation_ops_elec_move_ions(tr%propagation_ops_elec, gr, hm, st, namespace, space, ions_dyn, ions, &
146 ext_partners, mc, time - m_half*dt, m_half*dt, save_pos = .true.)
147
148 gfield => list_get_gauge_field(ext_partners)
149 if(associated(gfield)) then
150 call propagation_ops_elec_propagate_gauge_field(tr%propagation_ops_elec, gfield, &
151 m_half*dt, time, save_gf = .true.)
152 end if
154 call propagation_ops_elec_update_hamiltonian(namespace, space, st, gr, hm, ext_partners, time - dt*m_half)
155
156 ! apply Hamiltonian with dt
157 call propagation_ops_elec_fuse_density_exp_apply(tr%te, namespace, st, gr, hm, dt)
158
159 !restore to time 'time - dt'
160 call propagation_ops_elec_restore_ions(tr%propagation_ops_elec, ions_dyn, ions)
161
162 if(associated(gfield)) then
163 call propagation_ops_elec_restore_gauge_field(tr%propagation_ops_elec, namespace, space, hm, gr, ext_partners)
164 end if
165
166 pop_sub(propagator_dt.exponential_midpoint_predictor)
167 end subroutine exponential_midpoint_predictor
169
170!! Local Variables:
171!! mode: f90
172!! coding: utf-8
173!! End:
type(gauge_field_t) function, pointer, public list_get_gauge_field(partners)
real(real64), parameter, public m_two
Definition: global.F90:193
integer, parameter, public independent_particles
Theory level.
Definition: global.F90:237
real(real64), parameter, public m_half
Definition: global.F90:197
This module implements the underlying real-space grid.
Definition: grid.F90:119
This module defines classes and functions for interaction partners.
A module to handle KS potential, without the external potential.
This module handles the communicators for the various parallelization strategies.
Definition: multicomm.F90:147
subroutine, public propagation_ops_elec_restore_ions(wo, ions_dyn, ions)
subroutine, public propagation_ops_elec_propagate_gauge_field(wo, gfield, dt, time, save_gf)
subroutine, public propagation_ops_elec_update_hamiltonian(namespace, space, st, mesh, hm, ext_partners, time)
subroutine, public propagation_ops_elec_fuse_density_exp_apply(te, namespace, st, gr, hm, dt, dt2, op)
subroutine, public propagation_ops_elec_restore_gauge_field(wo, namespace, space, hm, mesh, ext_partners)
subroutine, public propagation_ops_elec_move_ions(wo, gr, hm, st, namespace, space, ions_dyn, ions, ext_partners, mc, time, dt, save_pos)
subroutine, public exponential_midpoint_predictor(hm, ks, namespace, space, gr, st, tr, time, dt, ions_dyn, ions, ext_partners, mc)
Exponential midpoint with prediction of the half time step This is equivalent to an explicit Magnus i...
subroutine, public exponential_midpoint(hm, namespace, space, gr, st, tr, time, dt, ions_dyn, ions, ext_partners, mc)
Exponential midpoint.
This module handles groups of electronic batches and their parallel distribution.
subroutine, public states_elec_group_copy(d, group_in, group_out, copy_data, special)
make a copy of a group
subroutine, public states_elec_end(st)
finalize the states_elec_t object
subroutine, public states_elec_copy(stout, stin, exclude_wfns, exclude_eigenval, special)
make a (selective) copy of a states_elec_t object
subroutine, public v_ks_calc(ks, namespace, space, hm, st, ions, ext_partners, calc_eigenval, time, calc_energy, calc_current, force_semilocal)
Definition: v_ks.F90:752
Definition: xc.F90:116
int true(void)