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