LCOV - code coverage report
Current view: top level - src - ec_environment.F (source / functions) Hit Total Coverage
Test: CP2K Regtests (git:4c33f95) Lines: 264 282 93.6 %
Date: 2025-01-30 06:53:08 Functions: 4 4 100.0 %

          Line data    Source code
       1             : !--------------------------------------------------------------------------------------------------!
       2             : !   CP2K: A general program to perform molecular dynamics simulations                              !
       3             : !   Copyright 2000-2025 CP2K developers group <https://cp2k.org>                                   !
       4             : !                                                                                                  !
       5             : !   SPDX-License-Identifier: GPL-2.0-or-later                                                      !
       6             : !--------------------------------------------------------------------------------------------------!
       7             : 
       8             : ! **************************************************************************************************
       9             : !> \brief Energy correction environment setup and handling
      10             : !> \par History
      11             : !>       2019.09 created
      12             : !> \author JGH
      13             : ! **************************************************************************************************
      14             : MODULE ec_environment
      15             :    USE atomic_kind_types,               ONLY: atomic_kind_type
      16             :    USE basis_set_container_types,       ONLY: add_basis_set_to_container,&
      17             :                                               remove_basis_from_container
      18             :    USE basis_set_types,                 ONLY: copy_gto_basis_set,&
      19             :                                               create_primitive_basis_set,&
      20             :                                               gto_basis_set_type
      21             :    USE bibliography,                    ONLY: Niklasson2003,&
      22             :                                               Niklasson2014,&
      23             :                                               cite_reference
      24             :    USE cp_control_types,                ONLY: dft_control_type
      25             :    USE cp_log_handling,                 ONLY: cp_get_default_logger,&
      26             :                                               cp_logger_get_default_unit_nr,&
      27             :                                               cp_logger_type
      28             :    USE dm_ls_scf_types,                 ONLY: ls_scf_env_type
      29             :    USE ec_env_types,                    ONLY: energy_correction_type
      30             :    USE input_constants,                 ONLY: &
      31             :         ec_diagonalization, ec_functional_dc, ec_functional_ext, ec_functional_harris, &
      32             :         ec_matrix_sign, ec_matrix_tc2, ec_matrix_trs4, ec_ot_atomic, ec_ot_diag, ec_ot_gs, &
      33             :         kg_cholesky, ls_cluster_atomic, ls_cluster_molecular, ls_s_inversion_hotelling, &
      34             :         ls_s_inversion_none, ls_s_inversion_sign_sqrt, ls_s_preconditioner_atomic, &
      35             :         ls_s_preconditioner_molecular, ls_s_preconditioner_none, ls_s_sqrt_ns, ls_s_sqrt_proot, &
      36             :         xc_vdw_fun_nonloc, xc_vdw_fun_pairpot
      37             :    USE input_cp2k_check,                ONLY: xc_functionals_expand
      38             :    USE input_section_types,             ONLY: section_get_ival,&
      39             :                                               section_vals_get,&
      40             :                                               section_vals_get_subs_vals,&
      41             :                                               section_vals_type,&
      42             :                                               section_vals_val_get
      43             :    USE kinds,                           ONLY: dp
      44             :    USE message_passing,                 ONLY: mp_para_env_type
      45             :    USE molecule_types,                  ONLY: molecule_of_atom,&
      46             :                                               molecule_type
      47             :    USE orbital_pointers,                ONLY: init_orbital_pointers
      48             :    USE particle_types,                  ONLY: particle_type
      49             :    USE qs_dispersion_nonloc,            ONLY: qs_dispersion_nonloc_init
      50             :    USE qs_dispersion_pairpot,           ONLY: qs_dispersion_pairpot_init
      51             :    USE qs_dispersion_types,             ONLY: qs_dispersion_type
      52             :    USE qs_dispersion_utils,             ONLY: qs_dispersion_env_set
      53             :    USE qs_environment_types,            ONLY: get_qs_env,&
      54             :                                               qs_environment_type
      55             :    USE qs_interactions,                 ONLY: init_interaction_radii_orb_basis
      56             :    USE qs_kind_types,                   ONLY: get_qs_kind,&
      57             :                                               get_qs_kind_set,&
      58             :                                               qs_kind_type
      59             :    USE qs_rho_types,                    ONLY: qs_rho_type
      60             :    USE string_utilities,                ONLY: uppercase
      61             :    USE xc,                              ONLY: xc_uses_kinetic_energy_density,&
      62             :                                               xc_uses_norm_drho
      63             :    USE xc_input_constants,              ONLY: xc_deriv_collocate
      64             : #include "./base/base_uses.f90"
      65             : 
      66             :    IMPLICIT NONE
      67             : 
      68             :    PRIVATE
      69             : 
      70             :    CHARACTER(len=*), PARAMETER, PRIVATE :: moduleN = 'ec_environment'
      71             : 
      72             :    PUBLIC :: ec_env_create
      73             :    PUBLIC :: ec_write_input
      74             : 
      75             : CONTAINS
      76             : 
      77             : ! **************************************************************************************************
      78             : !> \brief Allocates and intitializes ec_env
      79             : !> \param qs_env The QS environment
      80             : !> \param ec_env The energy correction environment (the object to create)
      81             : !> \param dft_section The DFT section
      82             : !> \param ec_section The energy correction input section
      83             : !> \par History
      84             : !>       2019.09 created
      85             : !> \author JGH
      86             : ! **************************************************************************************************
      87        7366 :    SUBROUTINE ec_env_create(qs_env, ec_env, dft_section, ec_section)
      88             :       TYPE(qs_environment_type), POINTER                 :: qs_env
      89             :       TYPE(energy_correction_type), POINTER              :: ec_env
      90             :       TYPE(section_vals_type), POINTER                   :: dft_section
      91             :       TYPE(section_vals_type), OPTIONAL, POINTER         :: ec_section
      92             : 
      93        7366 :       CPASSERT(.NOT. ASSOCIATED(ec_env))
      94      191516 :       ALLOCATE (ec_env)
      95        7366 :       CALL init_ec_env(qs_env, ec_env, dft_section, ec_section)
      96             : 
      97        7366 :    END SUBROUTINE ec_env_create
      98             : 
      99             : ! **************************************************************************************************
     100             : !> \brief Initializes energy correction environment
     101             : !> \param qs_env The QS environment
     102             : !> \param ec_env The energy correction environment
     103             : !> \param dft_section The DFT section
     104             : !> \param ec_section The energy correction input section
     105             : !> \par History
     106             : !>       2019.09 created
     107             : !> \author JGH
     108             : ! **************************************************************************************************
     109        7366 :    SUBROUTINE init_ec_env(qs_env, ec_env, dft_section, ec_section)
     110             :       TYPE(qs_environment_type), POINTER                 :: qs_env
     111             :       TYPE(energy_correction_type), POINTER              :: ec_env
     112             :       TYPE(section_vals_type), POINTER                   :: dft_section
     113             :       TYPE(section_vals_type), OPTIONAL, POINTER         :: ec_section
     114             : 
     115             :       CHARACTER(LEN=*), PARAMETER                        :: routineN = 'init_ec_env'
     116             : 
     117             :       INTEGER                                            :: handle, ikind, maxlgto, nkind, unit_nr
     118             :       LOGICAL                                            :: explicit
     119             :       REAL(KIND=dp)                                      :: eps_pgf_orb
     120        7366 :       TYPE(atomic_kind_type), DIMENSION(:), POINTER      :: atomic_kind_set
     121             :       TYPE(cp_logger_type), POINTER                      :: logger
     122             :       TYPE(dft_control_type), POINTER                    :: dft_control
     123             :       TYPE(gto_basis_set_type), POINTER                  :: basis_set, harris_basis
     124             :       TYPE(mp_para_env_type), POINTER                    :: para_env
     125             :       TYPE(qs_dispersion_type), POINTER                  :: dispersion_env
     126        7366 :       TYPE(qs_kind_type), DIMENSION(:), POINTER          :: qs_kind_set
     127             :       TYPE(qs_kind_type), POINTER                        :: qs_kind
     128             :       TYPE(qs_rho_type), POINTER                         :: rho
     129             :       TYPE(section_vals_type), POINTER                   :: ec_hfx_section, nl_section, pp_section, &
     130             :                                                             section1, section2, xc_fun_section, &
     131             :                                                             xc_section
     132             : 
     133        7366 :       CALL timeset(routineN, handle)
     134             : 
     135        7366 :       NULLIFY (atomic_kind_set, dispersion_env, ec_env%ls_env, para_env)
     136        7366 :       NULLIFY (ec_env%sab_orb, ec_env%sac_ppl, ec_env%sap_ppnl)
     137        7366 :       NULLIFY (ec_env%matrix_ks, ec_env%matrix_h, ec_env%matrix_s)
     138        7366 :       NULLIFY (ec_env%matrix_t, ec_env%matrix_p, ec_env%matrix_w)
     139        7366 :       NULLIFY (ec_env%task_list)
     140        7366 :       NULLIFY (ec_env%mao_coef)
     141        7366 :       NULLIFY (ec_env%force)
     142        7366 :       NULLIFY (ec_env%dispersion_env)
     143        7366 :       NULLIFY (ec_env%xc_section)
     144        7366 :       NULLIFY (ec_env%matrix_z)
     145        7366 :       NULLIFY (ec_env%matrix_hz)
     146        7366 :       NULLIFY (ec_env%matrix_wz)
     147        7366 :       NULLIFY (ec_env%z_admm)
     148        7366 :       NULLIFY (ec_env%p_env)
     149        7366 :       NULLIFY (ec_env%vxc_rspace)
     150        7366 :       NULLIFY (ec_env%vtau_rspace)
     151        7366 :       NULLIFY (ec_env%vadmm_rspace)
     152        7366 :       NULLIFY (ec_env%rhoout_r, ec_env%rhoz_r)
     153        7366 :       NULLIFY (ec_env%x_data)
     154        7366 :       ec_env%should_update = .TRUE.
     155        7366 :       ec_env%mao = .FALSE.
     156        7366 :       ec_env%do_ec_admm = .FALSE.
     157        7366 :       ec_env%do_ec_hfx = .FALSE.
     158        7366 :       ec_env%reuse_hfx = .FALSE.
     159             : 
     160        7366 :       IF (qs_env%energy_correction) THEN
     161             : 
     162         236 :          CPASSERT(PRESENT(ec_section))
     163             :          ! get a useful output_unit
     164         236 :          logger => cp_get_default_logger()
     165         236 :          IF (logger%para_env%is_source()) THEN
     166         118 :             unit_nr = cp_logger_get_default_unit_nr(logger, local=.TRUE.)
     167             :          ELSE
     168             :             unit_nr = -1
     169             :          END IF
     170             : 
     171             :          CALL section_vals_val_get(ec_section, "ALGORITHM", &
     172         236 :                                    i_val=ec_env%ks_solver)
     173             :          CALL section_vals_val_get(ec_section, "ENERGY_FUNCTIONAL", &
     174         236 :                                    i_val=ec_env%energy_functional)
     175             :          CALL section_vals_val_get(ec_section, "FACTORIZATION", &
     176         236 :                                    i_val=ec_env%factorization)
     177             :          CALL section_vals_val_get(ec_section, "OT_INITIAL_GUESS", &
     178         236 :                                    i_val=ec_env%ec_initial_guess)
     179             :          CALL section_vals_val_get(ec_section, "EPS_DEFAULT", &
     180         236 :                                    r_val=ec_env%eps_default)
     181             :          CALL section_vals_val_get(ec_section, "HARRIS_BASIS", &
     182         236 :                                    c_val=ec_env%basis)
     183             :          CALL section_vals_val_get(ec_section, "MAO", &
     184         236 :                                    l_val=ec_env%mao)
     185             :          CALL section_vals_val_get(ec_section, "MAO_MAX_ITER", &
     186         236 :                                    i_val=ec_env%mao_max_iter)
     187             :          CALL section_vals_val_get(ec_section, "MAO_EPS_GRAD", &
     188         236 :                                    r_val=ec_env%mao_eps_grad)
     189             :          CALL section_vals_val_get(ec_section, "MAO_EPS1", &
     190         236 :                                    r_val=ec_env%mao_eps1)
     191             :          CALL section_vals_val_get(ec_section, "MAO_IOLEVEL", &
     192         236 :                                    i_val=ec_env%mao_iolevel)
     193             :          ! Skip EC calculation if ground-state calculation did not converge
     194             :          CALL section_vals_val_get(ec_section, "SKIP_EC", &
     195         236 :                                    l_val=ec_env%skip_ec)
     196             :          ! Debug output
     197             :          CALL section_vals_val_get(ec_section, "DEBUG_FORCES", &
     198         236 :                                    l_val=ec_env%debug_forces)
     199             :          CALL section_vals_val_get(ec_section, "DEBUG_STRESS", &
     200         236 :                                    l_val=ec_env%debug_stress)
     201             :          CALL section_vals_val_get(ec_section, "DEBUG_EXTERNAL_METHOD", &
     202         236 :                                    l_val=ec_env%debug_external)
     203             :          ! ADMM
     204         236 :          CALL section_vals_val_get(ec_section, "ADMM", l_val=ec_env%do_ec_admm)
     205             :          ! EXTERNAL
     206             :          CALL section_vals_val_get(ec_section, "EXTERNAL_RESPONSE_FILENAME", &
     207         236 :                                    c_val=ec_env%exresp_fn)
     208             :          CALL section_vals_val_get(ec_section, "EXTERNAL_RESULT_FILENAME", &
     209         236 :                                    c_val=ec_env%exresult_fn)
     210             :          CALL section_vals_val_get(ec_section, "ERROR_ESTIMATION", &
     211         236 :                                    l_val=ec_env%do_error)
     212             : 
     213         236 :          ec_env%do_skip = .FALSE.
     214             : 
     215             :          ! set basis
     216         236 :          CALL get_qs_env(qs_env, qs_kind_set=qs_kind_set, nkind=nkind)
     217         236 :          CALL uppercase(ec_env%basis)
     218         384 :          SELECT CASE (ec_env%basis)
     219             :          CASE ("ORBITAL")
     220         316 :             DO ikind = 1, nkind
     221         168 :                qs_kind => qs_kind_set(ikind)
     222         168 :                CALL get_qs_kind(qs_kind=qs_kind, basis_set=basis_set, basis_type="ORB")
     223         316 :                IF (ASSOCIATED(basis_set)) THEN
     224         168 :                   NULLIFY (harris_basis)
     225         168 :                   CALL get_qs_kind(qs_kind=qs_kind, basis_set=harris_basis, basis_type="HARRIS")
     226         168 :                   IF (ASSOCIATED(harris_basis)) THEN
     227           6 :                      CALL remove_basis_from_container(qs_kind%basis_sets, basis_type="HARRIS")
     228             :                   END IF
     229         168 :                   NULLIFY (harris_basis)
     230         168 :                   CALL copy_gto_basis_set(basis_set, harris_basis)
     231         168 :                   CALL add_basis_set_to_container(qs_kind%basis_sets, harris_basis, "HARRIS")
     232             :                END IF
     233             :             END DO
     234             :          CASE ("PRIMITIVE")
     235           6 :             DO ikind = 1, nkind
     236           4 :                qs_kind => qs_kind_set(ikind)
     237           4 :                CALL get_qs_kind(qs_kind=qs_kind, basis_set=basis_set, basis_type="ORB")
     238           6 :                IF (ASSOCIATED(basis_set)) THEN
     239           4 :                   NULLIFY (harris_basis)
     240           4 :                   CALL get_qs_kind(qs_kind=qs_kind, basis_set=harris_basis, basis_type="HARRIS")
     241           4 :                   IF (ASSOCIATED(harris_basis)) THEN
     242           0 :                      CALL remove_basis_from_container(qs_kind%basis_sets, basis_type="HARRIS")
     243             :                   END IF
     244           4 :                   NULLIFY (harris_basis)
     245           4 :                   CALL create_primitive_basis_set(basis_set, harris_basis)
     246           4 :                   CALL get_qs_env(qs_env, dft_control=dft_control)
     247           4 :                   eps_pgf_orb = dft_control%qs_control%eps_pgf_orb
     248           4 :                   CALL init_interaction_radii_orb_basis(harris_basis, eps_pgf_orb)
     249           4 :                   harris_basis%kind_radius = basis_set%kind_radius
     250           4 :                   CALL add_basis_set_to_container(qs_kind%basis_sets, harris_basis, "HARRIS")
     251             :                END IF
     252             :             END DO
     253             :          CASE ("HARRIS")
     254         212 :             DO ikind = 1, nkind
     255         126 :                qs_kind => qs_kind_set(ikind)
     256         126 :                NULLIFY (harris_basis)
     257         126 :                CALL get_qs_kind(qs_kind=qs_kind, basis_set=harris_basis, basis_type="HARRIS")
     258         212 :                IF (.NOT. ASSOCIATED(harris_basis)) THEN
     259           0 :                   CPWARN("Harris Basis not defined for all types of atoms.")
     260             :                END IF
     261             :             END DO
     262             :          CASE DEFAULT
     263         236 :             CPABORT("Unknown basis set for energy correction (Harris functional)")
     264             :          END SELECT
     265             :          !
     266         236 :          CALL get_qs_kind_set(qs_kind_set, maxlgto=maxlgto, basis_type="HARRIS")
     267         236 :          CALL init_orbital_pointers(maxlgto + 1)
     268             :          !
     269         236 :          CALL uppercase(ec_env%basis)
     270             : 
     271             :          ! Basis may only differ from ground-state if explicitly added
     272         236 :          ec_env%basis_inconsistent = .FALSE.
     273         236 :          IF (ec_env%basis == "HARRIS") THEN
     274         212 :             DO ikind = 1, nkind
     275         126 :                qs_kind => qs_kind_set(ikind)
     276             :                ! Basis sets of ground-state
     277         126 :                CALL get_qs_kind(qs_kind=qs_kind, basis_set=basis_set, basis_type="ORB")
     278             :                ! Basis sets of energy correction
     279         126 :                CALL get_qs_kind(qs_kind=qs_kind, basis_set=harris_basis, basis_type="HARRIS")
     280             : 
     281         212 :                IF (basis_set%name .NE. harris_basis%name) THEN
     282          64 :                   ec_env%basis_inconsistent = .TRUE.
     283             :                END IF
     284             :             END DO
     285             :          END IF
     286             : 
     287             :          !Density-corrected DFT must be performed with the same basis as ground-state
     288         236 :          IF (ec_env%energy_functional == ec_functional_dc .AND. ec_env%basis_inconsistent) THEN
     289             :             CALL cp_abort(__LOCATION__, &
     290             :                           "DC-DFT: Correction and ground state need to use the same basis. "// &
     291           0 :                           "Checked by comparing basis set names only.")
     292             :          END IF
     293         236 :          IF (ec_env%energy_functional == ec_functional_ext .AND. ec_env%basis_inconsistent) THEN
     294             :             CALL cp_abort(__LOCATION__, &
     295             :                           "Exteranl Energy: Correction and ground state need to use the same basis. "// &
     296           0 :                           "Checked by comparing basis set names only.")
     297             :          END IF
     298             :          !
     299             :          ! set functional
     300         382 :          SELECT CASE (ec_env%energy_functional)
     301             :          CASE (ec_functional_harris)
     302         146 :             ec_env%ec_name = "Harris"
     303             :          CASE (ec_functional_dc)
     304          86 :             ec_env%ec_name = "DC-DFT"
     305             :          CASE (ec_functional_ext)
     306           4 :             ec_env%ec_name = "External Energy"
     307             :          CASE DEFAULT
     308         236 :             CPABORT("unknown energy correction")
     309             :          END SELECT
     310             :          ! select the XC section
     311         236 :          NULLIFY (xc_section)
     312         236 :          xc_section => section_vals_get_subs_vals(dft_section, "XC")
     313         236 :          section1 => section_vals_get_subs_vals(ec_section, "XC")
     314         236 :          section2 => section_vals_get_subs_vals(ec_section, "XC%XC_FUNCTIONAL")
     315         236 :          CALL section_vals_get(section2, explicit=explicit)
     316         236 :          IF (explicit) THEN
     317         232 :             CALL xc_functionals_expand(section2, section1)
     318         232 :             ec_env%xc_section => section1
     319             :          ELSE
     320           4 :             ec_env%xc_section => xc_section
     321             :          END IF
     322             :          ! Check whether energy correction requires the kinetic energy density and rebuild rho if necessary
     323         236 :          CALL get_qs_env(qs_env, dft_control=dft_control, rho=rho)
     324         236 :          xc_fun_section => section_vals_get_subs_vals(ec_env%xc_section, "XC_FUNCTIONAL")
     325             :          dft_control%use_kinetic_energy_density = dft_control%use_kinetic_energy_density .OR. &
     326         236 :                                                   xc_uses_kinetic_energy_density(xc_fun_section, dft_control%lsd)
     327             :          ! Same for density gradient
     328             :          dft_control%drho_by_collocation = dft_control%drho_by_collocation .OR. &
     329             :                                            (xc_uses_norm_drho(xc_fun_section, dft_control%lsd) .AND. &
     330         236 :                                             (section_get_ival(xc_section, "XC_GRID%XC_DERIV") == xc_deriv_collocate))
     331             :          ! dispersion
     332        1180 :          ALLOCATE (dispersion_env)
     333             :          NULLIFY (xc_section)
     334         236 :          xc_section => ec_env%xc_section
     335         236 :          CALL get_qs_env(qs_env, atomic_kind_set=atomic_kind_set, para_env=para_env)
     336         236 :          CALL qs_dispersion_env_set(dispersion_env, xc_section)
     337         236 :          IF (dispersion_env%type == xc_vdw_fun_pairpot) THEN
     338           0 :             NULLIFY (pp_section)
     339           0 :             pp_section => section_vals_get_subs_vals(xc_section, "VDW_POTENTIAL%PAIR_POTENTIAL")
     340           0 :             CALL qs_dispersion_pairpot_init(atomic_kind_set, qs_kind_set, dispersion_env, pp_section, para_env)
     341         236 :          ELSE IF (dispersion_env%type == xc_vdw_fun_nonloc) THEN
     342           0 :             CPABORT("nl-vdW functionals not available for EC calculations")
     343           0 :             NULLIFY (nl_section)
     344           0 :             nl_section => section_vals_get_subs_vals(xc_section, "VDW_POTENTIAL%NON_LOCAL")
     345           0 :             CALL qs_dispersion_nonloc_init(dispersion_env, para_env)
     346             :          END IF
     347         236 :          ec_env%dispersion_env => dispersion_env
     348             : 
     349             :          ! Check if hybrid functional are used
     350         236 :          ec_hfx_section => section_vals_get_subs_vals(ec_section, "XC%HF")
     351         236 :          CALL section_vals_get(ec_hfx_section, explicit=ec_env%do_ec_hfx)
     352             : 
     353             :          ! Initialize Harris LS solver environment
     354         236 :          ec_env%use_ls_solver = .FALSE.
     355             :          ec_env%use_ls_solver = (ec_env%ks_solver .EQ. ec_matrix_sign) &
     356             :                                 .OR. (ec_env%ks_solver .EQ. ec_matrix_trs4) &
     357         236 :                                 .OR. (ec_env%ks_solver .EQ. ec_matrix_tc2)
     358             : 
     359         236 :          IF (ec_env%use_ls_solver) THEN
     360          22 :             CALL ec_ls_create(qs_env, ec_env)
     361             :          END IF
     362             : 
     363             :       END IF
     364             : 
     365        7366 :       CALL timestop(handle)
     366             : 
     367        7366 :    END SUBROUTINE init_ec_env
     368             : 
     369             : ! **************************************************************************************************
     370             : !> \brief Initializes linear scaling environment for LS based solver of
     371             : !>        Harris energy functional and parses input section
     372             : !> \param qs_env ...
     373             : !> \param ec_env ...
     374             : !> \par History
     375             : !>       2020.10 created [Fabian Belleflamme]
     376             : !> \author Fabian Belleflamme
     377             : ! **************************************************************************************************
     378          22 :    SUBROUTINE ec_ls_create(qs_env, ec_env)
     379             :       TYPE(qs_environment_type), POINTER                 :: qs_env
     380             :       TYPE(energy_correction_type), POINTER              :: ec_env
     381             : 
     382             :       CHARACTER(LEN=*), PARAMETER                        :: routineN = 'ec_ls_create'
     383             : 
     384             :       INTEGER                                            :: handle
     385             :       REAL(KIND=dp)                                      :: mu
     386             :       TYPE(dft_control_type), POINTER                    :: dft_control
     387             :       TYPE(ls_scf_env_type), POINTER                     :: ls_env
     388          22 :       TYPE(molecule_type), DIMENSION(:), POINTER         :: molecule_set
     389          22 :       TYPE(particle_type), DIMENSION(:), POINTER         :: particle_set
     390             :       TYPE(section_vals_type), POINTER                   :: ec_section, input
     391             : 
     392          22 :       CALL timeset(routineN, handle)
     393             : 
     394         858 :       ALLOCATE (ec_env%ls_env)
     395          22 :       ls_env => ec_env%ls_env
     396             : 
     397          22 :       NULLIFY (dft_control, input, ls_env%para_env)
     398             : 
     399             :       CALL get_qs_env(qs_env, &
     400             :                       dft_control=dft_control, &
     401             :                       input=input, &
     402             :                       molecule_set=molecule_set, &
     403             :                       particle_set=particle_set, &
     404             :                       para_env=ls_env%para_env, &
     405          22 :                       nelectron_spin=ls_env%nelectron_spin)
     406             : 
     407             :       ! copy some basic stuff
     408          22 :       ls_env%nspins = dft_control%nspins
     409          22 :       ls_env%natoms = SIZE(particle_set, 1)
     410          22 :       CALL ls_env%para_env%retain()
     411             : 
     412             :       ! initialize block to group to defined molecules
     413          66 :       ALLOCATE (ls_env%ls_mstruct%atom_to_molecule(ls_env%natoms))
     414          22 :       CALL molecule_of_atom(molecule_set, atom_to_mol=ls_env%ls_mstruct%atom_to_molecule)
     415             : 
     416          22 :       ls_env%do_transport = .FALSE.
     417          22 :       ls_env%do_pao = .FALSE.
     418          22 :       ls_env%ls_mstruct%do_pao = ls_env%do_pao
     419          22 :       ls_env%do_pexsi = .FALSE.
     420          22 :       ls_env%has_unit_metric = .FALSE.
     421             : 
     422          22 :       ec_section => section_vals_get_subs_vals(input, "DFT%ENERGY_CORRECTION")
     423          22 :       CALL section_vals_val_get(ec_section, "EPS_FILTER", r_val=ls_env%eps_filter)
     424          22 :       CALL section_vals_val_get(ec_section, "MU", r_val=mu)
     425          22 :       CALL section_vals_val_get(ec_section, "FIXED_MU", l_val=ls_env%fixed_mu)
     426          66 :       ls_env%mu_spin = mu
     427          22 :       CALL section_vals_val_get(ec_section, "S_PRECONDITIONER", i_val=ls_env%s_preconditioner_type)
     428          22 :       CALL section_vals_val_get(ec_section, "MATRIX_CLUSTER_TYPE", i_val=ls_env%ls_mstruct%cluster_type)
     429          22 :       CALL section_vals_val_get(ec_section, "S_INVERSION", i_val=ls_env%s_inversion_type)
     430          22 :       CALL section_vals_val_get(ec_section, "CHECK_S_INV", l_val=ls_env%check_s_inv)
     431          22 :       CALL section_vals_val_get(ec_section, "REPORT_ALL_SPARSITIES", l_val=ls_env%report_all_sparsities)
     432          22 :       CALL section_vals_val_get(ec_section, "SIGN_METHOD", i_val=ls_env%sign_method)
     433          22 :       CALL section_vals_val_get(ec_section, "SIGN_ORDER", i_val=ls_env%sign_order)
     434          22 :       CALL section_vals_val_get(ec_section, "DYNAMIC_THRESHOLD", l_val=ls_env%dynamic_threshold)
     435          22 :       CALL section_vals_val_get(ec_section, "NON_MONOTONIC", l_val=ls_env%non_monotonic)
     436          22 :       CALL section_vals_val_get(ec_section, "S_SQRT_METHOD", i_val=ls_env%s_sqrt_method)
     437          22 :       CALL section_vals_val_get(ec_section, "S_SQRT_ORDER", i_val=ls_env%s_sqrt_order)
     438          22 :       CALL section_vals_val_get(ec_section, "EPS_LANCZOS", r_val=ls_env%eps_lanczos)
     439          22 :       CALL section_vals_val_get(ec_section, "MAX_ITER_LANCZOS", i_val=ls_env%max_iter_lanczos)
     440             : 
     441          24 :       SELECT CASE (ec_env%ks_solver)
     442             :       CASE (ec_matrix_sign)
     443             :          ! S inverse required for Sign matrix algorithm,
     444             :          ! calculated either by Hotelling or multiplying S matrix sqrt inv
     445          24 :          SELECT CASE (ls_env%s_inversion_type)
     446             :          CASE (ls_s_inversion_sign_sqrt)
     447           2 :             ls_env%needs_s_inv = .TRUE.
     448           2 :             ls_env%use_s_sqrt = .TRUE.
     449             :          CASE (ls_s_inversion_hotelling)
     450           0 :             ls_env%needs_s_inv = .TRUE.
     451           0 :             ls_env%use_s_sqrt = .FALSE.
     452             :          CASE (ls_s_inversion_none)
     453           0 :             ls_env%needs_s_inv = .FALSE.
     454           0 :             ls_env%use_s_sqrt = .FALSE.
     455             :          CASE DEFAULT
     456           2 :             CPABORT("")
     457             :          END SELECT
     458             :       CASE (ec_matrix_trs4, ec_matrix_tc2)
     459          20 :          ls_env%needs_s_inv = .FALSE.
     460          20 :          ls_env%use_s_sqrt = .TRUE.
     461             :       CASE DEFAULT
     462          22 :          CPABORT("")
     463             :       END SELECT
     464             : 
     465          22 :       SELECT CASE (ls_env%s_preconditioner_type)
     466             :       CASE (ls_s_preconditioner_none)
     467           0 :          ls_env%has_s_preconditioner = .FALSE.
     468             :       CASE DEFAULT
     469          22 :          ls_env%has_s_preconditioner = .TRUE.
     470             :       END SELECT
     471             : 
     472             :       ! buffer for the history of matrices, not needed here
     473          22 :       ls_env%extrapolation_order = 0
     474          22 :       ls_env%scf_history%nstore = 0
     475          22 :       ls_env%scf_history%istore = 0
     476          44 :       ALLOCATE (ls_env%scf_history%matrix(ls_env%nspins, ls_env%scf_history%nstore))
     477             : 
     478          22 :       NULLIFY (ls_env%mixing_store)
     479             : 
     480          22 :       CALL timestop(handle)
     481             : 
     482          44 :    END SUBROUTINE ec_ls_create
     483             : 
     484             : ! **************************************************************************************************
     485             : !> \brief Print out the energy correction input section
     486             : !>
     487             : !> \param ec_env ...
     488             : !> \par History
     489             : !>       2020.10 created [Fabian Belleflamme]
     490             : !> \author Fabian Belleflamme
     491             : ! **************************************************************************************************
     492         236 :    SUBROUTINE ec_write_input(ec_env)
     493             :       TYPE(energy_correction_type), POINTER              :: ec_env
     494             : 
     495             :       CHARACTER(LEN=*), PARAMETER                        :: routineN = 'ec_write_input'
     496             : 
     497             :       INTEGER                                            :: handle, unit_nr
     498             :       TYPE(cp_logger_type), POINTER                      :: logger
     499             :       TYPE(ls_scf_env_type), POINTER                     :: ls_env
     500             : 
     501         236 :       CALL timeset(routineN, handle)
     502             : 
     503         236 :       logger => cp_get_default_logger()
     504         236 :       IF (logger%para_env%is_source()) THEN
     505         118 :          unit_nr = cp_logger_get_default_unit_nr(logger, local=.TRUE.)
     506             :       ELSE
     507             :          unit_nr = -1
     508             :       END IF
     509             : 
     510         118 :       IF (unit_nr > 0) THEN
     511             : 
     512             :          WRITE (unit_nr, '(T2,A)') &
     513         118 :             "!"//REPEAT("-", 29)//" Energy Correction "//REPEAT("-", 29)//"!"
     514             : 
     515             :          ! Type of energy correction
     516         191 :          SELECT CASE (ec_env%energy_functional)
     517             :          CASE (ec_functional_harris)
     518          73 :             WRITE (unit_nr, '(T2,A,T61,A20)') "Energy Correction: ", "HARRIS FUNCTIONAL"
     519             :          CASE (ec_functional_dc)
     520          43 :             WRITE (unit_nr, '(T2,A,T61,A20)') "Energy Correction: ", "DC-DFT"
     521             :          CASE (ec_functional_ext)
     522         118 :             WRITE (unit_nr, '(T2,A,T61,A20)') "Energy Correction: ", "External"
     523             :          END SELECT
     524         118 :          WRITE (unit_nr, '()')
     525             : 
     526             :          ! Energy correction parameters
     527         118 :          WRITE (unit_nr, '(T2,A,T61,E20.3)') "eps_default:", ec_env%eps_default
     528             : 
     529         118 :          CALL uppercase(ec_env%basis)
     530         192 :          SELECT CASE (ec_env%basis)
     531             :          CASE ("ORBITAL")
     532          74 :             WRITE (unit_nr, '(T2,A,T61,A20)') "EC basis: ", "ORBITAL"
     533             :          CASE ("PRIMITIVE")
     534           1 :             WRITE (unit_nr, '(T2,A,T61,A20)') "EC basis: ", "PRIMITIVE"
     535             :          CASE ("HARRIS")
     536         118 :             WRITE (unit_nr, '(T2,A,T61,A20)') "EC Basis: ", "HARRIS"
     537             :          END SELECT
     538             : 
     539             :          ! Info how HFX in energy correction is treated
     540         118 :          IF (ec_env%do_ec_hfx) THEN
     541             : 
     542           8 :             WRITE (unit_nr, '(T2,A,T61,L20)') "DC-DFT with HFX", ec_env%do_ec_hfx
     543           8 :             WRITE (unit_nr, '(T2,A,T61,L20)') "Reuse HFX integrals", ec_env%reuse_hfx
     544           8 :             WRITE (unit_nr, '(T2,A,T61,L20)') "DC-DFT HFX with ADMM", ec_env%do_ec_admm
     545             : 
     546             :          END IF ! ec_env%do_ec_hfx
     547             : 
     548             :          ! Parameters for Harris functional solver
     549         118 :          IF (ec_env%energy_functional == ec_functional_harris) THEN
     550             : 
     551             :             ! Algorithm
     552         133 :             SELECT CASE (ec_env%ks_solver)
     553             :             CASE (ec_diagonalization)
     554          60 :                WRITE (unit_nr, '(T2,A,T61,A20)') "Algorithm: ", "DIAGONALIZATION"
     555             :             CASE (ec_ot_diag)
     556           2 :                WRITE (unit_nr, '(T2,A,T61,A20)') "Algorithm: ", "OT DIAGONALIZATION"
     557             :             CASE (ec_matrix_sign)
     558           1 :                WRITE (unit_nr, '(T2,A,T61,A20)') "Algorithm: ", "MATRIX_SIGN"
     559             :             CASE (ec_matrix_trs4)
     560           9 :                WRITE (unit_nr, '(T2,A,T61,A20)') "Algorithm: ", "TRS4"
     561           9 :                CALL cite_reference(Niklasson2003)
     562             :             CASE (ec_matrix_tc2)
     563           1 :                WRITE (unit_nr, '(T2,A,T61,A20)') "Algorithm: ", "TC2"
     564          74 :                CALL cite_reference(Niklasson2014)
     565             :             END SELECT
     566          73 :             WRITE (unit_nr, '()')
     567             : 
     568             :             ! MAO
     569          73 :             IF (ec_env%mao) THEN
     570           2 :                WRITE (unit_nr, '(T2,A,T61,L20)') "MAO:", ec_env%mao
     571           2 :                WRITE (unit_nr, '(T2,A,T61,L20)') "MAO_IOLEVEL:", ec_env%mao_iolevel
     572           2 :                WRITE (unit_nr, '(T2,A,T61,I20)') "MAO_MAX_ITER:", ec_env%mao_max_iter
     573           2 :                WRITE (unit_nr, '(T2,A,T61,E20.3)') "MAO_EPS_GRAD:", ec_env%mao_eps_grad
     574           2 :                WRITE (unit_nr, '(T2,A,T61,E20.3)') "MAO_EPS1:", ec_env%mao_eps1
     575           2 :                WRITE (unit_nr, '()')
     576             :             END IF
     577             : 
     578             :             ! Parameters for linear response solver
     579          73 :             IF (.NOT. ec_env%use_ls_solver) THEN
     580             : 
     581          62 :                WRITE (unit_nr, '(T2,A)') "MO Solver"
     582          62 :                WRITE (unit_nr, '()')
     583             : 
     584         122 :                SELECT CASE (ec_env%ks_solver)
     585             :                CASE (ec_diagonalization)
     586             : 
     587          60 :                   SELECT CASE (ec_env%factorization)
     588             :                   CASE (kg_cholesky)
     589          60 :                      WRITE (unit_nr, '(T2,A,T61,A20)') "Factorization: ", "CHOLESKY"
     590             :                   END SELECT
     591             : 
     592             :                CASE (ec_ot_diag)
     593             : 
     594             :                   ! OT Diagonalization
     595             :                   ! Initial guess : 1) block diagonal initial guess
     596             :                   !                 2) GS-density matrix (might require trafo if basis diff)
     597             : 
     598           2 :                   SELECT CASE (ec_env%ec_initial_guess)
     599             :                   CASE (ec_ot_atomic)
     600           1 :                      WRITE (unit_nr, '(T2,A,T61,A20)') "OT Diag initial guess: ", "ATOMIC"
     601             :                   CASE (ec_ot_gs)
     602           1 :                      WRITE (unit_nr, '(T2,A,T61,A20)') "OT Diag initial guess: ", "GROUND STATE DM"
     603             :                   END SELECT
     604             : 
     605             :                CASE DEFAULT
     606          62 :                   CPABORT("Unknown Diagonalization algorithm for Harris functional")
     607             :                END SELECT
     608             : 
     609             :             ELSE
     610             : 
     611          11 :                WRITE (unit_nr, '(T2,A)') "AO Solver"
     612          11 :                WRITE (unit_nr, '()')
     613             : 
     614          11 :                ls_env => ec_env%ls_env
     615          11 :                WRITE (unit_nr, '(T2,A,T61,E20.3)') "eps_filter:", ls_env%eps_filter
     616          11 :                WRITE (unit_nr, '(T2,A,T61,L20)') "fixed chemical potential (mu)", ls_env%fixed_mu
     617          11 :                WRITE (unit_nr, '(T2,A,T61,L20)') "Computing inv(S):", ls_env%needs_s_inv
     618          11 :                WRITE (unit_nr, '(T2,A,T61,L20)') "Computing sqrt(S):", ls_env%use_s_sqrt
     619          11 :                WRITE (unit_nr, '(T2,A,T61,L20)') "Computing S preconditioner ", ls_env%has_s_preconditioner
     620             : 
     621          11 :                IF (ls_env%use_s_sqrt) THEN
     622          21 :                   SELECT CASE (ls_env%s_sqrt_method)
     623             :                   CASE (ls_s_sqrt_ns)
     624          10 :                      WRITE (unit_nr, '(T2,A,T61,A20)') "S sqrt method:", "NEWTONSCHULZ"
     625             :                   CASE (ls_s_sqrt_proot)
     626           1 :                      WRITE (unit_nr, '(T2,A,T61,A20)') "S sqrt method:", "PROOT"
     627             :                   CASE DEFAULT
     628          11 :                      CPABORT("Unknown sqrt method.")
     629             :                   END SELECT
     630          11 :                   WRITE (unit_nr, '(T2,A,T61,I20)') "S sqrt order:", ls_env%s_sqrt_order
     631             :                END IF
     632             : 
     633          11 :                SELECT CASE (ls_env%s_preconditioner_type)
     634             :                CASE (ls_s_preconditioner_none)
     635           0 :                   WRITE (unit_nr, '(T2,A,T61,A20)') "S preconditioner type ", "NONE"
     636             :                CASE (ls_s_preconditioner_atomic)
     637          11 :                   WRITE (unit_nr, '(T2,A,T61,A20)') "S preconditioner type ", "ATOMIC"
     638             :                CASE (ls_s_preconditioner_molecular)
     639          11 :                   WRITE (unit_nr, '(T2,A,T61,A20)') "S preconditioner type ", "MOLECULAR"
     640             :                END SELECT
     641             : 
     642          22 :                SELECT CASE (ls_env%ls_mstruct%cluster_type)
     643             :                CASE (ls_cluster_atomic)
     644          11 :                   WRITE (unit_nr, '(T2,A,T61,A20)') "Cluster type", ADJUSTR("ATOMIC")
     645             :                CASE (ls_cluster_molecular)
     646           0 :                   WRITE (unit_nr, '(T2,A,T61,A20)') "Cluster type", ADJUSTR("MOLECULAR")
     647             :                CASE DEFAULT
     648          11 :                   CPABORT("Unknown cluster type")
     649             :                END SELECT
     650             : 
     651             :             END IF
     652             : 
     653             :          END IF ! if ec_functional_harris
     654             : 
     655         118 :          WRITE (unit_nr, '(T2,A)') REPEAT("-", 79)
     656         118 :          WRITE (unit_nr, '()')
     657             : 
     658             :       END IF ! unit_nr
     659             : 
     660         236 :       CALL timestop(handle)
     661             : 
     662         236 :    END SUBROUTINE ec_write_input
     663             : 
     664             : END MODULE ec_environment

Generated by: LCOV version 1.15