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
75 use output_oct_m
77 use parser_oct_m
78 use pes_oct_m
93 use rdmft_oct_m
95 use scf_oct_m
96 use space_oct_m
100 use stress_oct_m
101 use sort_oct_m
102 use system_oct_m
103 use td_oct_m
106 use v_ks_oct_m
107 use wannier_oct_m, only: wannier_t
109 use xc_oct_m
110 use xc_f03_lib_m
111 use xc_oep_oct_m
115
116 implicit none
117
118 private
119 public :: &
121
122
128 type, extends(system_t) :: electrons_t
129 ! Components are public by default
130 type(electron_space_t) :: space
131 class(ions_t), pointer :: ions => null()
132 type(photons_t), pointer :: photons => null()
133 type(grid_t) :: gr
134 type(states_elec_t) :: st
135 type(v_ks_t) :: ks
136 type(output_t) :: outp
137 type(multicomm_t) :: mc
138 type(hamiltonian_elec_t) :: hm
139 type(td_t) :: td
140 type(current_t) :: current_calculator
141 type(dipole_t) :: dipole
142 type(scf_t) :: scf
143 type(rdm_t) :: rdm
144
145 type(kpoints_t) :: kpoints
146
147 logical :: generate_epot
148
149 type(states_elec_t) :: st_copy
150
151 ! At the moment this is not treated as an external potential
152 class(lasers_t), pointer :: lasers => null()
153 class(gauge_field_t), pointer :: gfield => null()
154
155 ! List with all the external partners
156 ! This will become a list of interactions in the future
157 type(partner_list_t) :: ext_partners
158
159 !TODO: have a list of self interactions
160 type(xc_interaction_t), pointer :: xc_interaction => null()
161
162 type(dmp_t) :: dmp
163
164 logical :: ions_propagated = .false.
165
166 ! everything related to wannier functions
167 type(wannier_t) :: wannier
168
169 contains
170 procedure :: init_interaction => electrons_init_interaction
171 procedure :: new_algorithm => electrons_new_algorithm
172 procedure :: initialize => electrons_initialize
173 procedure :: do_algorithmic_operation => electrons_do_algorithmic_operation
174 procedure :: is_tolerance_reached => electrons_is_tolerance_reached
175 procedure :: update_quantity => electrons_update_quantity
176 procedure :: init_interaction_as_partner => electrons_init_interaction_as_partner
177 procedure :: copy_quantities_to_interaction => electrons_copy_quantities_to_interaction
178 procedure :: output_start => electrons_output_start
179 procedure :: output_write => electrons_output_write
180 procedure :: output_finish => electrons_output_finish
181 procedure :: process_is_slave => electrons_process_is_slave
182 procedure :: restart_write_data => electrons_restart_write_data
183 procedure :: restart_read_data => electrons_restart_read_data
184 procedure :: update_kinetic_energy => electrons_update_kinetic_energy
185 procedure :: algorithm_start => electrons_algorithm_start
186 procedure :: ground_state_run => electrons_ground_state_run_system
187 final :: electrons_finalize
188 end type electrons_t
189
190 interface electrons_t
191 procedure electrons_constructor
192 end interface electrons_t
193
194contains
195
200 function electrons_constructor(namespace, grp, calc_mode_id) result(sys)
201 class(electrons_t), pointer :: sys
202 type(namespace_t), intent(in) :: namespace
203 type(mpi_grp_t), intent(in) :: grp
204 integer, optional, intent(in) :: calc_mode_id
205
206 integer :: iatom
207 type(lattice_vectors_t) :: latt_inp
208 logical :: has_photons
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, latt_inp=latt_inp)
228 call grid_init_stage_1(sys%gr, sys%namespace, sys%space, sys%grp, sys%ions%symm, latt_inp, sys%ions%natoms, sys%ions%pos)
230 if (sys%space%is_periodic()) then
231 call sys%ions%latt%write_info(sys%namespace)
232 end if
234 ! Sanity check for atomic coordinates
235 do iatom = 1, sys%ions%natoms
236 ! Using the same tolerance of fold_into_cell to avoid problems with mixed periodicities
237 ! as the default tolerance of contains_point is too tight
238 if (.not. sys%gr%box%contains_point(sys%ions%pos(:, iatom), tol=1.0e-6_real64)) then
239 if (sys%space%periodic_dim /= sys%space%dim) then
240 write(message(1), '(a,i5,a)') "Atom ", iatom, " is outside the box."
241 call messages_warning(1, namespace=sys%namespace)
242 end if
243 end if
244 end do
245
246 ! we need k-points for periodic systems
247 call kpoints_init(sys%kpoints, sys%namespace, sys%gr%symm, sys%space%dim, sys%space%periodic_dim, sys%ions%latt)
249 call states_elec_init(sys%st, sys%namespace, sys%space, sys%ions%val_charge(), sys%kpoints, calc_mode_id)
250 call sys%st%write_info(sys%namespace)
251
252 ! if independent particles in N dimensions are being used, need to initialize them
253 ! after masses are set to 1 in grid_init_stage_1 -> derivatives_init
254 call sys%st%modelmbparticles%copy_masses(sys%gr%der%masses)
256 call elf_init(sys%namespace)
258 if (present(calc_mode_id)) then
259 sys%generate_epot = calc_mode_id /= option__calculationmode__dummy
260 else
261 sys%generate_epot = .true.
262 end if
263
264 call sys%dipole%init(sys%space)
266 sys%supported_interactions_as_partner = [current_to_mxll_field]
268 call sys%quantities%add(quantity_t("wavefunctions", updated_on_demand = .false.))
269 call sys%quantities%add(quantity_t("current", updated_on_demand = .true., parents=["wavefunctions"]))
270 call sys%quantities%add(quantity_t("dipole", updated_on_demand = .true., parents=["wavefunctions"]))
271 call current_init(sys%current_calculator, sys%namespace)
273 !%Variable EnablePhotons
274 !%Type logical
275 !%Default no
276 !%Section Hamiltonian
277 !%Description
278 !% This variable can be used to enable photons in several types of calculations.
279 !% It can be used to activate the one-photon OEP formalism.
280 !% In the case of CalculationMode = casida, it enables photon modes as
281 !% described in ACS Photonics 2019, 6, 11, 2757-2778.
282 !% Finally, if set to yes when solving the ferquency-dependent Sternheimer
283 !% equation, the photons are coupled to the electronic subsystem.
284 !%End
285 call messages_obsolete_variable(namespace, 'OEPPtX', 'EnablePhotons')
286 call parse_variable(namespace, 'EnablePhotons', .false., has_photons)
287 if (has_photons) then
288 call messages_experimental("EnablePhotons = yes")
289 sys%photons => photons_t(sys%namespace)
290 else
291 nullify(sys%photons)
292 end if
293
294 call sys%wannier%init_from_input(sys%namespace, sys%kpoints)
297
298 pop_sub_with_profile(electrons_constructor)
299 end function electrons_constructor
300
301 ! ---------------------------------------------------------
302 subroutine electrons_init_interaction(this, interaction)
303 class(electrons_t), target, intent(inout) :: this
304 class(interaction_t), intent(inout) :: interaction
305
306 real(real64) :: dmin
307 integer :: rankmin, depth
308 logical :: mxll_interaction_present
309 logical :: calc_dipole
310
311 push_sub(electrons_init_interactions)
312
313 mxll_interaction_present = .false.
314 select type (interaction)
316 call interaction%init(this%gr, 3)
317 mxll_interaction_present = .true.
318 interaction%type = mxll_field_trans
320 call interaction%init(this%gr, 3)
321 mxll_interaction_present = .true.
323 call interaction%init(this%gr, 3)
324 mxll_interaction_present = .true.
325 class default
326 message(1) = "Trying to initialize an unsupported interaction by the electrons."
327 call messages_fatal(1, namespace=this%namespace)
328 end select
329
330 if (mxll_interaction_present) then
331 calc_dipole = any(this%hm%mxll%coupling_mode == &
333
334 if (calc_dipole) then
335 assert(this%space%periodic_dim == 0)
336 this%hm%mxll%calc_field_dip = .true.
337 this%hm%mxll%center_of_mass(1:3) = this%ions%center_of_mass()
338 this%hm%mxll%center_of_mass_ip = mesh_nearest_point(this%gr, this%hm%mxll%center_of_mass, dmin, rankmin)
339 this%hm%mxll%center_of_mass_rankmin = rankmin
340 end if
341 end if
342
343 ! set interpolation depth for field-transfer interactions
344 select type (interaction)
345 class is (field_transfer_t)
346 ! interpolation depth depends on the propagator
347 select type (algo => this%algo)
348 type is (propagator_exp_mid_t)
349 depth = 3
350 type is (propagator_aetrs_t)
351 depth = 3
352 type is (propagator_bomd_t)
353 depth = 1
354 class default
355 message(1) = "The chosen algorithm does not yet support interaction interpolation"
356 call messages_fatal(1, namespace=this%namespace)
357 end select
358
359 call interaction%init_interpolation(depth, interaction%label)
360 end select
361
362 pop_sub(electrons_init_interactions)
363 end subroutine electrons_init_interaction
364
365 ! ---------------------------------------------------------
366 subroutine electrons_init_parallelization(this)
367 class(electrons_t), intent(inout) :: this
368
369 integer(int64) :: index_range(4)
370 real(real64) :: mesh_global, mesh_local, wfns
371 integer :: idir
372 real(real64) :: spiral_q(3), spiral_q_red(3)
373 type(block_t) :: blk
374
376
377 ! store the ranges for these two indices (serves as initial guess
378 ! for parallelization strategy)
379 index_range(1) = this%gr%np_global ! Number of points in mesh
380 index_range(2) = this%st%nst ! Number of states
381 index_range(3) = this%st%nik ! Number of k-points
382 index_range(4) = 100000 ! Some large number
383
384 ! create index and domain communicators
385 call multicomm_init(this%mc, this%namespace, this%grp, calc_mode_par, &
386 this%grp%size, index_range, (/ 5000, 1, 1, 1 /))
387
388 call this%ions%partition(this%mc)
389 call kpoints_distribute(this%st, this%mc)
390 call states_elec_distribute_nodes(this%st, this%namespace, this%mc)
391
392
393 if (parse_is_defined(this%namespace, 'TDMomentumTransfer') .or. &
394 parse_is_defined(this%namespace, 'TDReducedMomentumTransfer')) then
395 spiral_q = m_zero
396 if (parse_block(this%namespace, 'TDMomentumTransfer', blk) == 0) then
397 do idir = 1, this%space%dim
398 call parse_block_float(blk, 0, idir - 1, spiral_q(idir))
399 end do
400 else if(parse_block(this%namespace, 'TDReducedMomentumTransfer', blk) == 0) then
401 do idir = 1, this%space%dim
402 call parse_block_float(blk, 0, idir - 1, spiral_q_red(idir))
403 end do
404 call kpoints_to_absolute(this%kpoints%latt, spiral_q_red(1:this%space%dim), spiral_q(1:this%space%dim))
405 end if
406 call parse_block_end(blk)
407 call grid_init_stage_2(this%gr, this%namespace, this%space, this%mc, spiral_q)
408 else
409 call grid_init_stage_2(this%gr, this%namespace, this%space, this%mc)
410 end if
411
412 if (this%st%symmetrize_density) then
413 call mesh_check_symmetries(this%gr, this%gr%symm, this%ions%space%periodic_dim)
414 end if
415
416 call output_init(this%outp, this%namespace, this%space, this%st, this%gr, this%st%nst, this%ks)
417 call states_elec_densities_init(this%st, this%gr)
418 call states_elec_exec_init(this%st, this%namespace, this%mc)
419
420 if (associated(this%photons)) then
421 this%ks%has_photons = .true.
422 end if
423
424 call v_ks_init(this%ks, this%namespace, this%gr, this%st, this%ions, this%mc, this%space, this%kpoints)
425 if (this%ks%theory_level == kohn_sham_dft .or. this%ks%theory_level == generalized_kohn_sham_dft) then
426 this%xc_interaction => xc_interaction_t(this)
427 end if
428
429 ! For the moment the photons are initialized here
430
431 if(this%ks%has_photons) then
432 this%ks%pt => this%photons%modes
433 ! Temporary creation that should go in the system initialization later
434 call photon_mode_set_n_electrons(this%photons%modes, this%st%qtot)
435 write(message(1), '(a,i5,a)') 'Happy to have ', this%photons%modes%nmodes, ' photon modes with us.'
436 call messages_info(1)
437 call mf_init(this%ks%pt_mx, this%gr, this%st, this%ions, this%ks%pt)
438 ! OEP for photons
439 if(bitand(this%ks%xc_family, xc_family_oep) /= 0 .and. this%ks%xc%functional(func_x,1)%id == xc_oep_x) then
440 this%ks%oep_photon%level = this%ks%oep%level
441 call xc_oep_photon_init(this%ks%oep_photon, this%namespace, this%ks%xc_family, this%gr, this%st, this%mc, this%space)
442 else
443 this%ks%oep_photon%level = oep_level_none
444 end if
445
446 end if
447
448
449 ! Temporary place for the initialization of the lasers
450 this%lasers => lasers_t(this%namespace)
451 call lasers_parse_external_fields(this%lasers)
452 call lasers_generate_potentials(this%lasers, this%gr, this%space, this%ions%latt)
453 if(this%lasers%no_lasers > 0) then
454 call this%ext_partners%add(this%lasers)
455 call lasers_check_symmetries(this%lasers, this%kpoints)
456 else
457 deallocate(this%lasers)
458 end if
459
460 ! Temporary place for the initialization of the gauge field
461 this%gfield => gauge_field_t(this%namespace, this%ions%latt%rcell_volume)
462 if(gauge_field_is_used(this%gfield)) then
463 call this%ext_partners%add(this%gfield)
464 call gauge_field_check_symmetries(this%gfield, this%kpoints)
465 else
466 deallocate(this%gfield)
467 end if
468
469 call hamiltonian_elec_init(this%hm, this%namespace, this%space, this%gr, this%ions, this%ext_partners, &
470 this%st, this%ks%theory_level, this%ks%xc, this%mc, this%kpoints, &
471 need_exchange = output_need_exchange(this%outp) .or. this%ks%oep%level /= oep_level_none, &
472 xc_photons = this%ks%xc_photons )
473
474 if (this%hm%pcm%run_pcm .and. this%mc%par_strategy /= p_strategy_serial .and. this%mc%par_strategy /= p_strategy_states) then
475 call messages_experimental('Parallel in domain calculations with PCM')
476 end if
477
478 ! Print memory requirements
479 call messages_print_with_emphasis(msg='Approximate memory requirements', namespace=this%namespace)
480
481 mesh_global = mesh_global_memory(this%gr)
482 mesh_local = mesh_local_memory(this%gr)
483
484 call messages_write('Mesh')
485 call messages_new_line()
486 call messages_write(' global :')
487 call messages_write(mesh_global, units = unit_megabytes, fmt = '(f10.1)')
488 call messages_new_line()
489 call messages_write(' local :')
490 call messages_write(mesh_local, units = unit_megabytes, fmt = '(f10.1)')
491 call messages_new_line()
492 call messages_write(' total :')
493 call messages_write(mesh_global + mesh_local, units = unit_megabytes, fmt = '(f10.1)')
494 call messages_new_line()
495 call messages_info(namespace=this%namespace)
496
497 wfns = states_elec_wfns_memory(this%st, this%gr)
498 call messages_write('States')
499 call messages_new_line()
500 call messages_write(' real :')
501 call messages_write(wfns, units = unit_megabytes, fmt = '(f10.1)')
502 call messages_write(' (par_kpoints + par_states + par_domains)')
503 call messages_new_line()
504 call messages_write(' complex :')
505 call messages_write(2.0_8*wfns, units = unit_megabytes, fmt = '(f10.1)')
506 call messages_write(' (par_kpoints + par_states + par_domains)')
507 call messages_new_line()
508 call messages_info(namespace=this%namespace)
509
510 call messages_print_with_emphasis(namespace=this%namespace)
511
512 if (this%generate_epot) then
513 message(1) = "Info: Generating external potential"
514 call messages_info(1, namespace=this%namespace)
515 call hamiltonian_elec_epot_generate(this%hm, this%namespace, this%space, this%gr, this%ions, &
516 this%ext_partners, this%st)
517 message(1) = " done."
518 call messages_info(1, namespace=this%namespace)
519 end if
520
521 if (this%ks%theory_level /= independent_particles) then
522 call poisson_async_init(this%hm%psolver, this%mc)
523 ! slave nodes do not call the calculation routine
524 if (multicomm_is_slave(this%mc)) then
525 !for the moment we only have one type of slave
526 call poisson_slave_work(this%hm%psolver, this%namespace)
527 end if
528 end if
529
530 allocate(this%supported_interactions(0))
531 select case (this%hm%mxll%coupling_mode)
533 this%supported_interactions = [this%supported_interactions, mxll_e_field_to_matter]
535 this%supported_interactions = [this%supported_interactions, mxll_vec_pot_to_matter]
536 if (this%hm%mxll%add_zeeman) then
537 this%supported_interactions = [this%supported_interactions, mxll_b_field_to_matter]
538 end if
540 if (this%hm%mxll%add_electric_dip .or. this%hm%mxll%add_electric_quad) then
541 this%supported_interactions = [this%supported_interactions, mxll_e_field_to_matter]
542 end if
543 if (this%hm%mxll%add_magnetic_dip) then
544 this%supported_interactions = [this%supported_interactions, mxll_b_field_to_matter]
545 end if
547 ! Do not initialize any interaction with Maxwell
548 case default
549 message(1) = "Unknown maxwell-matter coupling"
550 call messages_fatal(1, namespace=this%namespace)
551 end select
552
553 call this%wannier%init_parallelization(this%namespace, this%st, this%ions, this%kpoints)
554
556 end subroutine electrons_init_parallelization
557
558 ! ---------------------------------------------------------
559 subroutine electrons_new_algorithm(this, factory)
560 class(electrons_t), intent(inout) :: this
561 class(algorithm_factory_t), intent(in) :: factory
562
564
565 call system_new_algorithm(this, factory)
566
567 select type (algo => this%algo)
568 class is (propagator_t)
569
570 call td_init(this%td, this%namespace, this%space, this%gr, this%ions, this%st, this%ks, &
571 this%hm, this%ext_partners, this%outp, this%dmp)
572
573 ! this corresponds to the first part of td_init_run
574 call td_allocate_wavefunctions(this%td, this%namespace, this%mc, this%gr, this%ions, this%st, &
575 this%hm, this%space)
576 call td_init_gaugefield(this%td, this%namespace, this%gr, this%st, this%ks, this%hm, &
577 this%ext_partners, this%space)
578
579 class is (minimizer_algorithm_t)
580
581 call electrons_gs_allocate_wavefunctions(this%namespace, this%gr, this%st, this%hm, this%scf, this%ks, &
582 this%ions)
583
584 class default
585 assert(.false.)
586 end select
587
589 end subroutine electrons_new_algorithm
590
591 ! ---------------------------------------------------------
592 subroutine electrons_initialize(this)
593 class(electrons_t), intent(inout) :: this
594
595 push_sub(electrons_initialize)
596
597 if (associated(this%ions)) call this%ions%initialize()
598
599 select type (algo => this%algo)
600 class is (propagator_t)
601 call td_set_from_scratch(this%td, .true.)
602 call td_load_restart_from_gs(this%td, this%namespace, this%space, this%mc, this%gr, &
603 this%ext_partners, this%st, this%ks, this%hm)
604 call this%wannier%init_data_from_file(this%kpoints, this%space)
605
606 class is (minimizer_algorithm_t)
607
608 call electrons_gs_initialize(this%namespace, this%scf, this%rdm, this%gr, this%mc, this%st, &
609 this%hm, this%ions, this%ks, this%space, this%ext_partners, fromscratch=.true.)
610 class default
611 assert(.false.)
612 end select
613
614 pop_sub(electrons_initialize)
615 end subroutine electrons_initialize
616
617 ! ---------------------------------------------------------
618 subroutine electrons_algorithm_start(this)
619 class(electrons_t), intent(inout) :: this
620
622
623 call system_algorithm_start(this)
624
625 select type (algo => this%algo)
626 class is (propagator_t)
627
628 ! additional initialization needed for electrons
629 call td_init_with_wavefunctions(this%td, this%namespace, this%space, this%mc, this%gr, this%ions, &
630 this%ext_partners, this%st, this%ks, this%hm, this%outp, this%dmp, td_get_from_scratch(this%td))
631
632 end select
633
635 end subroutine electrons_algorithm_start
636
637 ! ---------------------------------------------------------
638 logical function electrons_do_algorithmic_operation(this, operation, updated_quantities) result(done)
639 class(electrons_t), intent(inout) :: this
640 class(algorithmic_operation_t), intent(in) :: operation
641 character(len=:), allocatable, intent(out) :: updated_quantities(:)
642
643 logical :: update_energy_
644 type(gauge_field_t), pointer :: gfield
645 real(real64) :: time
646 integer :: iter
647
649 call profiling_in(trim(this%namespace%get())//":"//trim(operation%id))
650
651 update_energy_ = .true.
652
653 ! kick at t > 0 still missing!
655 done = .true.
656 select type (algo => this%algo)
657 class is (propagator_t)
658 time = algo%iteration%value()
659 select case (operation%id)
660 case (aetrs_first_half)
661 ! propagate half of the time step with H(time)
662 call get_fields_from_interaction(this, time)
663 call propagation_ops_elec_update_hamiltonian(this%namespace, this%space, this%st, this%gr, &
664 this%hm, this%ext_partners, time)
665 call propagation_ops_elec_exp_apply(this%td%tr%te, this%namespace, this%st, this%gr, this%hm, m_half*algo%dt)
666
667 case (aetrs_extrapolate)
668 ! Do the extrapolation of the Hamiltonian
669 ! First the extrapolation of the potential
670 call this%hm%ks_pot%interpolation_new(this%td%tr%vks_old, time+algo%dt, algo%dt)
671
672 !Get the potentials from the interpolator
673 call propagation_ops_elec_interpolate_get(this%hm, this%td%tr%vks_old)
674
675 ! Second the ions and gauge field which later on will be treated as extrapolation
676 ! of interactions, but this is not yet possible
677
678 ! move the ions to time t
679 call propagation_ops_elec_move_ions(this%td%tr%propagation_ops_elec, this%gr, this%hm, &
680 this%st, this%namespace, this%space, this%td%ions_dyn, this%ions, this%ext_partners, &
681 this%mc, time+algo%dt, algo%dt)
682
683 !Propagate gauge field
684 gfield => list_get_gauge_field(this%ext_partners)
685 if(associated(gfield)) then
686 call propagation_ops_elec_propagate_gauge_field(this%td%tr%propagation_ops_elec, gfield, &
687 algo%dt, time+algo%dt)
688 end if
689
690 !Update Hamiltonian and current
691 call get_fields_from_interaction(this, time+algo%dt)
692 call propagation_ops_elec_update_hamiltonian(this%namespace, this%space, this%st, this%gr, &
693 this%hm, this%ext_partners, time+algo%dt)
694
695 case (aetrs_second_half)
696 !Do the time propagation for the second half of the time step
697 call propagation_ops_elec_fuse_density_exp_apply(this%td%tr%te, this%namespace, this%st, &
698 this%gr, this%hm, m_half*algo%dt)
699
700 updated_quantities = ["wavefunctions"]
701
702 case (expmid_extrapolate)
703 ! the half step of this propagator screws with the gauge field kick
704 gfield => list_get_gauge_field(this%ext_partners)
705 if(associated(gfield)) then
706 assert(gauge_field_is_propagated(gfield) .eqv. .false.)
707 end if
708
709 ! Do the extrapolation of the Hamiltonian
710 ! First the extrapolation of the potential
711 call this%hm%ks_pot%interpolation_new(this%td%tr%vks_old, time+algo%dt, algo%dt)
712
713 ! get the potentials from the interpolator
714 call this%hm%ks_pot%interpolate_potentials(this%td%tr%vks_old, 3, time+algo%dt, algo%dt, time + algo%dt/m_two)
715
716 ! Second the ions which later on will be treated as extrapolation of interactions,
717 ! but this is not yet possible
718 ! move the ions to the half step
719 call propagation_ops_elec_move_ions(this%td%tr%propagation_ops_elec, this%gr, this%hm, this%st, &
720 this%namespace, this%space, this%td%ions_dyn, this%ions, this%ext_partners, &
721 this%mc, time + m_half*algo%dt, m_half*algo%dt, save_pos=.true.)
722
723 call get_fields_from_interaction(this, time + m_half*algo%dt)
724 call propagation_ops_elec_update_hamiltonian(this%namespace, this%space, this%st, this%gr, &
725 this%hm, this%ext_partners, time + m_half*algo%dt)
726
727 case (expmid_propagate)
728 ! Do the actual propagation step
729 call propagation_ops_elec_fuse_density_exp_apply(this%td%tr%te, this%namespace, this%st, &
730 this%gr, this%hm, algo%dt)
731
732 ! restore to previous time
733 call propagation_ops_elec_restore_ions(this%td%tr%propagation_ops_elec, this%td%ions_dyn, this%ions)
734
735 updated_quantities = ["wavefunctions"]
736
737 case (bomd_start)
738 call scf_init(this%scf, this%namespace, this%gr, this%ions, this%st, this%mc, this%hm, this%space)
739 ! the ions are propagated inside the propagation step already, so no need to do it at the end
740 this%ions_propagated = .true.
741
742 case (verlet_update_pos)
743 ! move the ions to time t
744 call propagation_ops_elec_propagate_ions_and_cell(this%gr, this%hm, this%st, this%namespace, this%space, &
745 this%td%ions_dyn, this%ions, this%mc, time+algo%dt, algo%dt)
746
747 case (bomd_elec_scf)
748 call hamiltonian_elec_epot_generate(this%hm, this%namespace, this%space, this%gr, this%ions, &
749 this%ext_partners, this%st, time = time+algo%dt)
750 ! now calculate the eigenfunctions
751 call scf_run(this%scf, this%namespace, this%space, this%mc, this%gr, this%ions, &
752 this%ext_partners, this%st, this%ks, this%hm, verbosity = verb_compact)
753 ! TODO: Check if this call is realy needed. - NTD
754 call hamiltonian_elec_epot_generate(this%hm, this%namespace, this%space, this%gr, this%ions, &
755 this%ext_partners, this%st, time = time+algo%dt)
756
757 ! update Hamiltonian and eigenvalues (fermi is *not* called)
758 call v_ks_calc(this%ks, this%namespace, this%space, this%hm, this%st, this%ions, this%ext_partners, &
759 calc_eigenval = .true., time = time+algo%dt, calc_energy = .true.)
760
761 ! Get the energies.
762 call energy_calc_total(this%namespace, this%space, this%hm, this%gr, this%st, this%ext_partners, iunit = -1)
763
764 updated_quantities = ["wavefunctions"]
765
766 case (verlet_compute_acc)
767 ! Do nothing, forces are computing in scf_run
768 if (this%td%ions_dyn%cell_relax()) then
769 assert(this%scf%calc_stress)
770 call this%td%ions_dyn%update_stress(this%ions%space, this%st%stress_tensors%total, &
771 this%ions%latt%rlattice, this%ions%latt%rcell_volume)
772 end if
773
774 case (verlet_compute_vel)
775 call ion_dynamics_propagate_vel(this%td%ions_dyn, this%ions)
776 ! TODO: Check if this call is realy needed. - NTD
777 call hamiltonian_elec_epot_generate(this%hm, this%namespace, this%space, this%gr, this%ions, &
778 this%ext_partners, this%st, time = time+algo%dt)
779 call this%ions%update_kinetic_energy()
780
781 case (expmid_start)
782 this%ions_propagated = .false.
783
784 case (aetrs_start)
785 ! the ions are propagated inside the propagation step already, so no need to do it at the end
786 this%ions_propagated = .true.
787
788 case (iteration_done)
790 done = .false.
791
792 case (bomd_finish)
793 call scf_end(this%scf)
794
796 case default
797 done = .false.
798 end select
799
800 class is(minimizer_algorithm_t)
801
802 ! Clocks starts at 0....
803 iter = nint(this%iteration%value()) + 1
804
805 select case(operation%id)
806 case (gs_scf_start)
807 call scf_start(this%scf, this%namespace, this%gr, this%ions, this%st, this%ks, this%hm, this%outp)
808
809 case (gs_scf_iteration)
810
811 call scf_iter(this%scf, this%namespace, this%space, this%mc, this%gr, this%ions, &
812 this%ext_partners, this%st, this%ks, this%hm, iter, outp = this%outp, &
813 restart_dump=this%scf%restart_dump)
814
815 algo%converged = scf_iter_finish(this%scf, this%namespace, this%space, this%gr, this%ions,&
816 this%st, this%ks, this%hm, iter, outp = this%outp)
817
818 updated_quantities = ["wavefunctions"]
819
820 case (gs_scf_finish)
821
822 ! Here iteration is iter-1, as the clock ticked before SCF_FINISH
823 call scf_finish(this%scf, this%namespace, this%space, this%gr, this%ions, &
824 this%ext_partners, this%st, this%ks, this%hm, iter-1, outp = this%outp)
825
826 case default
827 done = .false.
828 end select
829 class default
830 done = .false.
831 end select
832
833 call profiling_out(trim(this%namespace%get())//":"//trim(operation%id))
836
837 ! ---------------------------------------------------------
838 logical function electrons_is_tolerance_reached(this, tol) result(converged)
839 class(electrons_t), intent(in) :: this
840 real(real64), intent(in) :: tol
841
843
844 converged = .false.
845
848
849 ! ---------------------------------------------------------
850 subroutine electrons_update_quantity(this, label)
851 class(electrons_t), intent(inout) :: this
852 character(len=*), intent(in) :: label
853
854 class(quantity_t), pointer :: quantity
855
857 call profiling_in(trim(this%namespace%get())//":"//"UPDATE_QUANTITY")
858
859 quantity => this%quantities%get(label)
860 if(associated(quantity)) then
861 assert(quantity%updated_on_demand)
862 endif
863
864 select case (label)
865 case ("current")
866 call states_elec_allocate_current(this%st, this%space, this%gr)
867 call current_calculate(this%current_calculator, this%namespace, this%gr, &
868 this%hm, this%space, this%st)
869 case ("dipole")
870 call this%dipole%calculate(this%gr, this%ions, this%st)
871 case default
872 message(1) = "Incompatible quantity: "//trim(label)//"."
873 call messages_fatal(1, namespace=this%namespace)
874 end select
875
876 call profiling_out(trim(this%namespace%get())//":"//"UPDATE_QUANTITY")
878 end subroutine electrons_update_quantity
879
880 ! ---------------------------------------------------------
881 subroutine electrons_init_interaction_as_partner(partner, interaction)
882 class(electrons_t), intent(in) :: partner
883 class(interaction_surrogate_t), intent(inout) :: interaction
884
886
887 select type (interaction)
889 call interaction%init_from_partner(partner%gr, partner%space, partner%namespace)
890 class default
891 message(1) = "Unsupported interaction."
892 call messages_fatal(1, namespace=partner%namespace)
893 end select
894
897
898 ! ---------------------------------------------------------
899 subroutine electrons_copy_quantities_to_interaction(partner, interaction)
900 class(electrons_t), intent(inout) :: partner
901 class(interaction_surrogate_t), intent(inout) :: interaction
902
904 call profiling_in(trim(partner%namespace%get())//":"//"COPY_QUANTITY_INTER")
905
906 select type (interaction)
908 assert(allocated(partner%st%current))
909 interaction%partner_field(:,:) = partner%st%current(1:partner%gr%np,:,1)
910 call interaction%do_mapping()
911 class default
912 message(1) = "Unsupported interaction."
913 call messages_fatal(1, namespace=partner%namespace)
914 end select
915
916 call profiling_out(trim(partner%namespace%get())//":"//"COPY_QUANTITY_INTER")
919
920 ! ---------------------------------------------------------
921 subroutine electrons_output_start(this)
922 class(electrons_t), intent(inout) :: this
923
924 push_sub(electrons_output_start)
925
927 end subroutine electrons_output_start
928
929 ! ---------------------------------------------------------
930 subroutine electrons_output_write(this)
931 class(electrons_t), intent(inout) :: this
932
933 integer :: iter
934
935 push_sub(electrons_output_write)
936 call profiling_in(trim(this%namespace%get())//":"//"OUTPUT_WRITE")
937
938 select type (algo => this%algo)
939 class is (propagator_t)
940 iter = this%iteration%counter()
941
942 call td_write_iter(this%td%write_handler, this%namespace, this%space, this%outp, this%gr, &
943 this%st, this%hm, this%ions, this%ext_partners, this%hm%kick, this%ks, algo%dt, iter, this%mc, &
944 this%td%recalculate_gs, this%dmp%adiabatic_st)
946 if (this%outp%anything_now(iter)) then ! output
947 call td_write_output(this%namespace, this%space, this%gr, this%st, this%hm, this%ks, &
948 this%outp, this%ions, this%ext_partners, iter, algo%dt)
949 end if
950 ! This is written as an exception to avoid modifying the args of `td_write_output`
951 ! TODO(Alex) Implement IO registry class
952 if (this%wannier%options%td_method /= td_wannier_method_none) then
953 call this%wannier%write_iter(this%namespace, this%outp, iter, this%ions, this%kpoints)
954 end if
955 end select
956
957 call profiling_out(trim(this%namespace%get())//":"//"OUTPUT_WRITE")
959 end subroutine electrons_output_write
960
961 ! ---------------------------------------------------------
962 subroutine electrons_output_finish(this)
963 class(electrons_t), intent(inout) :: this
964
966
968 end subroutine electrons_output_finish
969
970 ! ---------------------------------------------------------
971 logical function electrons_process_is_slave(this) result(is_slave)
972 class(electrons_t), intent(in) :: this
973
975
976 is_slave = multicomm_is_slave(this%mc)
977
979 end function electrons_process_is_slave
980
981 ! ---------------------------------------------------------
982 subroutine electrons_exec_end_of_timestep_tasks(this, prop)
983 class(electrons_t), intent(inout) :: this
984 class(propagator_t), intent(in) :: prop
985
986 logical :: stopping
987 logical :: generate
988 logical :: update_energy_
989 integer :: nt
990 real(real64) :: time
991 type(gauge_field_t), pointer :: gfield
992
994 call profiling_in(trim(this%namespace%get())//":"//"END_OF_TIMESTEP")
995
996 stopping = .false.
997
998 nt = this%td%iter
999 ! this is the time at the end of the timestep, as required in all routines here
1000 time = prop%dt*nt
1001 update_energy_ = .true.
1002
1003 !Apply mask absorbing boundaries
1004 if (this%hm%abs_boundaries%abtype == mask_absorbing) call zvmask(this%gr, this%hm, this%st)
1005
1006 !Photoelectron stuff
1007 if (this%td%pesv%calc_spm .or. this%td%pesv%calc_mask .or. this%td%pesv%calc_flux) then
1008 call pes_calc(this%td%pesv, this%namespace, this%space, this%gr, this%st, &
1009 prop%dt, nt, this%gr%der, this%hm%kpoints, this%ext_partners, stopping)
1010 end if
1011
1012 ! For BOMD, we do not want the lines below to be executed
1013 select type(prop)
1014 type is(propagator_bomd_t)
1015 call profiling_out(trim(this%namespace%get())//":"//"END_OF_TIMESTEP")
1017 return
1018 end select
1019
1020 ! The propagation of the ions and the gauge field is currently done here.
1021 ! TODO: this code is to be moved to their own systems at some point
1022 generate = .false.
1023 if (this%td%ions_dyn%is_active()) then
1024 if (.not. this%ions_propagated) then
1025 call propagation_ops_elec_propagate_ions_and_cell(this%gr, this%hm, this%st, this%namespace, this%space, &
1026 this%td%ions_dyn, this%ions, this%mc, abs(nt*prop%dt), this%td%ions_dyn%ionic_scale*prop%dt)
1027 generate = .true.
1028 end if
1029 end if
1030
1031 gfield => list_get_gauge_field(this%ext_partners)
1032 if(associated(gfield)) then
1033 if (gauge_field_is_propagated(gfield) .and. .not. this%ions_propagated) then
1035 end if
1036 end if
1037
1038 if (generate .or. this%ions%has_time_dependent_species()) then
1039 call hamiltonian_elec_epot_generate(this%hm, this%namespace, this%space, this%gr, this%ions, &
1040 this%ext_partners, this%st, time = abs(nt*prop%dt))
1041 end if
1042
1043 call v_ks_calc(this%ks, this%namespace, this%space, this%hm, this%st, this%ions, this%ext_partners, &
1044 calc_eigenval = update_energy_, time = abs(nt*prop%dt), calc_energy = update_energy_)
1045
1046 if (update_energy_) then
1047 call energy_calc_total(this%namespace, this%space, this%hm, this%gr, this%st, this%ext_partners, iunit = -1)
1048 end if
1049
1050 ! Recalculate forces, update velocities...
1051 if (this%td%ions_dyn%ions_move() .or. this%outp%what(option__output__forces) &
1052 .or. this%td%write_handler%out(out_separate_forces)%write) then
1053 call forces_calculate(this%gr, this%namespace, this%ions, this%hm, this%ext_partners, &
1054 this%st, this%ks, t = abs(nt*prop%dt), dt = prop%dt)
1055 end if
1056
1057 if (this%td%ions_dyn%cell_relax() .or. this%outp%what(option__output__stress)) then
1058 call stress_calculate(this%namespace, this%gr, this%hm, this%st, this%ions, this%ks, this%ext_partners)
1059 end if
1060
1061 if(this%td%ions_dyn%is_active()) then
1062 call ion_dynamics_propagate_vel(this%td%ions_dyn, this%ions, atoms_moved = generate)
1063 call this%ions%update_kinetic_energy()
1064 end if
1065
1066 if(associated(gfield)) then
1067 if(gauge_field_is_propagated(gfield)) then
1068 call gauge_field_get_force(gfield, this%gr, this%st%d%spin_channels, this%st%current, this%ks%xc%lrc)
1070 end if
1071 end if
1072
1073 !We update the occupation matrices
1074 call lda_u_update_occ_matrices(this%hm%lda_u, this%namespace, this%gr, this%st, this%hm%phase, this%hm%energy)
1075
1076 ! this is needed to be compatible with the code in td_*
1077 this%td%iter = this%td%iter + 1
1078
1079 call profiling_out(trim(this%namespace%get())//":"//"END_OF_TIMESTEP")
1082
1083 ! ---------------------------------------------------------
1084 subroutine electrons_restart_write_data(this)
1085 class(electrons_t), intent(inout) :: this
1086
1087 integer :: ierr
1088
1090 call profiling_in(trim(this%namespace%get())//":"//"RESTART_WRITE")
1091
1092 select type (algo => this%algo)
1093 class is (propagator_t)
1094 call td_write_data(this%td%write_handler)
1095 call td_dump(this%td, this%namespace, this%space, this%gr, this%st, this%hm, &
1096 this%ks, this%ext_partners, this%iteration%counter(), ierr)
1097 if (ierr /= 0) then
1098 message(1) = "Unable to write time-dependent restart information."
1099 call messages_warning(1, namespace=this%namespace)
1100 end if
1101
1102 ! TODO: this is here because of legacy reasons and should be moved to the output framework
1103 call pes_output(this%td%pesv, this%namespace, this%space, this%gr, this%st, this%iteration%counter(), &
1104 this%outp, algo%dt, this%ions)
1105
1106 if (this%wannier%options%td_method /= td_wannier_method_none) then
1107 call this%wannier%restart_write_data(this%namespace, this%mc, this%gr)
1108 end if
1109 end select
1110
1111 call profiling_out(trim(this%namespace%get())//":"//"RESTART_WRITE")
1113 end subroutine electrons_restart_write_data
1114
1115 ! ---------------------------------------------------------
1116 ! this function returns true if restart data could be read
1117 logical function electrons_restart_read_data(this)
1118 class(electrons_t), intent(inout) :: this
1119
1120 logical :: from_scratch
1121
1123 call profiling_in(trim(this%namespace%get())//":"//"RESTART_READ")
1124
1125 select type (algo => this%algo)
1126 class is (propagator_t)
1127 from_scratch = .false.
1128 call td_load_restart_from_td(this%td, this%namespace, this%space, this%mc, this%gr, &
1129 this%ext_partners, this%st, this%ks, this%hm, from_scratch)
1130
1131 if (.not. from_scratch .and. this%wannier%options%td_method /= td_wannier_method_none) then
1132 call this%wannier%restart_read_data(this%namespace, this%mc, this%gr)
1133 end if
1134
1135 call td_set_from_scratch(this%td, from_scratch)
1136
1137 class is (minimizer_algorithm_t)
1138 from_scratch = .false.
1139 call electrons_gs_load_from_restart(this%namespace, this%scf, this%gr, this%mc, this%st, this%hm, &
1140 this%ks, this%space, this%ions, this%ext_partners,from_scratch)
1141
1142 ! electrons_gs_initialize still knows about fromScratch.
1143 assert(.false.)
1144 end select
1145
1146 if (from_scratch) then
1147 ! restart data could not be loaded
1149 else
1150 ! restart data could be loaded
1152 end if
1153
1154 call profiling_out(trim(this%namespace%get())//":"//"RESTART_READ")
1156 end function electrons_restart_read_data
1157
1158 !----------------------------------------------------------
1159 subroutine electrons_update_kinetic_energy(this)
1160 class(electrons_t), intent(inout) :: this
1161
1163
1164 if (states_are_real(this%st)) then
1165 this%kinetic_energy = denergy_calc_electronic(this%namespace, this%hm, this%gr%der, this%st, terms = term_kinetic)
1166 else
1167 this%kinetic_energy = zenergy_calc_electronic(this%namespace, this%hm, this%gr%der, this%st, terms = term_kinetic)
1168 end if
1169
1171
1172 end subroutine electrons_update_kinetic_energy
1173
1174 ! ---------------------------------------------------------
1175 subroutine get_fields_from_interaction(this, time)
1176 class(electrons_t), intent(inout) :: this
1177 real(real64), intent(in) :: time
1178
1180 real(real64), allocatable :: field_tmp(:, :)
1181
1183
1184 if (this%hm%mxll%coupling_mode == no_maxwell_coupling) then
1186 return
1187 end if
1188
1189 assert(this%gr%box%dim == 3)
1190
1191 safe_allocate(field_tmp(1:this%gr%np, 1:this%gr%box%dim))
1192 this%hm%mxll%e_field = m_zero
1193 this%hm%mxll%b_field = m_zero
1194 this%hm%mxll%vec_pot = m_zero
1195
1196 ! interpolate field from interaction
1197 call iter%start(this%interactions)
1198 do while (iter%has_next())
1199 select type (interaction => iter%get_next())
1200 class is (mxll_e_field_to_matter_t)
1201 call interaction%interpolate(time, field_tmp)
1202 call lalg_axpy(this%gr%np, 3, m_one, field_tmp, this%hm%mxll%e_field)
1203 class is (mxll_vec_pot_to_matter_t)
1204 call interaction%interpolate(time, field_tmp)
1205 call lalg_axpy(this%gr%np, 3, m_one, field_tmp, this%hm%mxll%vec_pot)
1206 class is (mxll_b_field_to_matter_t)
1207 call interaction%interpolate(time, field_tmp)
1208 call lalg_axpy(this%gr%np, 3, m_one, field_tmp, this%hm%mxll%b_field)
1209 end select
1210 end do
1211
1212 safe_deallocate_a(field_tmp)
1214
1215 end subroutine get_fields_from_interaction
1216
1217
1219 subroutine electrons_ground_state_run_system(sys, from_scratch)
1220 class(electrons_t), intent(inout) :: sys
1221 logical, intent(inout) :: from_scratch
1222
1224
1225 call electrons_ground_state_run(sys%namespace, sys%mc, sys%gr, sys%ions, &
1226 sys%ext_partners, sys%st, sys%ks, sys%hm, sys%outp, sys%space, from_scratch)
1227
1229
1231
1232
1233 subroutine electrons_finalize(sys)
1234 type(electrons_t), intent(inout) :: sys
1235
1236 type(partner_iterator_t) :: iter
1237 class(interaction_partner_t), pointer :: partner
1238
1239 push_sub(electrons_finalize)
1240
1241 if (associated(sys%algo)) then
1242 select type (algo => sys%algo)
1243 class is (propagator_t)
1244 call td_end_run(sys%td, sys%st, sys%hm, sys%dmp)
1245 call td_end(sys%td)
1246 class is(minimizer_algorithm_t)
1247 call electrons_gs_cleanup(sys%ks, sys%scf, sys%rdm, sys%st, sys%hm)
1248 end select
1249 end if
1250
1251 if (sys%ks%theory_level /= independent_particles) then
1252 call poisson_async_end(sys%hm%psolver, sys%mc)
1253 end if
1255 call iter%start(sys%ext_partners)
1256 do while (iter%has_next())
1257 partner => iter%get_next()
1258 safe_deallocate_p(partner)
1259 end do
1260 call sys%ext_partners%empty()
1261
1262 safe_deallocate_p(sys%xc_interaction)
1263
1264 call hamiltonian_elec_end(sys%hm)
1265
1266 nullify(sys%gfield)
1267 nullify(sys%lasers)
1268
1269 call multicomm_end(sys%mc)
1271 call xc_oep_photon_end(sys%ks%oep_photon)
1272 if (sys%ks%has_photons) then
1273 call mf_end(sys%ks%pt_mx)
1274 end if
1275
1276 call sys%dipole%end()
1277
1278 call v_ks_end(sys%ks)
1279
1280 call states_elec_end(sys%st)
1281
1282 deallocate(sys%ions)
1283 safe_deallocate_p(sys%photons)
1284
1285 call kpoints_end(sys%kpoints)
1286
1287 call grid_end(sys%gr)
1288
1289 call system_end(sys)
1290
1291 pop_sub(electrons_finalize)
1292 end subroutine electrons_finalize
1293
1294
1295end module electrons_oct_m
1296
1297!! Local Variables:
1298!! mode: f90
1299!! coding: utf-8
1300!! End:
constant times a vector plus a vector
Definition: lalg_basic.F90:173
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:688
logical function electrons_restart_read_data(this)
Definition: electrons.F90:1213
logical function electrons_process_is_slave(this)
Definition: electrons.F90:1067
subroutine electrons_init_interaction(this, interaction)
Definition: electrons.F90:398
subroutine electrons_finalize(sys)
Definition: electrons.F90:1329
subroutine electrons_exec_end_of_timestep_tasks(this, prop)
Definition: electrons.F90:1078
logical function electrons_do_algorithmic_operation(this, operation, updated_quantities)
Definition: electrons.F90:734
subroutine electrons_new_algorithm(this, factory)
Definition: electrons.F90:655
subroutine electrons_output_write(this)
Definition: electrons.F90:1026
subroutine get_fields_from_interaction(this, time)
Definition: electrons.F90:1271
subroutine electrons_algorithm_start(this)
Definition: electrons.F90:714
subroutine electrons_output_finish(this)
Definition: electrons.F90:1058
subroutine electrons_output_start(this)
Definition: electrons.F90:1017
subroutine electrons_init_parallelization(this)
Definition: electrons.F90:462
subroutine electrons_init_interaction_as_partner(partner, interaction)
Definition: electrons.F90:977
subroutine electrons_ground_state_run_system(sys, from_scratch)
Run a ground state calculation for a system of electrons.
Definition: electrons.F90:1315
subroutine electrons_update_kinetic_energy(this)
Definition: electrons.F90:1255
logical function electrons_is_tolerance_reached(this, tol)
Definition: electrons.F90:934
class(electrons_t) function, pointer electrons_constructor(namespace, grp, calc_mode_id)
@ brief Instantiate an instance of an electrons system
Definition: electrons.F90:296
subroutine electrons_copy_quantities_to_interaction(partner, interaction)
Definition: electrons.F90:995
subroutine electrons_restart_write_data(this)
Definition: electrons.F90:1180
subroutine electrons_update_quantity(this, label)
Definition: electrons.F90:946
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:340
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)
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:463
subroutine, public grid_end(gr)
finalize a grid object
Definition: grid.F90:490
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:1059
subroutine, public kpoints_init(this, namespace, symm, dim, periodic_dim, latt)
Definition: kpoints.F90:416
subroutine, public kpoints_to_absolute(latt, kin, kout)
Definition: kpoints.F90:1137
A module to handle KS potential, without the external potential.
subroutine, public lasers_check_symmetries(this, kpoints)
Definition: lasers.F90:557
subroutine, public lasers_parse_external_fields(this)
Definition: lasers.F90:246
subroutine, public lasers_generate_potentials(this, mesh, space, latt)
Definition: lasers.F90:445
subroutine, public lda_u_update_occ_matrices(this, namespace, mesh, st, phase, energy)
Definition: lda_u.F90:895
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:835
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:386
real(real64) pure function, public mesh_global_memory(mesh)
Definition: mesh.F90:791
real(real64) pure function, public mesh_local_memory(mesh)
Definition: mesh.F90:802
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
logical pure function, public multicomm_is_slave(this)
Definition: multicomm.F90:846
subroutine, public multicomm_init(mc, namespace, base_grp, mode_para, n_node, index_range, min_range)
create index and domain communicators
Definition: multicomm.F90:273
integer, parameter, public mxll_field_trans
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
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:879
subroutine, public output_init(outp, namespace, space, st, gr, nst, ks)
Definition: output.F90:211
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 mf_init(this, gr, st, ions, pt_mode)
subroutine, public mf_end(this)
subroutine, public photon_mode_set_n_electrons(this, qtot)
subroutine, public poisson_async_init(this, mc)
Definition: poisson.F90:1083
subroutine, public poisson_slave_work(this, namespace)
Definition: poisson.F90:1111
subroutine, public poisson_async_end(this, mc)
Definition: poisson.F90:1095
subroutine, public profiling_out(label)
Increment out counter and sum up difference between entry and exit time.
Definition: profiling.F90:631
subroutine, public profiling_in(label, exclude)
Increment in counter and save entry time.
Definition: profiling.F90:554
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_interpolate_get(hm, vks_old)
subroutine, public propagation_ops_elec_fuse_density_exp_apply(te, namespace, st, gr, hm, dt, dt2, op)
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:1296
subroutine, public scf_start(scf, namespace, gr, ions, st, ks, hm, outp, verbosity)
Preparation of the SCF cycle.
Definition: scf.F90:689
integer, parameter, public verb_compact
Definition: scf.F90:207
subroutine, public scf_init(scf, namespace, gr, ions, st, mc, hm, space)
Definition: scf.F90:260
subroutine, public scf_end(scf)
Definition: scf.F90:558
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:834
subroutine, public scf_iter(scf, namespace, space, mc, gr, ions, ext_partners, st, ks, hm, iter, outp, restart_dump)
Definition: scf.F90:880
logical function, public scf_iter_finish(scf, namespace, space, gr, ions, st, ks, hm, iter, outp, iters_done)
Definition: scf.F90:1217
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
This module implements the abstract system type.
Definition: system.F90:120
subroutine, public system_algorithm_start(this)
Definition: system.F90:1022
subroutine, public system_end(this)
Definition: system.F90:1151
subroutine, public system_new_algorithm(this, factory)
Definition: system.F90:947
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:1251
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:240
logical function, public td_get_from_scratch(td)
Definition: td.F90:1597
subroutine, public td_set_from_scratch(td, from_scratch)
Definition: td.F90:1608
subroutine, public td_dump(td, namespace, space, gr, st, hm, ks, ext_partners, iter, ierr)
Definition: td.F90:1384
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:1215
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:1286
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:1252
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:634
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:755
subroutine, public v_ks_init(ks, namespace, gr, st, ions, mc, space, kpoints)
Definition: v_ks.F90:257
Wannier module.
Definition: wannier.F90:108
Wannier options module.
integer, parameter, public td_wannier_method_none
integer, parameter, public xc_oep_x
Exact exchange.
integer, parameter, public func_x
Definition: xc.F90:120
integer, parameter, public oep_level_none
the OEP levels
Definition: xc_oep.F90:174
subroutine, public xc_oep_photon_init(oep, namespace, family, gr, st, mc, space)
subroutine, public xc_oep_photon_end(oep)
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:223
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 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:174
Main object containing all Wannier-related data and methods.
Definition: wannier.F90:151
int true(void)