Octopus
electrons.F90
Go to the documentation of this file.
1!! Copyright (C) 2002-2006 M. Marques, A. Castro, A. Rubio, G. Bertsch
2!! Copyright (C) 2009 X. Andrade
3!! Copyright (C) 2020 M. Oliveira
4!!
5!! This program is free software; you can redistribute it and/or modify
6!! it under the terms of the GNU General Public License as published by
7!! the Free Software Foundation; either version 2, or (at your option)
8!! any later version.
9!!
10!! This program is distributed in the hope that it will be useful,
11!! but WITHOUT ANY WARRANTY; without even the implied warranty of
12!! MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13!! GNU General Public License for more details.
14!!
15!! You should have received a copy of the GNU General Public License
16!! along with this program; if not, write to the Free Software
17!! Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
18!! 02110-1301, USA.
19!!
20
21#include "global.h"
22
23
24module electrons_oct_m
25 use accel_oct_m
33 use debug_oct_m
35 use dipole_oct_m
39 use elf_oct_m
43 use forces_oct_m
45 use global_oct_m
46 use grid_oct_m
56 use ions_oct_m
57 use kick_oct_m
62 use lasers_oct_m
63 use lda_u_oct_m
64 use loct_oct_m
65 use mesh_oct_m
68 use mpi_oct_m
73 use output_oct_m
75 use parser_oct_m
76 use pes_oct_m
91 use rdmft_oct_m
93 use scf_oct_m
94 use space_oct_m
98 use stress_oct_m
99 use sort_oct_m
101 use system_oct_m
102 use td_oct_m
105 use v_ks_oct_m
106 use wannier_oct_m, only: wannier_t
108 use xc_oct_m
109 use xc_f03_lib_m
110 use xc_oep_oct_m
114
115 implicit none
116
117 private
118 public :: &
120
121
127 type, extends(system_t) :: electrons_t
128 ! Components are public by default
129 type(electron_space_t) :: space
130 class(ions_t), pointer :: ions => null()
131 type(photons_t), pointer :: photons => null()
132 type(grid_t) :: gr
133 type(states_elec_t) :: st
134 type(v_ks_t) :: ks
135 type(output_t) :: outp
136 type(multicomm_t) :: mc
137 type(hamiltonian_elec_t) :: hm
138 type(td_t) :: td
139 type(current_t) :: current_calculator
140 type(dipole_t) :: dipole
141 type(scf_t) :: scf
142 type(rdm_t) :: rdm
143
144 type(kpoints_t) :: kpoints
145
146 logical :: generate_epot
147
148 type(states_elec_t) :: st_copy
149
150 ! At the moment this is not treated as an external potential
151 class(lasers_t), pointer :: lasers => null()
152 class(gauge_field_t), pointer :: gfield => null()
153
154 ! List with all the external partners
155 ! This will become a list of interactions in the future
156 type(partner_list_t) :: ext_partners
157
158 !TODO: have a list of self interactions
159 type(xc_interaction_t), pointer :: xc_interaction => null()
160
161 type(dmp_t) :: dmp
162
163 logical :: ions_propagated = .false.
164
165 ! everything related to wannier functions
166 type(wannier_t) :: wannier
167
168 contains
169 procedure :: init_interaction => electrons_init_interaction
170 procedure :: new_algorithm => electrons_new_algorithm
171 procedure :: initialize => electrons_initialize
172 procedure :: do_algorithmic_operation => electrons_do_algorithmic_operation
173 procedure :: is_tolerance_reached => electrons_is_tolerance_reached
174 procedure :: update_quantity => electrons_update_quantity
175 procedure :: init_interaction_as_partner => electrons_init_interaction_as_partner
176 procedure :: copy_quantities_to_interaction => electrons_copy_quantities_to_interaction
177 procedure :: output_start => electrons_output_start
178 procedure :: output_write => electrons_output_write
179 procedure :: output_finish => electrons_output_finish
180 procedure :: process_is_slave => electrons_process_is_slave
181 procedure :: restart_write_data => electrons_restart_write_data
182 procedure :: restart_read_data => electrons_restart_read_data
183 procedure :: update_kinetic_energy => electrons_update_kinetic_energy
184 procedure :: algorithm_start => electrons_algorithm_start
185 procedure :: ground_state_run => electrons_ground_state_run_system
186 final :: electrons_finalize
187 end type electrons_t
188
189 interface electrons_t
190 procedure electrons_constructor
191 end interface electrons_t
192
193contains
194
199 function electrons_constructor(namespace, grp, calc_mode_id) result(sys)
200 class(electrons_t), pointer :: sys
201 type(namespace_t), intent(in) :: namespace
202 type(mpi_grp_t), intent(in) :: grp
203 integer, optional, intent(in) :: calc_mode_id
204
205 integer :: iatom
206 integer(int64) :: go_type
207 type(lattice_vectors_t) :: latt_inp
208 logical :: has_photons, variable_cell, cell_dynamics
209
210 push_sub_with_profile(electrons_constructor)
211
212 allocate(sys)
213
214 sys%namespace = namespace
215
216 call sys%init_parallelization(grp)
217
218 call messages_obsolete_variable(sys%namespace, 'SystemName')
219
220 sys%space = electron_space_t(sys%namespace)
221 call sys%space%write_info(sys%namespace)
222 if (sys%space%has_mixed_periodicity()) then
223 call messages_experimental('Support for mixed periodicity systems')
224 end if
226 sys%ions => ions_t(sys%namespace, grp=sys%grp, latt_inp=latt_inp, shared_namespace=.true.)
228 ! We first determine whether the cell is varying or not, as this affects the generation of
229 ! the boundary points (a varying cell needs the full cube stencil, see grid_init_stage_1).
230 variable_cell = .false.
231 if (present(calc_mode_id)) then
232 if (calc_mode_id == option__calculationmode__go) then
233 call parse_variable(sys%namespace, 'GOType', option__gotype__ion_positions, go_type)
234 variable_cell = bitand(go_type, option__gotype__cell_shape) /= 0 &
235 .or. bitand(go_type, option__gotype__cell_volume) /= 0
236 end if
237 end if
238 call parse_variable(sys%namespace, 'CellDynamics', .false., cell_dynamics)
239 variable_cell = variable_cell .or. cell_dynamics
240
241 call grid_init_stage_1(sys%gr, sys%namespace, sys%space, sys%grp, &
242 sys%ions%symm, latt_inp, sys%ions%natoms, sys%ions%pos, variable_cell)
244 if (sys%space%is_periodic()) then
245 call sys%ions%latt%write_info(sys%namespace)
246 end if
248 ! Sanity check for atomic coordinates
249 do iatom = 1, sys%ions%natoms
250 ! Using the same tolerance of fold_into_cell to avoid problems with mixed periodicities
251 ! as the default tolerance of contains_point is too tight
252 if (.not. sys%gr%box%contains_point(sys%ions%pos(:, iatom), tol=1.0e-6_real64)) then
253 if (sys%space%periodic_dim /= sys%space%dim) then
254 write(message(1), '(a,i5,a)') "Atom ", iatom, " is outside the box."
255 call messages_warning(1, namespace=sys%namespace)
256 end if
257 end if
258 end do
259
260 ! Find possible non-symmorphic symmetries compatible with the real-space grid
261 if (sys%space%dim == 3) then
262 call symmetries_use_compatible_nonsymmorphic(sys%gr%symm, sys%gr%idx%ll, namespace)
263 end if
265 ! we need k-points for periodic systems
266 call kpoints_init(sys%kpoints, sys%namespace, sys%gr%symm, sys%space%dim, sys%space%periodic_dim, sys%ions%latt, &
267 sys%grp)
269 call states_elec_init(sys%st, sys%namespace, sys%space, sys%ions%val_charge(), sys%kpoints, calc_mode_id)
270 call sys%st%write_info(sys%namespace)
272 ! if independent particles in N dimensions are being used, need to initialize them
273 ! after masses are set to 1 in grid_init_stage_1 -> derivatives_init
274 call sys%st%modelmbparticles%copy_masses(sys%gr%der%masses)
276 call elf_init(sys%namespace)
278 if (present(calc_mode_id)) then
279 sys%generate_epot = calc_mode_id /= option__calculationmode__dummy
280 else
281 sys%generate_epot = .true.
282 end if
283
284 call sys%dipole%init(sys%space)
285
286 sys%supported_interactions_as_partner = [current_to_mxll_field]
287
288 call sys%quantities%add(quantity_t("wavefunctions", updated_on_demand = .false.))
289 call sys%quantities%add(quantity_t("current", updated_on_demand = .true., parents=["wavefunctions"]))
290 call sys%quantities%add(quantity_t("dipole", updated_on_demand = .true., parents=["wavefunctions"]))
291 call current_init(sys%current_calculator, sys%namespace)
292
293 !%Variable EnablePhotons
294 !%Type logical
295 !%Default no
296 !%Section Hamiltonian
297 !%Description
298 !% This variable can be used to enable photons in several types of calculations.
299 !% It can be used to activate the one-photon OEP formalism.
300 !% In the case of CalculationMode = casida, it enables photon modes as
301 !% described in ACS Photonics 2019, 6, 11, 2757-2778.
302 !% Finally, if set to yes when solving the ferquency-dependent Sternheimer
303 !% equation, the photons are coupled to the electronic subsystem.
304 !%End
305 call messages_obsolete_variable(namespace, 'OEPPtX', 'EnablePhotons')
306 call parse_variable(namespace, 'EnablePhotons', .false., has_photons)
307 if (has_photons) then
308 call messages_experimental("EnablePhotons = yes")
309 sys%photons => photons_t(sys%namespace, sys%grp)
310 else
311 nullify(sys%photons)
312 end if
313
314 call sys%wannier%init_from_input(sys%namespace, sys%kpoints, sys%ions, sys%space, sys%st, sys%gr)
315
317
318 pop_sub_with_profile(electrons_constructor)
319 end function electrons_constructor
320
321 ! ---------------------------------------------------------
322 subroutine electrons_init_interaction(this, interaction)
323 class(electrons_t), target, intent(inout) :: this
324 class(interaction_t), intent(inout) :: interaction
325
326 real(real64) :: dmin
327 integer :: rankmin, depth
328 logical :: mxll_interaction_present
329 logical :: calc_dipole
330
331 push_sub(electrons_init_interactions)
332
333 mxll_interaction_present = .false.
334 select type (interaction)
336 call interaction%init(this%gr, 3)
337 mxll_interaction_present = .true.
338 interaction%type = mxll_field_trans
340 call interaction%init(this%gr, 3)
341 mxll_interaction_present = .true.
343 call interaction%init(this%gr, 3)
344 mxll_interaction_present = .true.
345 class default
346 message(1) = "Trying to initialize an unsupported interaction by the electrons."
347 call messages_fatal(1, namespace=this%namespace)
348 end select
349
350 if (mxll_interaction_present) then
351 calc_dipole = any(this%hm%mxll%coupling_mode == &
353
354 if (calc_dipole) then
355 assert(this%space%periodic_dim == 0)
356 this%hm%mxll%calc_field_dip = .true.
357 this%hm%mxll%center_of_mass(1:3) = this%ions%center_of_mass()
358 this%hm%mxll%center_of_mass_ip = mesh_nearest_point(this%gr, this%hm%mxll%center_of_mass, dmin, rankmin)
359 this%hm%mxll%center_of_mass_rankmin = rankmin
360 end if
361 end if
362
363 ! set interpolation depth for field-transfer interactions
364 select type (interaction)
365 class is (field_transfer_t)
366 ! interpolation depth depends on the propagator
367 select type (algo => this%algo)
368 type is (propagator_exp_mid_t)
369 depth = 3
370 type is (propagator_aetrs_t)
371 depth = 3
372 type is (propagator_bomd_t)
373 depth = 1
374 class default
375 message(1) = "The chosen algorithm does not yet support interaction interpolation"
376 call messages_fatal(1, namespace=this%namespace)
377 end select
378
379 call interaction%init_interpolation(depth, interaction%label)
380 end select
381
382 pop_sub(electrons_init_interactions)
383 end subroutine electrons_init_interaction
384
385 ! ---------------------------------------------------------
386 subroutine electrons_init_parallelization(this)
387 class(electrons_t), intent(inout) :: this
388
389 integer(int64) :: index_range(4)
390 real(real64) :: mesh_global, mesh_local, wfns
391 integer :: idir
392 real(real64) :: spiral_q(3), spiral_q_red(3)
393 type(block_t) :: blk
394
396
397 ! store the ranges for these two indices (serves as initial guess
398 ! for parallelization strategy)
399 index_range(1) = this%gr%np_global ! Number of points in mesh
400 index_range(2) = this%st%nst ! Number of states
401 index_range(3) = this%st%nik ! Number of k-points
402 index_range(4) = 100000 ! Some large number
403
404 ! create index and domain communicators
405 call multicomm_init(this%mc, this%namespace, this%grp, calc_mode_par, &
406 this%grp%size, index_range, (/ 5000, 1, 1, 1 /))
407
408 call this%ions%partition(this%mc)
409 call kpoints_distribute(this%st, this%mc)
410 call states_elec_distribute_nodes(this%st, this%namespace, this%mc)
411
412
413 if (parse_is_defined(this%namespace, 'TDMomentumTransfer') .or. &
414 parse_is_defined(this%namespace, 'TDReducedMomentumTransfer')) then
415 spiral_q = m_zero
416 if (parse_block(this%namespace, 'TDMomentumTransfer', blk) == 0) then
417 do idir = 1, this%space%dim
418 call parse_block_float(blk, 0, idir - 1, spiral_q(idir))
419 end do
420 else if(parse_block(this%namespace, 'TDReducedMomentumTransfer', blk) == 0) then
421 do idir = 1, this%space%dim
422 call parse_block_float(blk, 0, idir - 1, spiral_q_red(idir))
423 end do
424 call kpoints_to_absolute(this%kpoints%latt, spiral_q_red(1:this%space%dim), spiral_q(1:this%space%dim))
425 end if
426 call parse_block_end(blk)
427 call grid_init_stage_2(this%gr, this%namespace, this%space, this%mc, spiral_q)
428 else
429 call grid_init_stage_2(this%gr, this%namespace, this%space, this%mc)
430 end if
431
432 if (this%st%symmetrize_density) then
433 call mesh_check_symmetries(this%gr, this%gr%symm, this%ions%space%periodic_dim)
434 end if
435
436 call output_init(this%outp, this%namespace, this%space, this%st, this%gr, this%st%nst, this%ks)
437 call states_elec_densities_init(this%st, this%gr)
438 call states_elec_exec_init(this%st, this%namespace, this%mc)
439
440 if (associated(this%photons)) then
441 call this%ks%v_ks_photons%set_active(.true.)
442 end if
443
444 call v_ks_init(this%ks, this%namespace, this%gr, this%st, this%ions, this%mc, this%space, &
445 this%kpoints)
446 if (this%ks%theory_level == kohn_sham_dft .or. this%ks%theory_level == generalized_kohn_sham_dft) then
447 this%xc_interaction => xc_interaction_t(this)
448 end if
449
450 ! For the moment the photons are initialized here
451 if (this%ks%v_ks_photons%active()) then
452 call this%ks%v_ks_photons%setup(this%namespace, this%photons%modes, this%gr, this%st, this%ions, &
453 this%mc, this%space, this%ks%xc, this%ks%xc_family, this%ks%oep%level)
454 end if
455
456
457 ! Temporary place for the initialization of the lasers
458 this%lasers => lasers_t(this%namespace)
459 call lasers_parse_external_fields(this%lasers)
460 call lasers_generate_potentials(this%lasers, this%gr, this%space, this%ions%latt)
461 if(this%lasers%no_lasers > 0) then
462 call this%ext_partners%add(this%lasers)
463 call lasers_check_symmetries(this%lasers, this%kpoints)
464 else
465 deallocate(this%lasers)
466 end if
467
468 ! Temporary place for the initialization of the gauge field
469 this%gfield => gauge_field_t(this%namespace, this%ions%latt%rcell_volume)
470 if(gauge_field_is_used(this%gfield)) then
471 call this%ext_partners%add(this%gfield)
472 call gauge_field_check_symmetries(this%gfield, this%kpoints)
473 else
474 deallocate(this%gfield)
475 end if
476
477 call hamiltonian_elec_init(this%hm, this%namespace, this%space, this%gr, this%ions, this%ext_partners, &
478 this%st, this%ks%theory_level, this%ks%xc, this%mc, this%kpoints, &
479 need_exchange = output_need_exchange(this%outp) .or. this%ks%oep%level /= oep_level_none, &
480 xc_photons = this%ks%v_ks_photons%get_xc_photons() )
482 if (this%hm%pcm%run_pcm .and. this%mc%par_strategy /= p_strategy_serial .and. this%mc%par_strategy /= p_strategy_states) then
483 call messages_experimental('Parallel in domain calculations with PCM')
484 end if
485
486 ! Print memory requirements
487 call messages_print_with_emphasis(msg='Approximate memory requirements', namespace=this%namespace)
488
489 mesh_global = mesh_global_memory(this%gr)
490 mesh_local = mesh_local_memory(this%gr)
491
492 call messages_write('Mesh')
493 call messages_new_line()
494 call messages_write(' global :')
495 call messages_write(mesh_global, units = unit_megabytes, fmt = '(f10.1)')
496 call messages_new_line()
497 call messages_write(' local :')
498 call messages_write(mesh_local, units = unit_megabytes, fmt = '(f10.1)')
499 call messages_new_line()
500 call messages_write(' total :')
501 call messages_write(mesh_global + mesh_local, units = unit_megabytes, fmt = '(f10.1)')
502 call messages_new_line()
503 call messages_info(namespace=this%namespace)
504
505 wfns = states_elec_wfns_memory(this%st, this%gr)
506 call messages_write('States')
507 call messages_new_line()
508 call messages_write(' real :')
509 call messages_write(wfns, units = unit_megabytes, fmt = '(f10.1)')
510 call messages_write(' (par_kpoints + par_states + par_domains)')
511 call messages_new_line()
512 call messages_write(' complex :')
513 call messages_write(2.0_8*wfns, units = unit_megabytes, fmt = '(f10.1)')
514 call messages_write(' (par_kpoints + par_states + par_domains)')
515 call messages_new_line()
516 call messages_info(namespace=this%namespace)
517
518 call messages_print_with_emphasis(namespace=this%namespace)
519
520 if (this%generate_epot) then
521 message(1) = "Info: Generating external potential"
522 call messages_info(1, namespace=this%namespace)
523 call hamiltonian_elec_epot_generate(this%hm, this%namespace, this%space, this%gr, this%ions, &
524 this%ext_partners, this%st)
525 message(1) = " done."
526 call messages_info(1, namespace=this%namespace)
527 end if
528
529 if (this%ks%theory_level /= independent_particles) then
530 call poisson_async_init(this%hm%psolver, this%mc)
531 ! slave nodes do not call the calculation routine
532 if (multicomm_is_slave(this%mc)) then
533 !for the moment we only have one type of slave
534 call poisson_slave_work(this%hm%psolver, this%namespace)
535 end if
536 end if
537
538 allocate(this%supported_interactions(0))
539 select case (this%hm%mxll%coupling_mode)
541 this%supported_interactions = [this%supported_interactions, mxll_e_field_to_matter]
543 this%supported_interactions = [this%supported_interactions, mxll_vec_pot_to_matter]
544 if (this%hm%mxll%add_zeeman) then
545 this%supported_interactions = [this%supported_interactions, mxll_b_field_to_matter]
546 end if
548 if (this%hm%mxll%add_electric_dip .or. this%hm%mxll%add_electric_quad) then
549 this%supported_interactions = [this%supported_interactions, mxll_e_field_to_matter]
550 end if
551 if (this%hm%mxll%add_magnetic_dip) then
552 this%supported_interactions = [this%supported_interactions, mxll_b_field_to_matter]
553 end if
555 ! Do not initialize any interaction with Maxwell
556 case default
557 message(1) = "Unknown maxwell-matter coupling"
558 call messages_fatal(1, namespace=this%namespace)
559 end select
560
561 call this%wannier%init_parallelization(this%namespace, this%st, this%ions, this%kpoints)
562
564 end subroutine electrons_init_parallelization
565
566 ! ---------------------------------------------------------
567 subroutine electrons_new_algorithm(this, factory)
568 class(electrons_t), intent(inout) :: this
569 class(algorithm_factory_t), intent(in) :: factory
570
572
573 call system_new_algorithm(this, factory)
574
575 select type (algo => this%algo)
576 class is (propagator_t)
577
578 call td_init(this%td, this%namespace, this%space, this%gr, this%ions, this%st, this%ks, &
579 this%hm, this%ext_partners, this%outp, this%dmp)
580
581 ! this corresponds to the first part of td_init_run
582 call td_allocate_wavefunctions(this%td, this%namespace, this%mc, this%gr, this%ions, this%st, &
583 this%hm, this%space)
584 call td_init_gaugefield(this%td, this%namespace, this%gr, this%st, this%ks, this%hm, &
585 this%ext_partners, this%space)
586
587 class is (minimizer_algorithm_t)
588
589 call electrons_gs_allocate_wavefunctions(this%namespace, this%gr, this%st, this%hm, this%scf, this%ks, &
590 this%ions)
591
592 class default
593 assert(.false.)
594 end select
595
597 end subroutine electrons_new_algorithm
598
599 ! ---------------------------------------------------------
600 subroutine electrons_initialize(this)
601 class(electrons_t), intent(inout) :: this
602
603 push_sub(electrons_initialize)
604
605 if (associated(this%ions)) call this%ions%initialize()
606
607 select type (algo => this%algo)
608 class is (propagator_t)
609 call td_set_from_scratch(this%td, .true.)
610 call td_load_restart_from_gs(this%td, this%namespace, this%space, this%mc, this%gr, &
611 this%ext_partners, this%st, this%ks, this%hm)
612 call this%wannier%init_data_from_file(this%kpoints)
613
614 class is (minimizer_algorithm_t)
615
616 call electrons_gs_initialize(this%namespace, this%scf, this%rdm, this%gr, this%mc, this%st, &
617 this%hm, this%ions, this%ks, this%space, this%ext_partners, fromscratch=.true.)
618 class default
619 assert(.false.)
620 end select
621
622 pop_sub(electrons_initialize)
623 end subroutine electrons_initialize
624
625 ! ---------------------------------------------------------
626 subroutine electrons_algorithm_start(this)
627 class(electrons_t), intent(inout) :: this
628
630
631 call system_algorithm_start(this)
632
633 select type (algo => this%algo)
634 class is (propagator_t)
635
636 ! additional initialization needed for electrons
637 call td_init_with_wavefunctions(this%td, this%namespace, this%space, this%mc, this%gr, this%ions, &
638 this%ext_partners, this%st, this%ks, this%hm, this%outp, this%dmp, td_get_from_scratch(this%td))
639
640 end select
641
643 end subroutine electrons_algorithm_start
644
645 ! ---------------------------------------------------------
646 logical function electrons_do_algorithmic_operation(this, operation, updated_quantities) result(done)
647 class(electrons_t), intent(inout) :: this
648 class(algorithmic_operation_t), intent(in) :: operation
649 character(len=:), allocatable, intent(out) :: updated_quantities(:)
650
651 logical :: update_energy_
652 type(gauge_field_t), pointer :: gfield
653 real(real64) :: time
654 integer :: iter
655
657 call profiling_in(trim(this%namespace%get())//":"//trim(operation%id))
658
659 update_energy_ = .true.
660
661 ! kick at t > 0 still missing!
663 done = .true.
664 select type (algo => this%algo)
665 class is (propagator_t)
666 time = algo%iteration%value()
667 select case (operation%id)
668 case (aetrs_first_half)
669 ! propagate half of the time step with H(time)
670 call get_fields_from_interaction(this, time)
671 call propagation_ops_elec_update_hamiltonian(this%namespace, this%space, this%st, this%gr, &
672 this%hm, this%ext_partners, time)
673 call propagation_ops_elec_exp_apply(this%td%tr%te, this%namespace, this%st, this%gr, this%hm, m_half*algo%dt)
674
675 case (aetrs_extrapolate)
676 ! Do the extrapolation of the Hamiltonian
677 ! First the extrapolation of the potential
678 call this%hm%ks_pot%interpolation_new(this%td%tr%vks_old, time+algo%dt, algo%dt)
679
680 !Get the potentials from the interpolator
681 call propagation_ops_elec_interpolate_get(this%hm, this%td%tr%vks_old)
682
683 ! Second the ions and gauge field which later on will be treated as extrapolation
684 ! of interactions, but this is not yet possible
685
686 ! move the ions to time t
687 call propagation_ops_elec_move_ions(this%td%tr%propagation_ops_elec, this%gr, this%hm, &
688 this%st, this%namespace, this%space, this%td%ions_dyn, this%ions, this%ext_partners, &
689 this%mc, time+algo%dt, algo%dt)
690
691 !Propagate gauge field
692 gfield => list_get_gauge_field(this%ext_partners)
693 if(associated(gfield)) then
694 call propagation_ops_elec_propagate_gauge_field(this%td%tr%propagation_ops_elec, gfield, &
695 algo%dt, time+algo%dt)
696 end if
697
698 !Update Hamiltonian and current
699 call get_fields_from_interaction(this, time+algo%dt)
700 call propagation_ops_elec_update_hamiltonian(this%namespace, this%space, this%st, this%gr, &
701 this%hm, this%ext_partners, time+algo%dt)
702
703 case (aetrs_second_half)
704 !Do the time propagation for the second half of the time step
705 call propagation_ops_elec_fuse_density_exp_apply(this%td%tr%te, this%namespace, this%st, &
706 this%gr, this%hm, m_half*algo%dt)
707
708 updated_quantities = ["wavefunctions"]
709
710 case (expmid_extrapolate)
711 ! the half step of this propagator screws with the gauge field kick
712 gfield => list_get_gauge_field(this%ext_partners)
713 if(associated(gfield)) then
714 assert(gauge_field_is_propagated(gfield) .eqv. .false.)
715 end if
716
717 ! Do the extrapolation of the Hamiltonian
718 ! First the extrapolation of the potential
719 call this%hm%ks_pot%interpolation_new(this%td%tr%vks_old, time+algo%dt, algo%dt)
720
721 ! get the potentials from the interpolator
722 call this%hm%ks_pot%interpolate_potentials(this%td%tr%vks_old, 3, time+algo%dt, algo%dt, time + algo%dt/m_two)
723
724 ! Second the ions which later on will be treated as extrapolation of interactions,
725 ! but this is not yet possible
726 ! move the ions to the half step
727 call propagation_ops_elec_move_ions(this%td%tr%propagation_ops_elec, this%gr, this%hm, this%st, &
728 this%namespace, this%space, this%td%ions_dyn, this%ions, this%ext_partners, &
729 this%mc, time + m_half*algo%dt, m_half*algo%dt, save_pos=.true.)
730
731 call get_fields_from_interaction(this, time + m_half*algo%dt)
732 call propagation_ops_elec_update_hamiltonian(this%namespace, this%space, this%st, this%gr, &
733 this%hm, this%ext_partners, time + m_half*algo%dt)
734
735 case (expmid_propagate)
736 ! Do the actual propagation step
737 call propagation_ops_elec_fuse_density_exp_apply(this%td%tr%te, this%namespace, this%st, &
738 this%gr, this%hm, algo%dt)
739
740 ! restore to previous time
741 call propagation_ops_elec_restore_ions(this%td%tr%propagation_ops_elec, this%td%ions_dyn, this%ions)
742
743 updated_quantities = ["wavefunctions"]
744
745 case (bomd_start)
746 call scf_init(this%scf, this%namespace, this%gr, this%ions, this%st, this%mc, this%hm, this%space)
747 ! the ions are propagated inside the propagation step already, so no need to do it at the end
748 this%ions_propagated = .true.
749
750 case (verlet_update_pos)
751 ! move the ions to time t
752 call propagation_ops_elec_propagate_ions_and_cell(this%gr, this%hm, this%st, this%namespace, this%space, &
753 this%td%ions_dyn, this%ions, this%mc, time+algo%dt, algo%dt)
754
755 case (bomd_elec_scf)
756 call hamiltonian_elec_epot_generate(this%hm, this%namespace, this%space, this%gr, this%ions, &
757 this%ext_partners, this%st, time = time+algo%dt)
758 ! now calculate the eigenfunctions
759 call scf_run(this%scf, this%namespace, this%space, this%mc, this%gr, this%ions, &
760 this%ext_partners, this%st, this%ks, this%hm, verbosity = verb_compact)
761 ! TODO: Check if this call is realy needed. - NTD
762 call hamiltonian_elec_epot_generate(this%hm, this%namespace, this%space, this%gr, this%ions, &
763 this%ext_partners, this%st, time = time+algo%dt)
764
765 ! update Hamiltonian and eigenvalues (fermi is *not* called)
766 call v_ks_calc(this%ks, this%namespace, this%space, this%hm, this%st, this%ions, this%ext_partners, &
767 calc_eigenval = .true., time = time+algo%dt, calc_energy = .true.)
768
769 ! Get the energies.
770 call energy_calc_total(this%namespace, this%space, this%hm, this%gr, this%st, this%ext_partners, iunit = -1)
771
772 updated_quantities = ["wavefunctions"]
773
774 case (verlet_compute_acc)
775 ! Do nothing, forces are computing in scf_run
776 if (this%td%ions_dyn%cell_relax()) then
777 assert(this%scf%calc_stress)
778 call this%td%ions_dyn%update_stress(this%ions%space, this%st%stress_tensors%total, &
779 this%ions%latt%rlattice, this%ions%latt%rcell_volume)
780 end if
781
782 case (verlet_compute_vel)
783 call ion_dynamics_propagate_vel(this%td%ions_dyn, this%ions)
784 ! TODO: Check if this call is realy needed. - NTD
785 call hamiltonian_elec_epot_generate(this%hm, this%namespace, this%space, this%gr, this%ions, &
786 this%ext_partners, this%st, time = time+algo%dt)
787 call this%ions%update_kinetic_energy()
788
789 case (expmid_start)
790 this%ions_propagated = .false.
791
792 case (aetrs_start)
793 ! the ions are propagated inside the propagation step already, so no need to do it at the end
794 this%ions_propagated = .true.
795
796 case (iteration_done)
798 done = .false.
799
800 case (bomd_finish)
801 call scf_end(this%scf)
802
804 case default
805 done = .false.
806 end select
807
808 class is(minimizer_algorithm_t)
809
810 ! Clocks starts at 0....
811 iter = nint(this%iteration%value()) + 1
812
813 select case(operation%id)
814 case (gs_scf_start)
815 call scf_start(this%scf, this%namespace, this%gr, this%ions, this%st, this%ks, this%hm, this%outp)
816
817 case (gs_scf_iteration)
818
819 call scf_iter(this%scf, this%namespace, this%space, this%mc, this%gr, this%ions, &
820 this%ext_partners, this%st, this%ks, this%hm, iter, outp = this%outp, &
821 restart_dump=this%scf%restart_dump)
822
823 algo%converged = scf_iter_finish(this%scf, this%namespace, this%space, this%gr, this%ions,&
824 this%st, this%ks, this%hm, iter, outp = this%outp)
825
826 updated_quantities = ["wavefunctions"]
827
828 case (gs_scf_finish)
829
830 ! Here iteration is iter-1, as the clock ticked before SCF_FINISH
831 call scf_finish(this%scf, this%namespace, this%space, this%gr, this%ions, &
832 this%ext_partners, this%st, this%ks, this%hm, iter-1, outp = this%outp)
833
834 case default
835 done = .false.
836 end select
837 class default
838 done = .false.
839 end select
840
841 call profiling_out(trim(this%namespace%get())//":"//trim(operation%id))
844
845 ! ---------------------------------------------------------
846 logical function electrons_is_tolerance_reached(this, tol) result(converged)
847 class(electrons_t), intent(in) :: this
848 real(real64), intent(in) :: tol
849
851
852 converged = .false.
853
856
857 ! ---------------------------------------------------------
858 subroutine electrons_update_quantity(this, label)
859 class(electrons_t), intent(inout) :: this
860 character(len=*), intent(in) :: label
861
862 class(quantity_t), pointer :: quantity
863
865 call profiling_in(trim(this%namespace%get())//":"//"UPDATE_QUANTITY")
866
867 quantity => this%quantities%get(label)
868 if(associated(quantity)) then
869 assert(quantity%updated_on_demand)
870 endif
871
872 select case (label)
873 case ("current")
874 call states_elec_allocate_current(this%st, this%space, this%gr)
875 call current_calculate(this%current_calculator, this%namespace, this%gr, &
876 this%hm, this%space, this%st)
877 case ("dipole")
878 call this%dipole%calculate(this%gr, this%ions, this%st)
879 case default
880 message(1) = "Incompatible quantity: "//trim(label)//"."
881 call messages_fatal(1, namespace=this%namespace)
882 end select
883
884 call profiling_out(trim(this%namespace%get())//":"//"UPDATE_QUANTITY")
886 end subroutine electrons_update_quantity
887
888 ! ---------------------------------------------------------
889 subroutine electrons_init_interaction_as_partner(partner, interaction)
890 class(electrons_t), intent(in) :: partner
891 class(interaction_surrogate_t), intent(inout) :: interaction
892
894
895 select type (interaction)
897 call interaction%init_from_partner(partner%gr, partner%space, partner%namespace)
898 class default
899 message(1) = "Unsupported interaction."
900 call messages_fatal(1, namespace=partner%namespace)
901 end select
902
905
906 ! ---------------------------------------------------------
907 subroutine electrons_copy_quantities_to_interaction(partner, interaction)
908 class(electrons_t), intent(inout) :: partner
909 class(interaction_surrogate_t), intent(inout) :: interaction
910
912 call profiling_in(trim(partner%namespace%get())//":"//"COPY_QUANTITY_INTER")
913
914 select type (interaction)
916 assert(allocated(partner%st%current))
917 interaction%partner_field(:,:) = partner%st%current(1:partner%gr%np,:,1)
918 call interaction%do_mapping()
919 class default
920 message(1) = "Unsupported interaction."
921 call messages_fatal(1, namespace=partner%namespace)
922 end select
923
924 call profiling_out(trim(partner%namespace%get())//":"//"COPY_QUANTITY_INTER")
927
928 ! ---------------------------------------------------------
929 subroutine electrons_output_start(this)
930 class(electrons_t), intent(inout) :: this
931
932 push_sub(electrons_output_start)
933
935 end subroutine electrons_output_start
936
937 ! ---------------------------------------------------------
938 subroutine electrons_output_write(this)
939 class(electrons_t), intent(inout) :: this
940
941 integer :: iter
942
943 push_sub(electrons_output_write)
944 call profiling_in(trim(this%namespace%get())//":"//"OUTPUT_WRITE")
945
946 select type (algo => this%algo)
947 class is (propagator_t)
948 iter = this%iteration%counter()
949
950 call td_write_iter(this%td%write_handler, this%namespace, this%space, this%outp, this%gr, &
951 this%st, this%hm, this%ions, this%ext_partners, this%hm%kick, this%ks, algo%dt, iter, this%mc, &
952 this%td%recalculate_gs, this%dmp%adiabatic_st)
954 if (this%outp%anything_now(iter)) then ! output
955 call td_write_output(this%namespace, this%space, this%gr, this%st, this%hm, this%ks, &
956 this%outp, this%ions, this%ext_partners, iter, algo%dt)
957 end if
958 ! This is written as an exception to avoid modifying the args of `td_write_output`
959 ! TODO(Alex) Implement IO registry class
960 call this%wannier%write_iter(this%namespace, this%outp, this%ions, this%kpoints)
961 end select
962
963 call profiling_out(trim(this%namespace%get())//":"//"OUTPUT_WRITE")
965 end subroutine electrons_output_write
966
967 ! ---------------------------------------------------------
968 subroutine electrons_output_finish(this)
969 class(electrons_t), intent(inout) :: this
970
972
974 end subroutine electrons_output_finish
975
976 ! ---------------------------------------------------------
977 logical function electrons_process_is_slave(this) result(is_slave)
978 class(electrons_t), intent(in) :: this
979
981
982 is_slave = multicomm_is_slave(this%mc)
983
985 end function electrons_process_is_slave
986
987 ! ---------------------------------------------------------
988 subroutine electrons_exec_end_of_timestep_tasks(this, prop)
989 class(electrons_t), intent(inout) :: this
990 class(propagator_t), intent(in) :: prop
991
992 logical :: stopping
993 logical :: generate
994 logical :: update_energy_
995 integer :: nt
996 real(real64) :: time
997 type(gauge_field_t), pointer :: gfield
998
1000 call profiling_in(trim(this%namespace%get())//":"//"END_OF_TIMESTEP")
1001
1002 stopping = .false.
1003
1004 nt = this%td%iter
1005 ! this is the time at the end of the timestep, as required in all routines here
1006 time = prop%dt*nt
1007 update_energy_ = .true.
1008
1009 !Apply mask absorbing boundaries
1010 if (this%hm%abs_boundaries%abtype == mask_absorbing) call zvmask(this%gr, this%hm, this%st)
1011
1012 !Photoelectron stuff
1013 if (this%td%pesv%calc_spm .or. this%td%pesv%calc_mask .or. this%td%pesv%calc_flux) then
1014 call pes_calc(this%td%pesv, this%namespace, this%space, this%gr, this%st, &
1015 prop%dt, nt, this%gr%der, this%hm%kpoints, this%ext_partners, stopping)
1016 end if
1017
1018 ! For BOMD, we do not want the lines below to be executed
1019 select type(prop)
1020 type is(propagator_bomd_t)
1021 call profiling_out(trim(this%namespace%get())//":"//"END_OF_TIMESTEP")
1023 return
1024 end select
1025
1026 ! The propagation of the ions and the gauge field is currently done here.
1027 ! TODO: this code is to be moved to their own systems at some point
1028 generate = .false.
1029 if (this%td%ions_dyn%is_active()) then
1030 if (.not. this%ions_propagated) then
1031 call propagation_ops_elec_propagate_ions_and_cell(this%gr, this%hm, this%st, this%namespace, this%space, &
1032 this%td%ions_dyn, this%ions, this%mc, abs(nt*prop%dt), this%td%ions_dyn%ionic_scale*prop%dt)
1033 generate = .true.
1034 end if
1035 end if
1036
1037 gfield => list_get_gauge_field(this%ext_partners)
1038 if(associated(gfield)) then
1039 if (gauge_field_is_propagated(gfield) .and. .not. this%ions_propagated) then
1041 end if
1042 end if
1043
1044 if (generate .or. this%ions%has_time_dependent_species()) then
1045 call hamiltonian_elec_epot_generate(this%hm, this%namespace, this%space, this%gr, this%ions, &
1046 this%ext_partners, this%st, time = abs(nt*prop%dt))
1047 end if
1048
1049 call v_ks_calc(this%ks, this%namespace, this%space, this%hm, this%st, this%ions, this%ext_partners, &
1050 calc_eigenval = update_energy_, time = abs(nt*prop%dt), calc_energy = update_energy_)
1051
1052 if (update_energy_) then
1053 call energy_calc_total(this%namespace, this%space, this%hm, this%gr, this%st, this%ext_partners, iunit = -1)
1054 end if
1055
1056 ! Recalculate forces, update velocities...
1057 if (this%td%ions_dyn%ions_move() .or. this%outp%what(option__output__forces) &
1058 .or. this%td%write_handler%out(out_separate_forces)%write) then
1059 call forces_calculate(this%gr, this%namespace, this%ions, this%hm, this%ext_partners, &
1060 this%st, this%ks, t = abs(nt*prop%dt), dt = prop%dt)
1061 end if
1062
1063 if (this%td%ions_dyn%cell_relax() .or. this%outp%what(option__output__stress)) then
1064 call stress_calculate(this%namespace, this%gr, this%hm, this%st, this%ions, this%ks, this%ext_partners)
1065 end if
1066
1067 if(this%td%ions_dyn%is_active()) then
1068 call ion_dynamics_propagate_vel(this%td%ions_dyn, this%ions, atoms_moved = generate)
1069 call this%ions%update_kinetic_energy()
1070 end if
1071
1072 if(associated(gfield)) then
1073 if(gauge_field_is_propagated(gfield)) then
1074 call gauge_field_get_force(gfield, this%gr, this%st%d%spin_channels, this%st%current, this%ks%xc%lrc)
1076 end if
1077 end if
1078
1079 !We update the occupation matrices
1080 call lda_u_update_occ_matrices(this%hm%lda_u, this%namespace, this%gr, this%st, this%hm%phase, this%hm%energy)
1081
1082 !Update the wannier matrices
1083 call this%wannier%update_matrices(nt, this%namespace, this%gr, this%space, this%st, this%kpoints, &
1084 this%hm, prop%dt)
1085
1086 ! this is needed to be compatible with the code in td_*
1087 this%td%iter = this%td%iter + 1
1088
1089 call profiling_out(trim(this%namespace%get())//":"//"END_OF_TIMESTEP")
1092
1093 ! ---------------------------------------------------------
1094 subroutine electrons_restart_write_data(this)
1095 class(electrons_t), intent(inout) :: this
1096
1097 integer :: ierr
1098
1100 call profiling_in(trim(this%namespace%get())//":"//"RESTART_WRITE")
1101
1102 select type (algo => this%algo)
1103 class is (propagator_t)
1104 call td_write_data(this%td%write_handler)
1105 call td_dump(this%td, this%namespace, this%space, this%gr, this%st, this%hm, &
1106 this%ks, this%ext_partners, this%iteration%counter(), ierr)
1107 if (ierr /= 0) then
1108 message(1) = "Unable to write time-dependent restart information."
1109 call messages_warning(1, namespace=this%namespace)
1110 end if
1111
1112 ! TODO: this is here because of legacy reasons and should be moved to the output framework
1113 call pes_output(this%td%pesv, this%namespace, this%space, this%gr, this%st, this%iteration%counter(), &
1114 this%outp, algo%dt, this%ions)
1115
1116 if (this%wannier%options%td_method /= td_wannier_method_none) then
1117 call this%wannier%restart_write_data(this%namespace, this%mc, this%gr)
1118 end if
1119 end select
1120
1121 call profiling_out(trim(this%namespace%get())//":"//"RESTART_WRITE")
1123 end subroutine electrons_restart_write_data
1124
1125 ! ---------------------------------------------------------
1126 ! this function returns true if restart data could be read
1127 logical function electrons_restart_read_data(this)
1128 class(electrons_t), intent(inout) :: this
1129
1130 logical :: from_scratch
1131
1133 call profiling_in(trim(this%namespace%get())//":"//"RESTART_READ")
1134
1135 select type (algo => this%algo)
1136 class is (propagator_t)
1137 from_scratch = .false.
1138 call td_load_restart_from_td(this%td, this%namespace, this%space, this%mc, this%gr, &
1139 this%ext_partners, this%st, this%ks, this%hm, from_scratch)
1140
1141 if (.not. from_scratch .and. this%wannier%options%td_method /= td_wannier_method_none) then
1142 call this%wannier%restart_read_data(this%namespace, this%mc, this%gr)
1143 end if
1144
1145 call td_set_from_scratch(this%td, from_scratch)
1146
1147 class is (minimizer_algorithm_t)
1148 from_scratch = .false.
1149 call electrons_gs_load_from_restart(this%namespace, this%scf, this%gr, this%mc, this%st, this%hm, &
1150 this%ks, this%space, this%ions, this%ext_partners,from_scratch)
1151
1152 ! electrons_gs_initialize still knows about fromScratch.
1153 assert(.false.)
1154 end select
1155
1156 if (from_scratch) then
1157 ! restart data could not be loaded
1159 else
1160 ! restart data could be loaded
1162 end if
1163
1164 call profiling_out(trim(this%namespace%get())//":"//"RESTART_READ")
1166 end function electrons_restart_read_data
1167
1168 !----------------------------------------------------------
1169 subroutine electrons_update_kinetic_energy(this)
1170 class(electrons_t), intent(inout) :: this
1171
1173
1174 if (states_are_real(this%st)) then
1175 this%kinetic_energy = denergy_calc_electronic(this%namespace, this%hm, this%gr%der, this%st, terms = term_kinetic)
1176 else
1177 this%kinetic_energy = zenergy_calc_electronic(this%namespace, this%hm, this%gr%der, this%st, terms = term_kinetic)
1178 end if
1179
1181
1182 end subroutine electrons_update_kinetic_energy
1183
1184 ! ---------------------------------------------------------
1185 subroutine get_fields_from_interaction(this, time)
1186 class(electrons_t), intent(inout) :: this
1187 real(real64), intent(in) :: time
1188
1190 real(real64), allocatable :: field_tmp(:, :)
1191
1193
1194 if (this%hm%mxll%coupling_mode == no_maxwell_coupling) then
1196 return
1197 end if
1198
1199 assert(this%gr%box%dim == 3)
1200
1201 safe_allocate(field_tmp(1:this%gr%np, 1:this%gr%box%dim))
1202 this%hm%mxll%e_field = m_zero
1203 this%hm%mxll%b_field = m_zero
1204 this%hm%mxll%vec_pot = m_zero
1205
1206 ! interpolate field from interaction
1207 call iter%start(this%interactions)
1208 do while (iter%has_next())
1209 select type (interaction => iter%get_next())
1210 class is (mxll_e_field_to_matter_t)
1211 call interaction%interpolate(time, field_tmp)
1212 call lalg_axpy(this%gr%np, 3, m_one, field_tmp, this%hm%mxll%e_field)
1213 class is (mxll_vec_pot_to_matter_t)
1214 call interaction%interpolate(time, field_tmp)
1215 call lalg_axpy(this%gr%np, 3, m_one, field_tmp, this%hm%mxll%vec_pot)
1216 class is (mxll_b_field_to_matter_t)
1217 call interaction%interpolate(time, field_tmp)
1218 call lalg_axpy(this%gr%np, 3, m_one, field_tmp, this%hm%mxll%b_field)
1219 end select
1220 end do
1221
1222 safe_deallocate_a(field_tmp)
1224
1225 end subroutine get_fields_from_interaction
1226
1227
1229 subroutine electrons_ground_state_run_system(sys, from_scratch)
1230 class(electrons_t), intent(inout) :: sys
1231 logical, intent(inout) :: from_scratch
1232
1234
1235 call electrons_ground_state_run(sys%namespace, sys%mc, sys%gr, sys%ions, &
1236 sys%ext_partners, sys%st, sys%ks, sys%hm, sys%outp, sys%space, from_scratch)
1237
1239
1241
1242
1243 subroutine electrons_finalize(sys)
1244 type(electrons_t), intent(inout) :: sys
1245
1246 type(partner_iterator_t) :: iter
1247 class(interaction_partner_t), pointer :: partner
1248
1249 push_sub(electrons_finalize)
1250
1251 if (associated(sys%algo)) then
1252 select type (algo => sys%algo)
1253 class is (propagator_t)
1254 call td_end_run(sys%td, sys%st, sys%hm, sys%dmp)
1255 call td_end(sys%td)
1256 class is(minimizer_algorithm_t)
1257 call electrons_gs_cleanup(sys%ks, sys%scf, sys%rdm, sys%st, sys%hm)
1258 end select
1259 end if
1260
1261 if (sys%ks%theory_level /= independent_particles) then
1262 call poisson_async_end(sys%hm%psolver, sys%mc)
1263 end if
1265 call iter%start(sys%ext_partners)
1266 do while (iter%has_next())
1267 partner => iter%get_next()
1268 safe_deallocate_p(partner)
1269 end do
1270 call sys%ext_partners%empty()
1271
1272 safe_deallocate_p(sys%xc_interaction)
1273
1274 call hamiltonian_elec_end(sys%hm)
1275
1276 nullify(sys%gfield)
1277 nullify(sys%lasers)
1278
1279 call multicomm_end(sys%mc)
1281 call sys%dipole%end()
1282
1283 call v_ks_end(sys%ks)
1284
1285 call states_elec_end(sys%st)
1286
1287 deallocate(sys%ions)
1288 safe_deallocate_p(sys%photons)
1289
1290 call kpoints_end(sys%kpoints)
1291
1292 call grid_end(sys%gr)
1293
1294 call system_end(sys)
1295
1296 pop_sub(electrons_finalize)
1297 end subroutine electrons_finalize
1298
1299
1300end module electrons_oct_m
1301
1302!! Local Variables:
1303!! mode: f90
1304!! coding: utf-8
1305!! End:
constant times a vector plus a vector
Definition: lalg_basic.F90:194
integer, parameter, public mask_absorbing
This module defines the abstract interfact for algorithm factories.
This module implements the basic elements defining algorithms.
Definition: algorithm.F90:143
character(len=algo_label_len), parameter, public iteration_done
Definition: algorithm.F90:174
This module handles the calculation mode.
type(calc_mode_par_t), public calc_mode_par
Singleton instance of parallel calculation mode.
integer, parameter, public p_strategy_serial
single domain, all states, k-points on a single processor
integer, parameter, public p_strategy_states
parallelization in states
subroutine, public current_calculate(this, namespace, gr, hm, space, st)
Compute total electronic current density.
Definition: current.F90:372
subroutine, public current_init(this, namespace)
Definition: current.F90:180
This module implements a calculator for the density and defines related functions.
Definition: density.F90:122
This modules implements the dipole moment of the matter system.
Definition: dipole.F90:110
A set of subroutines for performing the parts of a ground state calculation with an electrons system....
subroutine, public electrons_ground_state_run(namespace, mc, gr, ions, ext_partners, st, ks, hm, outp, space, fromScratch)
Run a ground state calculation for a system of electrons.
subroutine, public electrons_gs_allocate_wavefunctions(namespace, gr, st, hm, scf, ks, ions)
subroutine, public electrons_gs_initialize(namespace, scf, rdm, gr, mc, st, hm, ions, ks, space, ext_partners, fromScratch)
subroutine, public electrons_gs_load_from_restart(namespace, scf, gr, mc, st, hm, ks, space, ions, ext_partners, fromScratch)
subroutine, public electrons_gs_cleanup(ks, scf, rdm, st, hm)
subroutine electrons_initialize(this)
Definition: electrons.F90:696
logical function electrons_restart_read_data(this)
Definition: electrons.F90:1223
logical function electrons_process_is_slave(this)
Definition: electrons.F90:1073
subroutine electrons_init_interaction(this, interaction)
Definition: electrons.F90:418
subroutine electrons_finalize(sys)
Definition: electrons.F90:1339
subroutine electrons_exec_end_of_timestep_tasks(this, prop)
Definition: electrons.F90:1084
logical function electrons_do_algorithmic_operation(this, operation, updated_quantities)
Definition: electrons.F90:742
subroutine electrons_new_algorithm(this, factory)
Definition: electrons.F90:663
subroutine electrons_output_write(this)
Definition: electrons.F90:1034
subroutine get_fields_from_interaction(this, time)
Definition: electrons.F90:1281
subroutine electrons_algorithm_start(this)
Definition: electrons.F90:722
subroutine electrons_output_finish(this)
Definition: electrons.F90:1064
subroutine electrons_output_start(this)
Definition: electrons.F90:1025
subroutine electrons_init_parallelization(this)
Definition: electrons.F90:482
subroutine electrons_init_interaction_as_partner(partner, interaction)
Definition: electrons.F90:985
subroutine electrons_ground_state_run_system(sys, from_scratch)
Run a ground state calculation for a system of electrons.
Definition: electrons.F90:1325
subroutine electrons_update_kinetic_energy(this)
Definition: electrons.F90:1265
logical function electrons_is_tolerance_reached(this, tol)
Definition: electrons.F90:942
class(electrons_t) function, pointer electrons_constructor(namespace, grp, calc_mode_id)
@ brief Instantiate an instance of an electrons system
Definition: electrons.F90:295
subroutine electrons_copy_quantities_to_interaction(partner, interaction)
Definition: electrons.F90:1003
subroutine electrons_restart_write_data(this)
Definition: electrons.F90:1190
subroutine electrons_update_quantity(this, label)
Definition: electrons.F90:954
subroutine, public elf_init(namespace)
Definition: elf.F90:146
subroutine, public energy_calc_total(namespace, space, hm, gr, st, ext_partners, iunit, full)
This subroutine calculates the total energy of the system. Basically, it adds up the KS eigenvalues,...
real(real64) function, public zenergy_calc_electronic(namespace, hm, der, st, terms)
real(real64) function, public denergy_calc_electronic(namespace, hm, der, st, terms)
type(gauge_field_t) function, pointer, public list_get_gauge_field(partners)
This module implements the field transfer.
subroutine, public forces_calculate(gr, namespace, ions, hm, ext_partners, st, ks, vhxc_old, t, dt)
Definition: forces.F90:341
subroutine, public gauge_field_get_force(this, gr, spin_channels, current, lrc)
subroutine, public gauge_field_do_algorithmic_operation(this, operation, dt, time)
subroutine, public gauge_field_check_symmetries(this, kpoints)
logical pure function, public gauge_field_is_propagated(this)
logical pure function, public gauge_field_is_used(this)
real(real64), parameter, public m_two
Definition: global.F90:202
real(real64), parameter, public m_zero
Definition: global.F90:200
integer, parameter, public independent_particles
Theory level.
Definition: global.F90:250
integer, parameter, public generalized_kohn_sham_dft
Definition: global.F90:250
integer, parameter, public kohn_sham_dft
Definition: global.F90:250
real(real64), parameter, public m_half
Definition: global.F90:206
real(real64), parameter, public m_one
Definition: global.F90:201
This module implements the underlying real-space grid.
Definition: grid.F90:119
subroutine, public grid_init_stage_1(gr, namespace, space, grp, symm, latt, n_sites, site_position, variable_cell)
First stage of the grid initialization.
Definition: grid.F90:197
subroutine, public grid_init_stage_2(gr, namespace, space, mc, qvector)
Second stage of the grid initialization.
Definition: grid.F90:483
subroutine, public grid_end(gr)
finalize a grid object
Definition: grid.F90:510
integer, parameter, public term_kinetic
subroutine, public zvmask(mesh, hm, st)
subroutine, public hamiltonian_elec_end(hm)
subroutine, public hamiltonian_elec_epot_generate(this, namespace, space, gr, ions, ext_partners, st, time)
subroutine, public hamiltonian_elec_init(hm, namespace, space, gr, ions, ext_partners, st, theory_level, xc, mc, kpoints, need_exchange, xc_photons)
integer, parameter, public mxll_vec_pot_to_matter
integer, parameter, public mxll_b_field_to_matter
integer, parameter, public mxll_e_field_to_matter
integer, parameter, public current_to_mxll_field
This module defines the abstract interaction_t class, and some auxiliary classes for interactions.
This module defines classes and functions for interaction partners.
subroutine, public ion_dynamics_propagate_vel(this, ions, atoms_moved)
subroutine, public kpoints_end(this)
Definition: kpoints.F90:1068
subroutine, public kpoints_init(this, namespace, symm, dim, periodic_dim, latt, grp)
Definition: kpoints.F90:419
subroutine, public kpoints_to_absolute(latt, kin, kout)
Definition: kpoints.F90:1147
A module to handle KS potential, without the external potential.
subroutine, public lasers_check_symmetries(this, kpoints)
Definition: lasers.F90:558
subroutine, public lasers_parse_external_fields(this)
Definition: lasers.F90:247
subroutine, public lasers_generate_potentials(this, mesh, space, latt)
Definition: lasers.F90:446
subroutine, public lda_u_update_occ_matrices(this, namespace, mesh, st, phase, energy)
Definition: lda_u.F90:894
System information (time, memory, sysname)
Definition: loct.F90:117
This module defines the meshes, which are used in Octopus.
Definition: mesh.F90:120
subroutine, public mesh_check_symmetries(mesh, symm, periodic_dim)
Definition: mesh.F90:844
integer function, public mesh_nearest_point(mesh, pos, dmin, rankmin)
Returns the index of the point which is nearest to a given vector position pos.
Definition: mesh.F90:391
real(real64) pure function, public mesh_global_memory(mesh)
Definition: mesh.F90:800
real(real64) pure function, public mesh_local_memory(mesh)
Definition: mesh.F90:811
subroutine, public messages_print_with_emphasis(msg, iunit, namespace)
Definition: messages.F90:898
character(len=512), private msg
Definition: messages.F90:167
subroutine, public messages_warning(no_lines, all_nodes, namespace)
Definition: messages.F90:525
subroutine, public messages_obsolete_variable(namespace, name, rep)
Definition: messages.F90:1000
subroutine, public messages_new_line()
Definition: messages.F90:1089
character(len=256), dimension(max_lines), public message
to be output by fatal, warning
Definition: messages.F90:162
subroutine, public messages_fatal(no_lines, only_root_writes, namespace)
Definition: messages.F90:410
subroutine, public messages_experimental(name, namespace)
Definition: messages.F90:1040
subroutine, public messages_info(no_lines, iunit, debug_only, stress, all_nodes, namespace)
Definition: messages.F90:594
This module implements the basic minimizer framework.
character(len=algo_label_len), parameter, public gs_scf_start
character(len=algo_label_len), parameter, public gs_scf_finish
character(len=algo_label_len), parameter, public gs_scf_iteration
general module for modelmb particles
This module handles the communicators for the various parallelization strategies.
Definition: multicomm.F90:147
subroutine, public multicomm_end(mc)
Definition: multicomm.F90:706
subroutine, public multicomm_init(mc, namespace, base_grp, mode_para, n_processes, index_range, min_range)
create index and domain communicators
Definition: multicomm.F90:273
logical pure function, public multicomm_is_slave(this)
Definition: multicomm.F90:846
integer, parameter, public length_gauge_dipole
integer, parameter, public no_maxwell_coupling
integer, parameter, public velocity_gauge_dipole
integer, parameter, public multipolar_expansion
integer, parameter, public full_minimal_coupling
Maxwell-field-to-matter interactions.
integer, parameter, public mxll_field_trans
this module contains the low-level part of the output system
Definition: output_low.F90:117
this module contains the output system
Definition: output.F90:117
logical function, public output_need_exchange(outp)
Definition: output.F90:859
subroutine, public output_init(outp, namespace, space, st, gr, nst, ks)
Definition: output.F90:207
logical function, public parse_is_defined(namespace, name)
Definition: parser.F90:463
integer function, public parse_block(namespace, name, blk, check_varinfo_)
Definition: parser.F90:623
subroutine, public pes_calc(pes, namespace, space, mesh, st, dt, iter, der, kpoints, ext_partners, stopping)
Definition: pes.F90:271
subroutine, public pes_output(pes, namespace, space, gr, st, iter, outp, dt, ions)
Definition: pes.F90:297
subroutine, public poisson_async_init(this, mc)
Definition: poisson.F90:1136
subroutine, public poisson_slave_work(this, namespace)
Definition: poisson.F90:1164
subroutine, public poisson_async_end(this, mc)
Definition: poisson.F90:1148
subroutine, public profiling_out(label)
Increment out counter and sum up difference between entry and exit time.
Definition: profiling.F90:668
subroutine, public profiling_in(label, exclude)
Increment in counter and save entry time.
Definition: profiling.F90:600
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_propagate_ions_and_cell(gr, hm, st, namespace, space, ions_dyn, ions, mc, time, dt_ions)
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, st_td)
Apply to all states, and accumulate the density in the same pass.
subroutine, public propagation_ops_elec_interpolate_get(hm, vks_old)
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 propagation_ops_elec_exp_apply(te, namespace, st, mesh, hm, dt, op)
character(len=algo_label_len), parameter, public aetrs_start
character(len=algo_label_len), parameter, public aetrs_finish
character(len=algo_label_len), parameter, public aetrs_extrapolate
character(len=algo_label_len), parameter, public aetrs_first_half
character(len=algo_label_len), parameter, public aetrs_second_half
character(len=algo_label_len), parameter, public bomd_start
character(len=algo_label_len), parameter, public bomd_elec_scf
character(len=algo_label_len), parameter, public bomd_finish
character(len=algo_label_len), parameter, public expmid_extrapolate
character(len=algo_label_len), parameter, public expmid_finish
character(len=algo_label_len), parameter, public expmid_start
character(len=algo_label_len), parameter, public expmid_propagate
This module implements the basic propagator framework.
Definition: propagator.F90:119
character(len=30), parameter, public verlet_compute_acc
type(algorithmic_operation_t), parameter, public op_verlet_compute_acc
character(len=30), parameter, public verlet_update_pos
type(algorithmic_operation_t), parameter, public op_verlet_compute_vel
character(len=30), parameter, public verlet_compute_vel
This module defines the quantity_t class and the IDs for quantities, which can be exposed by a system...
Definition: quantity.F90:140
Implementation details for regridding.
Definition: regridding.F90:172
subroutine, public scf_finish(scf, namespace, space, gr, ions, ext_partners, st, ks, hm, iter, outp)
Definition: scf.F90:1320
subroutine, public scf_start(scf, namespace, gr, ions, st, ks, hm, outp, verbosity)
Preparation of the SCF cycle.
Definition: scf.F90:713
integer, parameter, public verb_compact
Definition: scf.F90:206
subroutine, public scf_init(scf, namespace, gr, ions, st, mc, hm, space)
Definition: scf.F90:260
subroutine, public scf_end(scf)
Definition: scf.F90:577
subroutine, public scf_run(scf, namespace, space, mc, gr, ions, ext_partners, st, ks, hm, outp, verbosity, iters_done, restart_dump)
Legacy version of the SCF code.
Definition: scf.F90:858
subroutine, public scf_iter(scf, namespace, space, mc, gr, ions, ext_partners, st, ks, hm, iter, outp, restart_dump)
Definition: scf.F90:904
logical function, public scf_iter_finish(scf, namespace, space, gr, ions, st, ks, hm, iter, outp, iters_done)
Definition: scf.F90:1241
This module is intended to contain "only mathematical" functions and procedures.
Definition: sort.F90:119
pure logical function, public states_are_real(st)
This module handles spin dimensions of the states and the k-point distribution.
real(real64) function, public states_elec_wfns_memory(st, mesh)
return the memory usage of a states_elec_t object
subroutine, public states_elec_distribute_nodes(st, namespace, mc)
Distribute states over the processes for states parallelization.
subroutine, public states_elec_densities_init(st, gr)
subroutine, public states_elec_end(st)
finalize the states_elec_t object
subroutine, public kpoints_distribute(this, mc)
distribute k-points over the nodes in the corresponding communicator
subroutine, public states_elec_exec_init(st, namespace, mc)
Further initializations.
subroutine, public states_elec_init(st, namespace, space, valence_charge, kpoints, calc_mode_id)
Initialize a new states_elec_t object.
subroutine, public states_elec_allocate_current(st, space, mesh)
This module implements the calculation of the stress tensor.
Definition: stress.F90:120
subroutine, public stress_calculate(namespace, gr, hm, st, ions, ks, ext_partners)
This computes the total stress on the lattice.
Definition: stress.F90:188
subroutine, public symmetries_use_compatible_nonsymmorphic(this, ll, namespace)
Detect if some non-symmorphic operations are compatible with the real-space grid If yes,...
Definition: symmetries.F90:811
This module implements the abstract system type.
Definition: system.F90:120
subroutine, public system_algorithm_start(this)
Definition: system.F90:1023
subroutine, public system_end(this)
Definition: system.F90:1152
subroutine, public system_new_algorithm(this, factory)
Definition: system.F90:948
Definition: td.F90:116
subroutine, public td_init_with_wavefunctions(td, namespace, space, mc, gr, ions, ext_partners, st, ks, hm, outp, dmp, from_scratch)
Definition: td.F90:929
subroutine, public td_end(td)
Definition: td.F90:650
subroutine, public td_load_restart_from_gs(td, namespace, space, mc, gr, ext_partners, st, ks, hm)
Definition: td.F90:1250
subroutine, public td_allocate_wavefunctions(td, namespace, mc, gr, ions, st, hm, space)
Definition: td.F90:585
subroutine, public td_init(td, namespace, space, gr, ions, st, ks, hm, ext_partners, outp, dmp)
Definition: td.F90:239
logical function, public td_get_from_scratch(td)
Definition: td.F90:1585
subroutine, public td_set_from_scratch(td, from_scratch)
Definition: td.F90:1596
subroutine, public td_dump(td, namespace, space, gr, st, hm, ks, ext_partners, iter, ierr)
Definition: td.F90:1389
subroutine, public td_init_gaugefield(td, namespace, gr, st, ks, hm, ext_partners, space)
Definition: td.F90:619
subroutine, public td_load_restart_from_td(td, namespace, space, mc, gr, ext_partners, st, ks, hm, from_scratch)
Definition: td.F90:1214
subroutine, public td_end_run(td, st, hm, dmp)
Definition: td.F90:665
subroutine, public td_write_output(namespace, space, gr, st, hm, ks, outp, ions, ext_partners, iter, dt)
Definition: td_write.F90:1290
subroutine, public td_write_iter(writ, namespace, space, outp, gr, st, hm, ions, ext_partners, kick, ks, dt, iter, mc, recalculate_gs, dmp_st)
Definition: td_write.F90:1069
subroutine, public td_write_data(writ)
Definition: td_write.F90:1256
integer, parameter, public out_separate_forces
Definition: td_write.F90:204
This module defines the unit system, used for input and output.
type(unit_t), public unit_megabytes
For large amounts of data (natural code units are bytes)
subroutine, public v_ks_end(ks)
Definition: v_ks.F90:600
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:720
subroutine, public v_ks_init(ks, namespace, gr, st, ions, mc, space, kpoints)
Definition: v_ks.F90:252
Wannier module.
Definition: wannier.F90:120
Wannier options module.
integer, parameter, public td_wannier_method_none
Definition: xc.F90:120
integer, parameter, public oep_level_none
the OEP levels
Definition: xc_oep.F90:173
Abstract class for the algorithm factories.
Descriptor of one algorithmic operation.
Definition: algorithm.F90:165
Class to transfer a current to a Maxwell field.
Extension of space that contains the knowledge of the spin dimension.
Class describing the electron system.
Definition: electrons.F90:222
class defining the field_transfer interaction
These class extend the list and list iterator to make an interaction list.
abstract interaction class
abstract class for general interaction partners
surrogate interaction class to avoid circular dependencies between modules.
Abstract class implementing minimizers.
class to transfer a Maxwell B field to a matter system
class to transfer a Maxwell electric field to a medium
class to transfer a Maxwell vector potential to a medium
Implements a propagator for Approximate ETRS.
Implements a propagator for Born-Oppenheimer molecular dynamics.
Implements the explicit exponential midpoint propagator (without predictor-corrector)
Abstract class implementing propagators.
Definition: propagator.F90:144
Systems (system_t) can expose quantities that can be used to calculate interactions with other system...
Definition: quantity.F90:173
Abstract class for systems.
Definition: system.F90:175
Main object containing all Wannier-related data and methods.
Definition: wannier.F90:155
int true(void)