(git:33f85d8)
Loading...
Searching...
No Matches
rpa_gw_sigma_x.F
Go to the documentation of this file.
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 Routines to calculate EXX within GW
10!> \par History
11!> 07.2020 separated from mp2.F [F. Stein, code by Jan Wilhelm]
12!> 07.2024 determine number of corrected MOs from BSE cutoffs [Maximilian Graml]
13!> \author Jan Wilhelm, Frederick Stein
14! **************************************************************************************************
17 USE admm_types, ONLY: admm_type,&
21 USE cp_cfm_types, ONLY: cp_cfm_create,&
26 USE cp_dbcsr_api, ONLY: &
28 dbcsr_release, dbcsr_release_p, dbcsr_set, dbcsr_type, dbcsr_type_antisymmetric, &
29 dbcsr_type_symmetric
36 USE cp_files, ONLY: close_file,&
39 USE cp_fm_types, ONLY: cp_fm_create,&
47 USE hfx_ri, ONLY: hfx_ri_update_ks
58 USE kinds, ONLY: dp
60 USE kpoint_types, ONLY: get_kpoint_info,&
63 USE machine, ONLY: m_walltime
64 USE mathconstants, ONLY: gaussi,&
65 z_one,&
66 z_zero
70 USE mp2_types, ONLY: mp2_type
72 USE physcon, ONLY: evolt
78 USE qs_mo_types, ONLY: get_mo_set,&
81 USE qs_rho_types, ONLY: qs_rho_get,&
86
87!$ USE OMP_LIB, ONLY: omp_get_max_threads, omp_get_thread_num, omp_get_num_threads
88
89#include "./base/base_uses.f90"
90
91 IMPLICIT NONE
92
93 PRIVATE
94
95 CHARACTER(len=*), PARAMETER, PRIVATE :: moduleN = 'rpa_gw_sigma_x'
96
98
99CONTAINS
100
101! **************************************************************************************************
102!> \brief ...
103!> \param qs_env ...
104!> \param mp2_env ...
105!> \param mos_mp2 ...
106!> \param energy_ex ...
107!> \param energy_xc_admm ...
108!> \param t3 ...
109!> \param unit_nr ...
110!> \par History
111!> 04.2015 created
112!> \author Jan Wilhelm
113! **************************************************************************************************
114 SUBROUTINE compute_vec_sigma_x_minus_vxc_gw(qs_env, mp2_env, mos_mp2, energy_ex, energy_xc_admm, t3, unit_nr)
115 TYPE(qs_environment_type), POINTER :: qs_env
116 TYPE(mp2_type) :: mp2_env
117 TYPE(mo_set_type), DIMENSION(:), INTENT(IN) :: mos_mp2
118 REAL(kind=dp), INTENT(OUT) :: energy_ex, energy_xc_admm(2), t3
119 INTEGER, INTENT(IN) :: unit_nr
120
121 CHARACTER(len=*), PARAMETER :: routinen = 'compute_vec_Sigma_x_minus_vxc_gw'
122
123 CHARACTER(4) :: occ_virt
124 CHARACTER(LEN=40) :: line
125 INTEGER :: dimen, gw_corr_lev_occ, gw_corr_lev_tot, gw_corr_lev_virt, handle, homo, &
126 homo_reduced_bse, homo_startindex_bse, i_img, ikp, irep, ispin, iunit, max_corr_lev_occ, &
127 max_corr_lev_virt, myfun, myfun_aux, myfun_prim, n_level_gw, n_level_gw_ref, n_rep_hf, &
128 nkp, nkp_sigma, nmo, nspins, print_exx, virtual_reduced_bse, virtual_startindex_bse
129 LOGICAL :: calc_ints, charge_constrain_tmp, do_admm_rpa, do_hfx, do_kpoints_cubic_rpa, &
130 do_kpoints_from_gamma, do_ri_sigma_x, really_read_line
131 REAL(kind=dp) :: e_gap_gw, e_homo_gw, e_lumo_gw, eh1, ehfx, eigval_dft, eigval_hf_at_dft, &
132 energy_exc, energy_exc1, energy_exc1_aux_fit, energy_exc_aux_fit, energy_total, &
133 exx_minus_vxc, hfx_fraction, min_direct_hf_at_dft_gap, t1, t2, tmp
134 REAL(kind=dp), ALLOCATABLE, DIMENSION(:) :: matrix_tmp_2_diag
135 REAL(kind=dp), ALLOCATABLE, DIMENSION(:, :) :: eigenval_kp_hf_at_dft, vec_sigma_x
136 REAL(kind=dp), ALLOCATABLE, DIMENSION(:, :, :) :: eigenval_kp, vec_sigma_x_minus_vxc_gw, &
137 vec_sigma_x_minus_vxc_gw_im
138 REAL(kind=dp), DIMENSION(:), POINTER :: mo_eigenvalues
139 TYPE(admm_type), POINTER :: admm_env
140 TYPE(cp_fm_type), POINTER :: mo_coeff
141 TYPE(dbcsr_p_type), ALLOCATABLE, DIMENSION(:) :: mat_exchange_for_kp_from_gamma
142 TYPE(dbcsr_p_type), DIMENSION(:), POINTER :: matrix_ks, matrix_ks_aux_fit, &
143 matrix_ks_aux_fit_hfx, rho_ao, &
144 rho_ao_aux_fit
145 TYPE(dbcsr_p_type), DIMENSION(:, :), POINTER :: matrix_ks_2d, matrix_ks_kp_im, &
146 matrix_ks_kp_re, matrix_ks_transl, matrix_sigma_x_minus_vxc, matrix_sigma_x_minus_vxc_im, &
147 rho_ao_2d
148 TYPE(dbcsr_type) :: matrix_tmp, matrix_tmp_2, mo_coeff_b
149 TYPE(dft_control_type), POINTER :: dft_control
150 TYPE(kpoint_type), POINTER :: kpoints, kpoints_sigma
151 TYPE(mp_para_env_type), POINTER :: para_env
152 TYPE(qs_energy_type), POINTER :: energy
153 TYPE(qs_ks_env_type), POINTER :: ks_env
154 TYPE(qs_rho_type), POINTER :: rho, rho_aux_fit
155 TYPE(section_vals_type), POINTER :: hfx_sections, input, xc_section, &
156 xc_section_admm_aux, &
157 xc_section_admm_prim
158
159 NULLIFY (admm_env, matrix_ks, matrix_ks_aux_fit, rho_ao, matrix_sigma_x_minus_vxc, input, &
160 xc_section, xc_section_admm_aux, xc_section_admm_prim, hfx_sections, rho, &
161 dft_control, para_env, ks_env, mo_coeff, matrix_sigma_x_minus_vxc_im, matrix_ks_aux_fit_hfx, &
162 rho_aux_fit, rho_ao_aux_fit)
163
164 CALL timeset(routinen, handle)
165
166 t1 = m_walltime()
167
168 do_admm_rpa = mp2_env%ri_rpa%do_admm
169 do_ri_sigma_x = mp2_env%ri_g0w0%do_ri_Sigma_x
170 do_kpoints_cubic_rpa = qs_env%mp2_env%ri_rpa_im_time%do_im_time_kpoints
171 do_kpoints_from_gamma = qs_env%mp2_env%ri_rpa_im_time%do_kpoints_from_Gamma
172 print_exx = mp2_env%ri_g0w0%print_exx
173
174 IF (do_kpoints_cubic_rpa) THEN
175 cpassert(do_ri_sigma_x)
176 END IF
177
178 IF (do_kpoints_cubic_rpa) THEN
179
180 CALL get_qs_env(qs_env, &
181 admm_env=admm_env, &
182 matrix_ks_kp=matrix_ks_transl, &
183 rho=rho, &
184 input=input, &
185 dft_control=dft_control, &
186 para_env=para_env, &
187 kpoints=kpoints, &
188 ks_env=ks_env, &
189 energy=energy)
190 nkp = kpoints%nkp
191
192 ELSE
193
194 CALL get_qs_env(qs_env, &
195 admm_env=admm_env, &
196 matrix_ks=matrix_ks, &
197 rho=rho, &
198 input=input, &
199 dft_control=dft_control, &
200 para_env=para_env, &
201 ks_env=ks_env, &
202 energy=energy)
203 nkp = 1
204 CALL qs_rho_get(rho, rho_ao=rho_ao)
205
206 IF (do_admm_rpa) THEN
207 CALL get_admm_env(admm_env, matrix_ks_aux_fit=matrix_ks_aux_fit, rho_aux_fit=rho_aux_fit, &
208 matrix_ks_aux_fit_hfx=matrix_ks_aux_fit_hfx)
209 CALL qs_rho_get(rho_aux_fit, rho_ao=rho_ao_aux_fit)
210
211 ! RPA/GW with ADMM for EXX or the exchange self-energy only implemented for
212 ! ADMM_PURIFICATION_METHOD NONE
213 ! METHOD BASIS_PROJECTION
214 ! in the admm section
215 cpassert(admm_env%purification_method == do_admm_purify_none)
216 cpassert(dft_control%admm_control%method == do_admm_basis_projection)
217 END IF
218 END IF
219
220 nspins = dft_control%nspins
221
222 ! safe ks matrix for later: we will transform matrix_ks
223 ! to T-cell index and then to k-points for band structure calculation
224 IF (do_kpoints_from_gamma) THEN
225 ! not yet there: open shell
226 ALLOCATE (qs_env%mp2_env%ri_g0w0%matrix_ks(nspins))
227 DO ispin = 1, nspins
228 NULLIFY (qs_env%mp2_env%ri_g0w0%matrix_ks(ispin)%matrix)
229 ALLOCATE (qs_env%mp2_env%ri_g0w0%matrix_ks(ispin)%matrix)
230 CALL dbcsr_create(qs_env%mp2_env%ri_g0w0%matrix_ks(ispin)%matrix, &
231 template=matrix_ks(ispin)%matrix)
232 CALL dbcsr_desymmetrize(matrix_ks(ispin)%matrix, &
233 qs_env%mp2_env%ri_g0w0%matrix_ks(ispin)%matrix)
234
235 END DO
236 END IF
237
238 IF (do_kpoints_cubic_rpa) THEN
239
240 CALL allocate_matrix_ks_kp(matrix_ks_transl, matrix_ks_kp_re, matrix_ks_kp_im, kpoints)
241 CALL transform_matrix_ks_to_kp(matrix_ks_transl, matrix_ks_kp_re, matrix_ks_kp_im, kpoints)
242
243 DO ispin = 1, nspins
244 DO i_img = 1, SIZE(matrix_ks_transl, 2)
245 CALL dbcsr_set(matrix_ks_transl(ispin, i_img)%matrix, 0.0_dp)
246 END DO
247 END DO
248
249 END IF
250
251 ! initialize matrix_sigma_x_minus_vxc
252 NULLIFY (matrix_sigma_x_minus_vxc)
253 CALL dbcsr_allocate_matrix_set(matrix_sigma_x_minus_vxc, nspins, nkp)
254 IF (do_kpoints_cubic_rpa) THEN
255 NULLIFY (matrix_sigma_x_minus_vxc_im)
256 CALL dbcsr_allocate_matrix_set(matrix_sigma_x_minus_vxc_im, nspins, nkp)
257 END IF
258
259 DO ispin = 1, nspins
260 DO ikp = 1, nkp
261
262 IF (do_kpoints_cubic_rpa) THEN
263
264 ALLOCATE (matrix_sigma_x_minus_vxc(ispin, ikp)%matrix)
265 CALL dbcsr_create(matrix_sigma_x_minus_vxc(ispin, ikp)%matrix, &
266 template=matrix_ks_kp_re(1, 1)%matrix, &
267 matrix_type=dbcsr_type_symmetric)
268
269 CALL dbcsr_copy(matrix_sigma_x_minus_vxc(ispin, ikp)%matrix, matrix_ks_kp_re(ispin, ikp)%matrix)
270 CALL dbcsr_set(matrix_ks_kp_re(ispin, ikp)%matrix, 0.0_dp)
271
272 ALLOCATE (matrix_sigma_x_minus_vxc_im(ispin, ikp)%matrix)
273 CALL dbcsr_create(matrix_sigma_x_minus_vxc_im(ispin, ikp)%matrix, &
274 template=matrix_ks_kp_im(1, 1)%matrix, &
275 matrix_type=dbcsr_type_antisymmetric)
276
277 CALL dbcsr_copy(matrix_sigma_x_minus_vxc_im(ispin, ikp)%matrix, matrix_ks_kp_im(ispin, ikp)%matrix)
278 CALL dbcsr_set(matrix_ks_kp_im(ispin, ikp)%matrix, 0.0_dp)
279
280 ELSE
281
282 ALLOCATE (matrix_sigma_x_minus_vxc(ispin, ikp)%matrix)
283 CALL dbcsr_create(matrix_sigma_x_minus_vxc(ispin, ikp)%matrix, &
284 template=matrix_ks(1)%matrix)
285
286 CALL dbcsr_copy(matrix_sigma_x_minus_vxc(ispin, ikp)%matrix, matrix_ks(ispin)%matrix)
287 CALL dbcsr_set(matrix_ks(ispin)%matrix, 0.0_dp)
288
289 END IF
290
291 END DO
292 END DO
293
294 ! set DFT functional to none and hfx_fraction to zero
295 hfx_sections => section_vals_get_subs_vals(input, "DFT%XC%HF")
296 CALL section_vals_get(hfx_sections, explicit=do_hfx)
297
298 IF (do_hfx) THEN
299 hfx_fraction = qs_env%x_data(1, 1)%general_parameter%fraction
300 qs_env%x_data(:, :)%general_parameter%fraction = 0.0_dp
301 END IF
302 xc_section => section_vals_get_subs_vals(input, "DFT%XC")
303 CALL section_vals_val_get(xc_section, "XC_FUNCTIONAL%_SECTION_PARAMETERS_", &
304 i_val=myfun)
305 CALL section_vals_val_set(xc_section, "XC_FUNCTIONAL%_SECTION_PARAMETERS_", &
306 i_val=xc_none)
307
308 ! in ADMM, also set the XC functional for ADMM correction to none
309 ! do not do this if we do ADMM for Sigma_x
310 IF (dft_control%do_admm) THEN
311 xc_section_admm_aux => section_vals_get_subs_vals(admm_env%xc_section_aux, &
312 "XC_FUNCTIONAL")
313 CALL section_vals_val_get(xc_section_admm_aux, "_SECTION_PARAMETERS_", &
314 i_val=myfun_aux)
315 CALL section_vals_val_set(xc_section_admm_aux, "_SECTION_PARAMETERS_", &
316 i_val=xc_none)
317
318 ! the same for the primary basis
319 xc_section_admm_prim => section_vals_get_subs_vals(admm_env%xc_section_primary, &
320 "XC_FUNCTIONAL")
321 CALL section_vals_val_get(xc_section_admm_prim, "_SECTION_PARAMETERS_", &
322 i_val=myfun_prim)
323 CALL section_vals_val_set(xc_section_admm_prim, "_SECTION_PARAMETERS_", &
324 i_val=xc_none)
325
326 ! for ADMMQ/S, set the charge_constrain to false (otherwise wrong results)
327 charge_constrain_tmp = .false.
328 IF (admm_env%charge_constrain) THEN
329 admm_env%charge_constrain = .false.
330 charge_constrain_tmp = .true.
331 END IF
332
333 END IF
334
335 ! if we do ADMM for Sigma_x, we write the ADMM correction into matrix_ks_aux_fit
336 ! and therefore we should set it to zero
337 IF (do_admm_rpa) THEN
338 DO ispin = 1, nspins
339 CALL dbcsr_set(matrix_ks_aux_fit(ispin)%matrix, 0.0_dp)
340 END DO
341 END IF
342
343 IF (.NOT. mp2_env%ri_g0w0%update_xc_energy) THEN
344 energy_total = energy%total
345 energy_exc = energy%exc
346 energy_exc1 = energy%exc1
347 energy_exc_aux_fit = energy%ex
348 energy_exc1_aux_fit = energy%exc_aux_fit
349 energy_ex = energy%exc1_aux_fit
350 END IF
351
352 ! Remove the Exchange-correlation energy contributions from the total energy
353 energy%total = energy%total - (energy%exc + energy%exc1 + energy%ex + &
354 energy%exc_aux_fit + energy%exc1_aux_fit)
355
356 ! calculate KS-matrix without XC and without HF
357 CALL qs_ks_build_kohn_sham_matrix(qs_env=qs_env, calculate_forces=.false., &
358 just_energy=.false.)
359
360 IF (.NOT. mp2_env%ri_g0w0%update_xc_energy) THEN
361 energy%exc = energy_exc
362 energy%exc1 = energy_exc1
363 energy%exc_aux_fit = energy_ex
364 energy%exc1_aux_fit = energy_exc_aux_fit
365 energy%ex = energy_exc1_aux_fit
366 energy%total = energy_total
367 END IF
368
369 ! set the DFT functional and HF fraction back
370 CALL section_vals_val_set(xc_section, "XC_FUNCTIONAL%_SECTION_PARAMETERS_", &
371 i_val=myfun)
372 IF (do_hfx) THEN
373 qs_env%x_data(:, :)%general_parameter%fraction = hfx_fraction
374 END IF
375
376 IF (dft_control%do_admm) THEN
377 xc_section_admm_aux => section_vals_get_subs_vals(admm_env%xc_section_aux, &
378 "XC_FUNCTIONAL")
379 xc_section_admm_prim => section_vals_get_subs_vals(admm_env%xc_section_primary, &
380 "XC_FUNCTIONAL")
381
382 CALL section_vals_val_set(xc_section_admm_aux, "_SECTION_PARAMETERS_", &
383 i_val=myfun_aux)
384 CALL section_vals_val_set(xc_section_admm_prim, "_SECTION_PARAMETERS_", &
385 i_val=myfun_prim)
386 IF (charge_constrain_tmp) THEN
387 admm_env%charge_constrain = .true.
388 END IF
389 END IF
390
391 IF (do_kpoints_cubic_rpa) THEN
392 CALL transform_matrix_ks_to_kp(matrix_ks_transl, matrix_ks_kp_re, matrix_ks_kp_im, kpoints)
393 END IF
394
395 ! remove the single-particle part (kin. En + Hartree pot) and change the sign
396 DO ispin = 1, nspins
397 IF (do_kpoints_cubic_rpa) THEN
398 DO ikp = 1, nkp
399 CALL dbcsr_add(matrix_sigma_x_minus_vxc(ispin, ikp)%matrix, matrix_ks_kp_re(ispin, ikp)%matrix, -1.0_dp, 1.0_dp)
400 CALL dbcsr_add(matrix_sigma_x_minus_vxc_im(ispin, ikp)%matrix, matrix_ks_kp_im(ispin, ikp)%matrix, -1.0_dp, 1.0_dp)
401 END DO
402 ELSE
403 CALL dbcsr_add(matrix_sigma_x_minus_vxc(ispin, 1)%matrix, matrix_ks(ispin)%matrix, -1.0_dp, 1.0_dp)
404 END IF
405 END DO
406
407 IF (do_kpoints_cubic_rpa) THEN
408
409 CALL transform_sigma_x_minus_vxc_to_mo_basis(kpoints, matrix_sigma_x_minus_vxc, &
410 matrix_sigma_x_minus_vxc_im, &
411 vec_sigma_x_minus_vxc_gw, &
412 vec_sigma_x_minus_vxc_gw_im, &
413 para_env, nmo, mp2_env)
414
415 ELSE
416
417 DO ispin = 1, nspins
418 CALL dbcsr_set(matrix_ks(ispin)%matrix, 0.0_dp)
419 IF (do_admm_rpa) THEN
420 CALL dbcsr_set(matrix_ks_aux_fit(ispin)%matrix, 0.0_dp)
421 END IF
422 END DO
423
424 hfx_sections => section_vals_get_subs_vals(input, "DFT%XC%WF_CORRELATION%RI_RPA%HF")
425
426 CALL section_vals_get(hfx_sections, n_repetition=n_rep_hf)
427
428 ! in most cases, we calculate the exchange self-energy here. But if we do only RI for
429 ! the exchange self-energy, we do not calculate exchange here
430 ehfx = 0.0_dp
431 IF (.NOT. do_ri_sigma_x) THEN
432
433 CALL exx_pre_hfx(hfx_sections, qs_env%mp2_env%ri_rpa%x_data, qs_env%mp2_env%ri_rpa%reuse_hfx)
434 calc_ints = .NOT. qs_env%mp2_env%ri_rpa%reuse_hfx
435
436 ! add here HFX (=Sigma_exchange) to matrix_sigma_x_minus_vxc
437 DO irep = 1, n_rep_hf
438 IF (do_admm_rpa) THEN
439 matrix_ks_2d(1:nspins, 1:1) => matrix_ks_aux_fit(1:nspins)
440 rho_ao_2d(1:nspins, 1:1) => rho_ao_aux_fit(1:nspins)
441 ELSE
442 matrix_ks_2d(1:nspins, 1:1) => matrix_ks(1:nspins)
443 rho_ao_2d(1:nspins, 1:1) => rho_ao(1:nspins)
444 END IF
445
446 IF (qs_env%mp2_env%ri_rpa%x_data(irep, 1)%do_hfx_ri) THEN
447 CALL hfx_ri_update_ks(qs_env, qs_env%mp2_env%ri_rpa%x_data(irep, 1)%ri_data, matrix_ks_2d, ehfx, &
448 rho_ao=rho_ao_2d, geometry_did_change=calc_ints, nspins=nspins, &
449 hf_fraction=qs_env%mp2_env%ri_rpa%x_data(irep, 1)%general_parameter%fraction)
450
451 IF (do_admm_rpa) THEN
452 !for ADMMS, we need the exchange matrix k(d) for both spins
453 DO ispin = 1, nspins
454 CALL dbcsr_copy(matrix_ks_aux_fit_hfx(ispin)%matrix, matrix_ks_2d(ispin, 1)%matrix, &
455 name="HF exch. part of matrix_ks_aux_fit for ADMMS")
456 END DO
457 END IF
458 ELSE
459 CALL integrate_four_center(qs_env, qs_env%mp2_env%ri_rpa%x_data, matrix_ks_2d, eh1, &
460 rho_ao_2d, hfx_sections, &
461 para_env, calc_ints, irep, .true., &
462 ispin=1)
463 ehfx = ehfx + eh1
464 END IF
465 END DO
466
467 !ADMM XC correction
468 IF (do_admm_rpa) THEN
469 CALL calc_exx_admm_xc_contributions(qs_env=qs_env, &
470 matrix_prim=matrix_ks, &
471 matrix_aux=matrix_ks_aux_fit, &
472 x_data=qs_env%mp2_env%ri_rpa%x_data, &
473 exc=energy_xc_admm(1), &
474 exc_aux_fit=energy_xc_admm(2), &
475 calc_forces=.false., &
476 use_virial=.false.)
477 END IF
478
479 IF (do_kpoints_from_gamma .AND. print_exx == gw_print_exx) THEN
480 ALLOCATE (mat_exchange_for_kp_from_gamma(1))
481
482 DO ispin = 1, 1
483 NULLIFY (mat_exchange_for_kp_from_gamma(ispin)%matrix)
484 ALLOCATE (mat_exchange_for_kp_from_gamma(ispin)%matrix)
485 CALL dbcsr_create(mat_exchange_for_kp_from_gamma(ispin)%matrix, template=matrix_ks(ispin)%matrix)
486 CALL dbcsr_desymmetrize(matrix_ks(ispin)%matrix, mat_exchange_for_kp_from_gamma(ispin)%matrix)
487 END DO
488
489 END IF
490
491 CALL exx_post_hfx(qs_env, qs_env%mp2_env%ri_rpa%x_data, qs_env%mp2_env%ri_rpa%reuse_hfx)
492 END IF
493
494 energy_ex = ehfx
495
496 ! transform Fock-Matrix (calculated in integrate_four_center, written in matrix_ks_aux_fit in case
497 ! of ADMM) from ADMM basis to primary basis
498 IF (do_admm_rpa) THEN
499 CALL admm_mo_merge_ks_matrix(qs_env)
500 END IF
501
502 DO ispin = 1, nspins
503 CALL dbcsr_add(matrix_sigma_x_minus_vxc(ispin, 1)%matrix, matrix_ks(ispin)%matrix, 1.0_dp, 1.0_dp)
504 END DO
505
506 ! safe matrix_sigma_x_minus_vxc for later: for example, we will transform matrix_sigma_x_minus_vxc
507 ! to T-cell index and then to k-points for band structure calculation
508 IF (do_kpoints_from_gamma) THEN
509 ! not yet there: open shell
510 ALLOCATE (qs_env%mp2_env%ri_g0w0%matrix_sigma_x_minus_vxc(nspins))
511 DO ispin = 1, nspins
512 NULLIFY (qs_env%mp2_env%ri_g0w0%matrix_sigma_x_minus_vxc(ispin)%matrix)
513 ALLOCATE (qs_env%mp2_env%ri_g0w0%matrix_sigma_x_minus_vxc(ispin)%matrix)
514 CALL dbcsr_create(qs_env%mp2_env%ri_g0w0%matrix_sigma_x_minus_vxc(ispin)%matrix, &
515 template=matrix_ks(ispin)%matrix)
516
517 CALL dbcsr_desymmetrize(matrix_sigma_x_minus_vxc(ispin, 1)%matrix, &
518 qs_env%mp2_env%ri_g0w0%matrix_sigma_x_minus_vxc(ispin)%matrix)
519
520 END DO
521 END IF
522
523 CALL dbcsr_desymmetrize(matrix_ks(1)%matrix, mo_coeff_b)
524 CALL dbcsr_set(mo_coeff_b, 0.0_dp)
525
526 ! Transform matrix_sigma_x_minus_vxc to MO basis
527 DO ispin = 1, nspins
528
529 CALL get_mo_set(mo_set=mos_mp2(ispin), &
530 mo_coeff=mo_coeff, &
531 eigenvalues=mo_eigenvalues, &
532 nmo=nmo, &
533 homo=homo, &
534 nao=dimen)
535
536 IF (ispin == 1) THEN
537
538 ALLOCATE (vec_sigma_x_minus_vxc_gw(nmo, nspins, nkp))
539 vec_sigma_x_minus_vxc_gw = 0.0_dp
540
541 ALLOCATE (matrix_tmp_2_diag(dimen))
542 END IF
543
544 CALL dbcsr_set(mo_coeff_b, 0.0_dp)
545 CALL copy_fm_to_dbcsr(mo_coeff, mo_coeff_b, keep_sparsity=.false.)
546
547 ! initialize matrix_tmp and matrix_tmp2
548 IF (ispin == 1) THEN
549 CALL dbcsr_create(matrix_tmp, template=mo_coeff_b)
550 CALL dbcsr_copy(matrix_tmp, mo_coeff_b)
551 CALL dbcsr_set(matrix_tmp, 0.0_dp)
552
553 CALL dbcsr_create(matrix_tmp_2, template=mo_coeff_b)
554 CALL dbcsr_copy(matrix_tmp_2, mo_coeff_b)
555 CALL dbcsr_set(matrix_tmp_2, 0.0_dp)
556 END IF
557
558 gw_corr_lev_occ = mp2_env%ri_g0w0%corr_mos_occ
559 gw_corr_lev_virt = mp2_env%ri_g0w0%corr_mos_virt
560
561 ! If SVD is used to invert overlap matrix (for CHOLESKY OFF), some MOs are removed
562 ! Therefore, setting the number of gw_corr_lev_virt simply to dimen - homo leads to index problems
563 ! Instead, we take into account the removed MOs
564 max_corr_lev_occ = homo
565 max_corr_lev_virt = nmo - homo
566
567 ! If BSE is invoked, manipulate corrected MO number
568 IF (mp2_env%bse%do_bse) THEN
569 ! Logic: If cutoff is negative, all MOs are included in BSE, i.e. we need to correct them all
570 ! If cutoff is positive, we can reduce the number of MOs to be corrected and force gw_corr_lev_...
571 ! to a sufficiently large number by setting it to -2 and read indices afterwards
572 ! Handling for occupied levels
573 IF (mp2_env%bse%bse_cutoff_occ < 0) THEN
574 gw_corr_lev_occ = -1
575 ELSE
576 IF (gw_corr_lev_occ > 0) THEN
577 gw_corr_lev_occ = -2
578 END IF
579 END IF
580 ! Handling for virtual levels
581 IF (mp2_env%bse%bse_cutoff_empty < 0) THEN
582 gw_corr_lev_virt = -1
583 ELSE
584 IF (gw_corr_lev_virt > 0) THEN
585 gw_corr_lev_virt = -2
586 END IF
587 END IF
588
589 ! Obtain indices from DFT if gw_corr... are set to -2
590 CALL determine_cutoff_indices(mo_eigenvalues, &
591 homo, max_corr_lev_virt, &
592 homo_reduced_bse, virtual_reduced_bse, &
593 homo_startindex_bse, virtual_startindex_bse, &
594 mp2_env)
595 IF (gw_corr_lev_occ == -2) THEN
596 cpwarn("BSE cutoff overwrites user input for CORR_MOS_OCC")
597 gw_corr_lev_occ = homo_reduced_bse
598 END IF
599 IF (gw_corr_lev_virt == -2) THEN
600 cpwarn("BSE cutoff overwrites user input for CORR_MOS_VIRT")
601 gw_corr_lev_virt = virtual_reduced_bse
602 END IF
603 END IF
604
605 ! if requested number of occ/virt levels for correction either exceed the number of
606 ! occ/virt levels or the requested number is negative, default to correct all
607 ! occ/virt level energies
608 IF (gw_corr_lev_occ > homo .OR. gw_corr_lev_occ < 0) gw_corr_lev_occ = max_corr_lev_occ
609 IF (gw_corr_lev_virt > max_corr_lev_virt .OR. gw_corr_lev_virt < 0) gw_corr_lev_virt = max_corr_lev_virt
610 IF (ispin == 1) THEN
611 mp2_env%ri_g0w0%corr_mos_occ = gw_corr_lev_occ
612 mp2_env%ri_g0w0%corr_mos_virt = gw_corr_lev_virt
613 ELSE IF (ispin == 2) THEN
614 ! ensure that the total number of corrected MOs is the same for alpha and beta, important
615 ! for parallelization
616 IF (mp2_env%ri_g0w0%corr_mos_occ + mp2_env%ri_g0w0%corr_mos_virt /= &
617 gw_corr_lev_occ + gw_corr_lev_virt) THEN
618 gw_corr_lev_virt = mp2_env%ri_g0w0%corr_mos_occ + mp2_env%ri_g0w0%corr_mos_virt - gw_corr_lev_occ
619 END IF
620 mp2_env%ri_g0w0%corr_mos_occ_beta = gw_corr_lev_occ
621 mp2_env%ri_g0w0%corr_mos_virt_beta = gw_corr_lev_virt
622
623 END IF
624
625 CALL dbcsr_multiply('N', 'N', 1.0_dp, matrix_sigma_x_minus_vxc(ispin, 1)%matrix, &
626 mo_coeff_b, 0.0_dp, matrix_tmp, first_column=homo + 1 - gw_corr_lev_occ, &
627 last_column=homo + gw_corr_lev_virt)
628
629 CALL dbcsr_multiply('T', 'N', 1.0_dp, mo_coeff_b, &
630 matrix_tmp, 0.0_dp, matrix_tmp_2, first_row=homo + 1 - gw_corr_lev_occ, &
631 last_row=homo + gw_corr_lev_virt)
632
633 CALL dbcsr_get_diag(matrix_tmp_2, matrix_tmp_2_diag)
634 vec_sigma_x_minus_vxc_gw(1:nmo, ispin, 1) = matrix_tmp_2_diag(1:nmo)
635
636 CALL dbcsr_set(matrix_tmp, 0.0_dp)
637 CALL dbcsr_set(matrix_tmp_2, 0.0_dp)
638
639 END DO
640
641 CALL para_env%sum(vec_sigma_x_minus_vxc_gw)
642
643 END IF
644
645 CALL dbcsr_release(mo_coeff_b)
646 CALL dbcsr_release(matrix_tmp)
647 CALL dbcsr_release(matrix_tmp_2)
648 IF (do_kpoints_cubic_rpa) THEN
649 CALL dbcsr_deallocate_matrix_set(matrix_ks_kp_re)
650 CALL dbcsr_deallocate_matrix_set(matrix_ks_kp_im)
651 END IF
652
653 DO ispin = 1, nspins
654 DO ikp = 1, nkp
655 CALL dbcsr_release_p(matrix_sigma_x_minus_vxc(ispin, ikp)%matrix)
656 IF (do_kpoints_cubic_rpa) THEN
657 CALL dbcsr_release_p(matrix_sigma_x_minus_vxc_im(ispin, ikp)%matrix)
658 END IF
659 END DO
660 END DO
661
662 ALLOCATE (mp2_env%ri_g0w0%vec_Sigma_x_minus_vxc_gw(nmo, nspins, nkp))
663
664 IF (print_exx == gw_print_exx) THEN
665
666 IF (do_kpoints_from_gamma) THEN
667
668 gw_corr_lev_tot = gw_corr_lev_occ + gw_corr_lev_virt
669
670 CALL get_qs_env(qs_env=qs_env, &
671 kpoints=kpoints)
672
673 CALL trunc_coulomb_for_exchange(qs_env)
674
675 CALL compute_kpoints(qs_env, kpoints, unit_nr)
676
677 ALLOCATE (eigenval_kp(nmo, 1, nspins))
678
679 CALL get_bandstruc_and_k_dependent_mos(qs_env, eigenval_kp)
680
681 CALL compute_minus_vxc_kpoints(qs_env)
682
683 nkp_sigma = SIZE(eigenval_kp, 2)
684
685 ALLOCATE (vec_sigma_x(nmo, nkp_sigma))
686 vec_sigma_x(:, :) = 0.0_dp
687
688 CALL trafo_to_mo_and_kpoints(qs_env, &
689 mat_exchange_for_kp_from_gamma(1)%matrix, &
690 vec_sigma_x(homo - gw_corr_lev_occ + 1:homo + gw_corr_lev_virt, :), &
691 homo, gw_corr_lev_occ, gw_corr_lev_virt, 1)
692
693 CALL dbcsr_release(mat_exchange_for_kp_from_gamma(1)%matrix)
694 DEALLOCATE (mat_exchange_for_kp_from_gamma(1)%matrix)
695 DEALLOCATE (mat_exchange_for_kp_from_gamma)
696
697 DEALLOCATE (vec_sigma_x_minus_vxc_gw)
698
699 ALLOCATE (vec_sigma_x_minus_vxc_gw(nmo, nspins, nkp_sigma))
700
701 vec_sigma_x_minus_vxc_gw(:, 1, :) = vec_sigma_x(:, :) + &
702 qs_env%mp2_env%ri_g0w0%vec_Sigma_x_minus_vxc_gw(:, 1, :)
703
704 kpoints_sigma => qs_env%mp2_env%ri_rpa_im_time%kpoints_Sigma
705
706 ELSE
707
708 nkp_sigma = 1
709
710 END IF
711
712 IF (unit_nr > 0) THEN
713
714 ALLOCATE (eigenval_kp_hf_at_dft(nmo, nkp_sigma))
715 eigenval_kp_hf_at_dft(:, :) = eigenval_kp(:, :, 1) + vec_sigma_x_minus_vxc_gw(:, 1, :)
716
717 min_direct_hf_at_dft_gap = 100.0_dp
718
719 WRITE (unit_nr, '(T3,A)') ''
720 WRITE (unit_nr, '(T3,A)') 'Exchange energies'
721 WRITE (unit_nr, '(T3,A)') '-----------------'
722 WRITE (unit_nr, '(T3,A)') ''
723 WRITE (unit_nr, '(T6,2A)') 'MO e_n^DFT Sigma_x-vxc e_n^HF@DFT'
724 DO ikp = 1, nkp_sigma
725 IF (nkp_sigma > 1) THEN
726 WRITE (unit_nr, '(T3,A)') ''
727 WRITE (unit_nr, '(T3,A7,I3,A3,I3,A8,3F7.3,A12,3F7.3)') 'Kpoint ', ikp, ' /', nkp_sigma, &
728 ' xkp =', kpoints_sigma%xkp(1, ikp), kpoints_sigma%xkp(2, ikp), &
729 kpoints_sigma%xkp(3, ikp), ' and xkp =', -kpoints_sigma%xkp(1, ikp), &
730 -kpoints_sigma%xkp(2, ikp), -kpoints_sigma%xkp(3, ikp)
731 WRITE (unit_nr, '(T3,A)') ''
732 END IF
733 DO n_level_gw = 1, gw_corr_lev_occ + gw_corr_lev_virt
734
735 n_level_gw_ref = n_level_gw + homo - gw_corr_lev_occ
736 IF (n_level_gw <= gw_corr_lev_occ) THEN
737 occ_virt = 'occ'
738 ELSE
739 occ_virt = 'vir'
740 END IF
741
742 eigval_dft = eigenval_kp(n_level_gw_ref, ikp, 1)*evolt
743 exx_minus_vxc = real(vec_sigma_x_minus_vxc_gw(n_level_gw_ref, 1, ikp)*evolt, kind=dp)
744 eigval_hf_at_dft = eigenval_kp_hf_at_dft(n_level_gw_ref, ikp)*evolt
745
746 WRITE (unit_nr, '(T4,I4,3A,3F21.3,3F21.3,3F21.3)') &
747 n_level_gw_ref, ' ( ', occ_virt, ') ', eigval_dft, exx_minus_vxc, eigval_hf_at_dft
748
749 END DO
750 e_homo_gw = maxval(eigenval_kp_hf_at_dft(homo - gw_corr_lev_occ + 1:homo, ikp))
751 e_lumo_gw = minval(eigenval_kp_hf_at_dft(homo + 1:homo + gw_corr_lev_virt, ikp))
752 e_gap_gw = e_lumo_gw - e_homo_gw
753 IF (e_gap_gw < min_direct_hf_at_dft_gap) min_direct_hf_at_dft_gap = e_gap_gw
754 WRITE (unit_nr, '(T3,A)') ''
755 WRITE (unit_nr, '(T3,A,F53.2)') 'HF@DFT HOMO-LUMO gap (eV)', e_gap_gw*evolt
756 WRITE (unit_nr, '(T3,A)') ''
757 END DO
758
759 WRITE (unit_nr, '(T3,A)') ''
760 WRITE (unit_nr, '(T3,A)') ''
761 WRITE (unit_nr, '(T3,A,F63.3)') 'HF@DFT direct bandgap (eV)', min_direct_hf_at_dft_gap*evolt
762
763 WRITE (unit_nr, '(T3,A)') ''
764 WRITE (unit_nr, '(T3,A)') 'End of exchange energies'
765 WRITE (unit_nr, '(T3,A)') '------------------------'
766 WRITE (unit_nr, '(T3,A)') ''
767
768 cpabort('Stop after printing exchange energies.')
769
770 ELSE
771 CALL para_env%sync()
772 END IF
773
774 END IF
775
776 IF (print_exx == gw_read_exx) THEN
777
778 CALL open_file(unit_number=iunit, file_name="exx.out")
779
780 really_read_line = .false.
781
782 DO WHILE (.true.)
783
784 READ (iunit, '(A)') line
785
786 IF (line == " End of exchange energies ") EXIT
787
788 IF (really_read_line) THEN
789
790 READ (line(1:7), *) n_level_gw_ref
791 READ (line(17:40), *) tmp
792
793 DO ikp = 1, SIZE(vec_sigma_x_minus_vxc_gw, 3)
794 vec_sigma_x_minus_vxc_gw(n_level_gw_ref, 1, ikp) = tmp/evolt
795 END DO
796
797 END IF
798
799 IF (line == " MO Sigma_x-vxc ") really_read_line = .true.
800
801 END DO
802
803 CALL close_file(iunit)
804
805 END IF
806
807 ! store vec_Sigma_x_minus_vxc_gw in the mp2_environment
808 mp2_env%ri_g0w0%vec_Sigma_x_minus_vxc_gw(:, :, :) = vec_sigma_x_minus_vxc_gw(:, :, :)
809
810 ! clean up
811 DEALLOCATE (matrix_sigma_x_minus_vxc, vec_sigma_x_minus_vxc_gw)
812 IF (do_kpoints_cubic_rpa) THEN
813 DEALLOCATE (matrix_sigma_x_minus_vxc_im)
814 END IF
815
816 t2 = m_walltime()
817
818 t3 = t2 - t1
819
820 CALL timestop(handle)
821
823
824! **************************************************************************************************
825!> \brief ...
826!> \param kpoints ...
827!> \param matrix_sigma_x_minus_vxc ...
828!> \param matrix_sigma_x_minus_vxc_im ...
829!> \param vec_Sigma_x_minus_vxc_gw ...
830!> \param vec_Sigma_x_minus_vxc_gw_im ...
831!> \param para_env ...
832!> \param nmo ...
833!> \param mp2_env ...
834! **************************************************************************************************
835 SUBROUTINE transform_sigma_x_minus_vxc_to_mo_basis(kpoints, matrix_sigma_x_minus_vxc, &
836 matrix_sigma_x_minus_vxc_im, vec_Sigma_x_minus_vxc_gw, &
837 vec_Sigma_x_minus_vxc_gw_im, para_env, nmo, mp2_env)
838
839 TYPE(kpoint_type), POINTER :: kpoints
840 TYPE(dbcsr_p_type), DIMENSION(:, :), POINTER :: matrix_sigma_x_minus_vxc, &
841 matrix_sigma_x_minus_vxc_im
842 REAL(kind=dp), ALLOCATABLE, DIMENSION(:, :, :) :: vec_sigma_x_minus_vxc_gw, &
843 vec_sigma_x_minus_vxc_gw_im
844 TYPE(mp_para_env_type), INTENT(IN) :: para_env
845 INTEGER :: nmo
846 TYPE(mp2_type) :: mp2_env
847
848 CHARACTER(LEN=*), PARAMETER :: routinen = 'transform_sigma_x_minus_vxc_to_MO_basis'
849
850 INTEGER :: dimen, gw_corr_lev_occ, gw_corr_lev_virt, handle, homo, i_global, iib, ikp, &
851 ispin, j_global, jjb, max_corr_lev_occ, max_corr_lev_virt, ncol_local, nkp, nrow_local, &
852 nspins
853 INTEGER, DIMENSION(2) :: kp_range
854 INTEGER, DIMENSION(:), POINTER :: col_indices, row_indices
855 REAL(kind=dp) :: imval, reval
856 TYPE(cp_cfm_type) :: cfm_mos, cfm_sigma_x_minus_vxc, &
857 cfm_sigma_x_minus_vxc_mo_basis, cfm_tmp
858 TYPE(cp_fm_struct_type), POINTER :: matrix_struct
859 TYPE(cp_fm_type) :: fwork_im, fwork_re
860 TYPE(kpoint_env_type), POINTER :: kp
861 TYPE(mo_set_type), POINTER :: mo_set, mo_set_im, mo_set_re
862
863 CALL timeset(routinen, handle)
864
865 mo_set => kpoints%kp_env(1)%kpoint_env%mos(1, 1)
866 CALL get_mo_set(mo_set, nmo=nmo)
867
868 nspins = SIZE(matrix_sigma_x_minus_vxc, 1)
869 CALL get_kpoint_info(kpoints, nkp=nkp, kp_range=kp_range)
870
871 ! if this CPASSERT is wrong, please make sure that the kpoint group size PARALLEL_GROUP_SIZE
872 ! in the kpoint environment &DFT &KPOINTS is -1
873 cpassert(kp_range(1) == 1 .AND. kp_range(2) == nkp)
874
875 ALLOCATE (vec_sigma_x_minus_vxc_gw(nmo, nspins, nkp))
876 vec_sigma_x_minus_vxc_gw = 0.0_dp
877
878 ALLOCATE (vec_sigma_x_minus_vxc_gw_im(nmo, nspins, nkp))
879 vec_sigma_x_minus_vxc_gw_im = 0.0_dp
880
881 CALL cp_fm_get_info(mo_set%mo_coeff, matrix_struct=matrix_struct)
882 CALL cp_fm_create(fwork_re, matrix_struct)
883 CALL cp_fm_create(fwork_im, matrix_struct)
884 CALL cp_cfm_create(cfm_mos, matrix_struct)
885 CALL cp_cfm_create(cfm_sigma_x_minus_vxc, matrix_struct)
886 CALL cp_cfm_create(cfm_sigma_x_minus_vxc_mo_basis, matrix_struct)
887 CALL cp_cfm_create(cfm_tmp, matrix_struct)
888
889 CALL cp_cfm_get_info(matrix=cfm_sigma_x_minus_vxc_mo_basis, &
890 nrow_local=nrow_local, &
891 ncol_local=ncol_local, &
892 row_indices=row_indices, &
893 col_indices=col_indices)
894
895 ! Transform matrix_sigma_x_minus_vxc to MO basis
896 DO ikp = 1, nkp
897
898 kp => kpoints%kp_env(ikp)%kpoint_env
899
900 DO ispin = 1, nspins
901
902 ! v_xc_n to fm matrix
903 CALL copy_dbcsr_to_fm(matrix_sigma_x_minus_vxc(ispin, ikp)%matrix, fwork_re)
904 CALL copy_dbcsr_to_fm(matrix_sigma_x_minus_vxc_im(ispin, ikp)%matrix, fwork_im)
905
906 CALL cp_cfm_scale_and_add_fm(z_zero, cfm_sigma_x_minus_vxc, z_one, fwork_re)
907 CALL cp_cfm_scale_and_add_fm(z_one, cfm_sigma_x_minus_vxc, gaussi, fwork_im)
908
909 ! get real part (1) and imag. part (2) of the mo coeffs
910 mo_set_re => kp%mos(1, ispin)
911 mo_set_im => kp%mos(2, ispin)
912
913 CALL cp_cfm_scale_and_add_fm(z_zero, cfm_mos, z_one, mo_set_re%mo_coeff)
914 CALL cp_cfm_scale_and_add_fm(z_one, cfm_mos, gaussi, mo_set_im%mo_coeff)
915
916 ! tmp = V(k)*C(k)
917 CALL parallel_gemm('N', 'N', nmo, nmo, nmo, z_one, cfm_sigma_x_minus_vxc, &
918 cfm_mos, z_zero, cfm_tmp)
919
920 ! V_n(k) = C^H(k)*tmp
921 CALL parallel_gemm('C', 'N', nmo, nmo, nmo, z_one, cfm_mos, cfm_tmp, &
922 z_zero, cfm_sigma_x_minus_vxc_mo_basis)
923
924 DO jjb = 1, ncol_local
925
926 j_global = col_indices(jjb)
927
928 DO iib = 1, nrow_local
929
930 i_global = row_indices(iib)
931
932 IF (j_global == i_global .AND. i_global <= nmo) THEN
933
934 reval = real(cfm_sigma_x_minus_vxc_mo_basis%local_data(iib, jjb), kind=dp)
935 imval = aimag(cfm_sigma_x_minus_vxc_mo_basis%local_data(iib, jjb))
936
937 vec_sigma_x_minus_vxc_gw(i_global, ispin, ikp) = reval
938 vec_sigma_x_minus_vxc_gw_im(i_global, ispin, ikp) = imval
939
940 END IF
941
942 END DO
943
944 END DO
945
946 END DO
947
948 END DO
949
950 CALL para_env%sum(vec_sigma_x_minus_vxc_gw)
951 CALL para_env%sum(vec_sigma_x_minus_vxc_gw_im)
952 ! also adjust in the case of kpoints too big gw_corr_lev_occ and gw_corr_lev_virt
953 DO ispin = 1, nspins
954 CALL get_mo_set(mo_set=kpoints%kp_env(1)%kpoint_env%mos(ispin, 1), &
955 homo=homo, nao=dimen)
956 ! If SVD is used to invert overlap matrix (for CHOLESKY OFF), some MOs are removed
957 ! Therefore, setting the number of gw_corr_lev_virt simply to dimen - homo leads to index problems
958 ! Instead, we take into account the removed MOs
959 max_corr_lev_occ = homo
960 max_corr_lev_virt = nmo - homo
961
962 gw_corr_lev_occ = mp2_env%ri_g0w0%corr_mos_occ
963 gw_corr_lev_virt = mp2_env%ri_g0w0%corr_mos_virt
964 ! if corrected occ/virt levels exceed the number of occ/virt levels or are negative,
965 ! correct all occ/virt level energies
966 IF (gw_corr_lev_occ > homo .OR. gw_corr_lev_occ < 0) gw_corr_lev_occ = max_corr_lev_occ
967 IF (gw_corr_lev_virt > max_corr_lev_virt .OR. gw_corr_lev_virt < 0) gw_corr_lev_virt = max_corr_lev_virt
968 IF (ispin == 1) THEN
969 mp2_env%ri_g0w0%corr_mos_occ = gw_corr_lev_occ
970 mp2_env%ri_g0w0%corr_mos_virt = gw_corr_lev_virt
971 ELSE IF (ispin == 2) THEN
972 ! ensure that the total number of corrected MOs is the same for alpha and beta, important
973 ! for parallelization
974 IF (mp2_env%ri_g0w0%corr_mos_occ + mp2_env%ri_g0w0%corr_mos_virt /= &
975 gw_corr_lev_occ + gw_corr_lev_virt) THEN
976 gw_corr_lev_virt = mp2_env%ri_g0w0%corr_mos_occ + mp2_env%ri_g0w0%corr_mos_virt - gw_corr_lev_occ
977 END IF
978 mp2_env%ri_g0w0%corr_mos_occ_beta = gw_corr_lev_occ
979 mp2_env%ri_g0w0%corr_mos_virt_beta = gw_corr_lev_virt
980 END IF
981 END DO
982
983 CALL cp_fm_release(fwork_re)
984 CALL cp_fm_release(fwork_im)
985 CALL cp_cfm_release(cfm_mos)
986 CALL cp_cfm_release(cfm_sigma_x_minus_vxc)
987 CALL cp_cfm_release(cfm_sigma_x_minus_vxc_mo_basis)
988 CALL cp_cfm_release(cfm_tmp)
989
990 CALL timestop(handle)
991
992 END SUBROUTINE
993
994! **************************************************************************************************
995!> \brief ...
996!> \param matrix_ks_transl ...
997!> \param matrix_ks_kp_re ...
998!> \param matrix_ks_kp_im ...
999!> \param kpoints ...
1000! **************************************************************************************************
1001 SUBROUTINE transform_matrix_ks_to_kp(matrix_ks_transl, matrix_ks_kp_re, matrix_ks_kp_im, kpoints)
1002
1003 TYPE(dbcsr_p_type), DIMENSION(:, :), POINTER :: matrix_ks_transl, matrix_ks_kp_re, &
1004 matrix_ks_kp_im
1005 TYPE(kpoint_type), POINTER :: kpoints
1006
1007 CHARACTER(len=*), PARAMETER :: routinen = 'transform_matrix_ks_to_kp'
1008
1009 INTEGER :: handle, ikp, ispin, nkp, nspin
1010 INTEGER, DIMENSION(:, :, :), POINTER :: cell_to_index
1011 REAL(kind=dp), DIMENSION(:, :), POINTER :: xkp
1012 TYPE(neighbor_list_set_p_type), DIMENSION(:), &
1013 POINTER :: sab_nl
1014
1015 CALL timeset(routinen, handle)
1016
1017 NULLIFY (sab_nl)
1018 CALL get_kpoint_info(kpoints, nkp=nkp, xkp=xkp, sab_nl=sab_nl, cell_to_index=cell_to_index)
1019
1020 cpassert(ASSOCIATED(sab_nl))
1021
1022 nspin = SIZE(matrix_ks_transl, 1)
1023
1024 DO ikp = 1, nkp
1025 DO ispin = 1, nspin
1026
1027 CALL dbcsr_set(matrix_ks_kp_re(ispin, ikp)%matrix, 0.0_dp)
1028 CALL dbcsr_set(matrix_ks_kp_im(ispin, ikp)%matrix, 0.0_dp)
1029 CALL rskp_transform(rmatrix=matrix_ks_kp_re(ispin, ikp)%matrix, &
1030 cmatrix=matrix_ks_kp_im(ispin, ikp)%matrix, &
1031 rsmat=matrix_ks_transl, ispin=ispin, &
1032 xkp=xkp(1:3, ikp), cell_to_index=cell_to_index, sab_nl=sab_nl)
1033
1034 END DO
1035 END DO
1036
1037 CALL timestop(handle)
1038
1039 END SUBROUTINE
1040
1041! **************************************************************************************************
1042!> \brief ...
1043!> \param matrix_ks_transl ...
1044!> \param matrix_ks_kp_re ...
1045!> \param matrix_ks_kp_im ...
1046!> \param kpoints ...
1047! **************************************************************************************************
1048 SUBROUTINE allocate_matrix_ks_kp(matrix_ks_transl, matrix_ks_kp_re, matrix_ks_kp_im, kpoints)
1049
1050 TYPE(dbcsr_p_type), DIMENSION(:, :), POINTER :: matrix_ks_transl, matrix_ks_kp_re, &
1051 matrix_ks_kp_im
1052 TYPE(kpoint_type), POINTER :: kpoints
1053
1054 CHARACTER(len=*), PARAMETER :: routinen = 'allocate_matrix_ks_kp'
1055
1056 INTEGER :: handle, ikp, ispin, nkp, nspin
1057 INTEGER, DIMENSION(:, :, :), POINTER :: cell_to_index
1058 REAL(kind=dp), DIMENSION(:, :), POINTER :: xkp
1059 TYPE(neighbor_list_set_p_type), DIMENSION(:), &
1060 POINTER :: sab_nl
1061
1062 CALL timeset(routinen, handle)
1063
1064 NULLIFY (sab_nl)
1065 CALL get_kpoint_info(kpoints, nkp=nkp, xkp=xkp, sab_nl=sab_nl, cell_to_index=cell_to_index)
1066
1067 cpassert(ASSOCIATED(sab_nl))
1068
1069 nspin = SIZE(matrix_ks_transl, 1)
1070
1071 NULLIFY (matrix_ks_kp_re, matrix_ks_kp_im)
1072 CALL dbcsr_allocate_matrix_set(matrix_ks_kp_re, nspin, nkp)
1073 CALL dbcsr_allocate_matrix_set(matrix_ks_kp_im, nspin, nkp)
1074
1075 DO ikp = 1, nkp
1076 DO ispin = 1, nspin
1077
1078 ALLOCATE (matrix_ks_kp_re(ispin, ikp)%matrix)
1079 ALLOCATE (matrix_ks_kp_im(ispin, ikp)%matrix)
1080
1081 CALL dbcsr_create(matrix_ks_kp_re(ispin, ikp)%matrix, &
1082 template=matrix_ks_transl(1, 1)%matrix, &
1083 matrix_type=dbcsr_type_symmetric)
1084 CALL dbcsr_create(matrix_ks_kp_im(ispin, ikp)%matrix, &
1085 template=matrix_ks_transl(1, 1)%matrix, &
1086 matrix_type=dbcsr_type_antisymmetric)
1087
1088 CALL cp_dbcsr_alloc_block_from_nbl(matrix_ks_kp_re(ispin, ikp)%matrix, sab_nl)
1089 CALL cp_dbcsr_alloc_block_from_nbl(matrix_ks_kp_im(ispin, ikp)%matrix, sab_nl)
1090
1091 CALL dbcsr_set(matrix_ks_kp_re(ispin, ikp)%matrix, 0.0_dp)
1092 CALL dbcsr_set(matrix_ks_kp_im(ispin, ikp)%matrix, 0.0_dp)
1093
1094 END DO
1095 END DO
1096
1097 CALL timestop(handle)
1098
1099 END SUBROUTINE
1100
1101END MODULE rpa_gw_sigma_x
1102
Contains ADMM methods which require molecular orbitals.
subroutine, public admm_mo_merge_ks_matrix(qs_env)
...
Types and set/get functions for auxiliary density matrix methods.
Definition admm_types.F:15
subroutine, public get_admm_env(admm_env, mo_derivs_aux_fit, mos_aux_fit, sab_aux_fit, sab_aux_fit_asymm, sab_aux_fit_vs_orb, matrix_s_aux_fit, matrix_s_aux_fit_kp, matrix_s_aux_fit_vs_orb, matrix_s_aux_fit_vs_orb_kp, task_list_aux_fit, matrix_ks_aux_fit, matrix_ks_aux_fit_kp, matrix_ks_aux_fit_im, matrix_ks_aux_fit_dft, matrix_ks_aux_fit_hfx, matrix_ks_aux_fit_dft_kp, matrix_ks_aux_fit_hfx_kp, rho_aux_fit, rho_aux_fit_buffer, admm_dm)
Get routine for the ADMM env.
Definition admm_types.F:593
Auxiliary routines for GW + Bethe-Salpeter for computing electronic excitations.
Definition bse_util.F:13
subroutine, public determine_cutoff_indices(eigenval, homo, virtual, homo_red, virt_red, homo_incl, virt_incl, mp2_env)
Reads cutoffs for BSE from mp2_env and compares to energies in Eigenval to extract reduced homo/virtu...
Definition bse_util.F:1130
Basic linear algebra operations for complex full matrices.
subroutine, public cp_cfm_scale_and_add_fm(alpha, matrix_a, beta, matrix_b)
Scale and add two BLACS matrices (a = alpha*a + beta*b). where b is a real matrix (adapted from cp_cf...
Represents a complex full matrix distributed on many processors.
subroutine, public cp_cfm_create(matrix, matrix_struct, name)
Creates a new full matrix with the given structure.
subroutine, public cp_cfm_release(matrix)
Releases a full matrix.
subroutine, public cp_cfm_get_info(matrix, name, nrow_global, ncol_global, nrow_block, ncol_block, nrow_local, ncol_local, row_indices, col_indices, local_data, context, matrix_struct, para_env)
Returns information about a full matrix.
Defines control structures, which contain the parameters and the settings for the DFT-based calculati...
subroutine, public dbcsr_release_p(matrix)
...
subroutine, public dbcsr_desymmetrize(matrix_a, matrix_b)
...
subroutine, public dbcsr_copy(matrix_b, matrix_a, name, keep_sparsity, keep_imaginary)
...
subroutine, public dbcsr_multiply(transa, transb, alpha, matrix_a, matrix_b, beta, matrix_c, first_row, last_row, first_column, last_column, first_k, last_k, retain_sparsity, filter_eps, flop)
...
subroutine, public dbcsr_set(matrix, alpha)
...
subroutine, public dbcsr_release(matrix)
...
subroutine, public dbcsr_add(matrix_a, matrix_b, alpha_scalar, beta_scalar)
...
subroutine, public dbcsr_get_diag(matrix, diag)
Copies the diagonal elements from the given matrix into the given array.
DBCSR operations in CP2K.
subroutine, public copy_dbcsr_to_fm(matrix, fm)
Copy a DBCSR matrix to a BLACS matrix.
subroutine, public copy_fm_to_dbcsr(fm, matrix, keep_sparsity)
Copy a BLACS matrix to a dbcsr matrix.
Utility routines to open and close files. Tracking of preconnections.
Definition cp_files.F:16
subroutine, public open_file(file_name, file_status, file_form, file_action, file_position, file_pad, unit_number, debug, skip_get_unit_number, file_access)
Opens the requested file using a free unit number.
Definition cp_files.F:308
subroutine, public close_file(unit_number, file_status, keep_preconnection)
Close an open file given by its logical unit number. Optionally, keep the file and unit preconnected.
Definition cp_files.F:119
represent the structure of a full matrix
represent a full matrix distributed on many processors
Definition cp_fm_types.F:15
subroutine, public cp_fm_get_info(matrix, name, nrow_global, ncol_global, nrow_block, ncol_block, nrow_local, ncol_local, row_indices, col_indices, local_data, context, nrow_locals, ncol_locals, matrix_struct, para_env)
returns all kind of information about the full matrix
subroutine, public cp_fm_create(matrix, matrix_struct, name, use_sp)
creates a new full matrix with the given structure
Routines to calculate HFX energy and potential.
subroutine, public integrate_four_center(qs_env, x_data, ks_matrix, ehfx, rho_ao, hfx_section, para_env, geometry_did_change, irep, distribute_fock_matrix, ispin)
computes four center integrals for a full basis set and updates the Kohn-Sham-Matrix and energy....
Routines to calculate EXX in RPA and energy correction methods.
Definition hfx_exx.F:16
subroutine, public calc_exx_admm_xc_contributions(qs_env, matrix_prim, matrix_aux, x_data, exc, exc_aux_fit, calc_forces, use_virial)
Calculate the RI_RPAHF / EC_ENVHF ADMM XC contributions to the KS matrices and the respective energie...
Definition hfx_exx.F:629
subroutine, public exx_pre_hfx(ext_hfx_section, x_data, reuse_hfx)
Prepare the external x_data for integration. Simply change the HFX fraction in case the qs_envx_data ...
Definition hfx_exx.F:735
subroutine, public exx_post_hfx(qs_env, x_data, reuse_hfx)
Revert back to the proper HFX fraction in case qs_envx_data is reused.
Definition hfx_exx.F:760
RI-methods for HFX.
Definition hfx_ri.F:12
subroutine, public hfx_ri_update_ks(qs_env, ri_data, ks_matrix, ehfx, mos, rho_ao, geometry_did_change, nspins, hf_fraction)
...
Definition hfx_ri.F:1036
collects all constants needed in input so that they can be used without circular dependencies
integer, parameter, public do_admm_purify_none
integer, parameter, public gw_print_exx
integer, parameter, public do_admm_basis_projection
integer, parameter, public gw_read_exx
integer, parameter, public xc_none
objects that represent the structure of input sections and the data contained in an input section
subroutine, public section_vals_val_set(section_vals, keyword_name, i_rep_section, i_rep_val, val, l_val, i_val, r_val, c_val, l_vals_ptr, i_vals_ptr, r_vals_ptr, c_vals_ptr)
sets the requested value
recursive type(section_vals_type) function, pointer, public section_vals_get_subs_vals(section_vals, subsection_name, i_rep_section, can_return_null)
returns the values of the requested subsection
subroutine, public section_vals_get(section_vals, ref_count, n_repetition, n_subs_vals_rep, section, explicit)
returns various attributes about the section_vals
subroutine, public section_vals_val_get(section_vals, keyword_name, i_rep_section, i_rep_val, n_rep_val, val, l_val, i_val, r_val, c_val, l_vals, i_vals, r_vals, c_vals, explicit)
returns the requested value
Defines the basic variable types.
Definition kinds.F:23
integer, parameter, public dp
Definition kinds.F:34
Routines needed for kpoint calculation.
subroutine, public rskp_transform(rmatrix, cmatrix, rsmat, ispin, xkp, cell_to_index, sab_nl, is_complex, rs_sign)
Transformation of real space matrices to a kpoint.
Types and basic routines needed for a kpoint calculation.
subroutine, public get_kpoint_info(kpoint, kp_scheme, nkp_grid, kp_shift, symmetry, verbose, full_grid, use_real_wfn, eps_geo, parallel_group_size, kp_range, nkp, xkp, wkp, para_env, blacs_env_all, para_env_kp, para_env_inter_kp, blacs_env, kp_env, kp_aux_env, mpools, iogrp, nkp_groups, kp_dist, cell_to_index, index_to_cell, sab_nl, sab_nl_nosym)
Retrieve information from a kpoint environment.
Machine interface based on Fortran 2003 and POSIX.
Definition machine.F:17
real(kind=dp) function, public m_walltime()
returns time from a real-time clock, protected against rolling early/easily
Definition machine.F:147
Definition of mathematical constants and functions.
complex(kind=dp), parameter, public z_one
complex(kind=dp), parameter, public gaussi
complex(kind=dp), parameter, public z_zero
Interface to the message passing library MPI.
Routines to calculate and distribute 2c- and 3c- integrals for RI.
subroutine, public compute_kpoints(qs_env, kpoints, unit_nr)
...
Framework for 2c-integrals for RI.
Definition mp2_ri_2c.F:14
subroutine, public trunc_coulomb_for_exchange(qs_env, trunc_coulomb, rel_cutoff_trunc_coulomb_ri_x, cell_grid, do_bvk_cell)
...
Definition mp2_ri_2c.F:1613
Types needed for MP2 calculations.
Definition mp2_types.F:14
basic linear algebra operations for full matrixes
Definition of physical constants:
Definition physcon.F:68
real(kind=dp), parameter, public evolt
Definition physcon.F:183
subroutine, public get_qs_env(qs_env, atomic_kind_set, qs_kind_set, cell, super_cell, cell_ref, use_ref_cell, kpoints, dft_control, mos, sab_orb, sab_all, qmmm, qmmm_periodic, sac_ae, sac_ppl, sac_lri, sap_ppnl, sab_vdw, sab_scp, sap_oce, sab_lrc, sab_se, sab_xtbe, sab_tbe, sab_core, sab_xb, sab_xtb_pp, sab_xtb_nonbond, sab_almo, sab_kp, sab_kp_nosym, particle_set, energy, force, matrix_h, matrix_h_im, matrix_ks, matrix_ks_im, matrix_vxc, run_rtp, rtp, matrix_h_kp, matrix_h_im_kp, matrix_ks_kp, matrix_ks_im_kp, matrix_vxc_kp, kinetic_kp, matrix_s_kp, matrix_w_kp, matrix_s_ri_aux_kp, matrix_s, matrix_s_ri_aux, matrix_w, matrix_p_mp2, matrix_p_mp2_admm, rho, rho_xc, pw_env, ewald_env, ewald_pw, active_space, mpools, input, para_env, blacs_env, scf_control, rel_control, kinetic, qs_charges, vppl, rho_core, rho_nlcc, rho_nlcc_g, ks_env, ks_qmmm_env, wf_history, scf_env, local_particles, local_molecules, distribution_2d, dbcsr_dist, molecule_kind_set, molecule_set, subsys, cp_subsys, oce, local_rho_set, rho_atom_set, task_list, task_list_soft, rho0_atom_set, rho0_mpole, rhoz_set, ecoul_1c, rho0_s_rs, rho0_s_gs, do_kpoints, has_unit_metric, requires_mo_derivs, mo_derivs, mo_loc_history, nkind, natom, nelectron_total, nelectron_spin, efield, neighbor_list_id, linres_control, xas_env, virial, cp_ddapc_env, cp_ddapc_ewald, outer_scf_history, outer_scf_ihistory, x_data, et_coupling, dftb_potential, results, se_taper, se_store_int_env, se_nddo_mpole, se_nonbond_env, admm_env, lri_env, lri_density, exstate_env, ec_env, harris_env, dispersion_env, gcp_env, vee, rho_external, external_vxc, mask, mp2_env, bs_env, kg_env, wanniercentres, atprop, ls_scf_env, do_transport, transport_env, v_hartree_rspace, s_mstruct_changed, rho_changed, potential_changed, forces_up_to_date, mscfg_env, almo_scf_env, gradient_history, variable_history, embed_pot, spin_embed_pot, polar_env, mos_last_converged, eeq, rhs)
Get the QUICKSTEP environment.
routines that build the Kohn-Sham matrix (i.e calculate the coulomb and xc parts
subroutine, public qs_ks_build_kohn_sham_matrix(qs_env, calculate_forces, just_energy, print_active, ext_ks_matrix)
routine where the real calculations are made: the KS matrix is calculated
Definition and initialisation of the mo data type.
Definition qs_mo_types.F:22
subroutine, public get_mo_set(mo_set, maxocc, homo, lfomo, nao, nelectron, n_el_f, nmo, eigenvalues, occupation_numbers, mo_coeff, mo_coeff_b, uniform_occupation, kts, mu, flexible_electron_count)
Get the components of a MO set data structure.
Define the neighbor list data types and the corresponding functionality.
superstucture that hold various representations of the density and keeps track of which ones are vali...
subroutine, public qs_rho_get(rho_struct, rho_ao, rho_ao_im, rho_ao_kp, rho_ao_im_kp, rho_r, drho_r, rho_g, drho_g, tau_r, tau_g, rho_r_valid, drho_r_valid, rho_g_valid, drho_g_valid, tau_r_valid, tau_g_valid, tot_rho_r, tot_rho_g, rho_r_sccs, soft_valid, complex_rho_ao)
returns info about the density described by this object. If some representation is not available an e...
Routines treating GW and RPA calculations with kpoints.
subroutine, public get_bandstruc_and_k_dependent_mos(qs_env, eigenval_kp)
...
Routines to calculate EXX within GW.
subroutine, public compute_vec_sigma_x_minus_vxc_gw(qs_env, mp2_env, mos_mp2, energy_ex, energy_xc_admm, t3, unit_nr)
...
Routines for GW, continuous development [Jan Wilhelm].
Definition rpa_gw.F:14
subroutine, public trafo_to_mo_and_kpoints(qs_env, mat_self_energy_ao_ao, vec_sigma, homo, gw_corr_lev_occ, gw_corr_lev_virt, ispin)
...
Definition rpa_gw.F:6344
subroutine, public compute_minus_vxc_kpoints(qs_env)
...
Definition rpa_gw.F:6219
stores some data used in wavefunction fitting
Definition admm_types.F:120
Represent a complex full matrix.
keeps the information about the structure of a full matrix
represent a full matrix
Keeps information about a specific k-point.
Contains information about kpoints.
stores all the informations relevant to an mpi environment
calculation environment to calculate the ks matrix, holds all the needed vars. assumes that the core ...
keeps the density in various representations, keeping track of which ones are valid.