Branch data Line data Source code
1 : : !!****m* ABINIT/m_optics_vloc
2 : : !! NAME
3 : : !! m_optics_vloc
4 : : !!
5 : : !! FUNCTION
6 : : !!
7 : : !!
8 : : !! COPYRIGHT
9 : : !! Copyright (C) 2010-2026 ABINIT group (SM,VR,FJ,MT)
10 : : !! This file is distributed under the terms of the
11 : : !! GNU General Public License, see ~abinit/COPYING
12 : : !! or http://www.gnu.org/copyleft/gpl.txt .
13 : : !!
14 : : !! SOURCE
15 : :
16 : : #if defined HAVE_CONFIG_H
17 : : #include "config.h"
18 : : #endif
19 : :
20 : : #include "abi_common.h"
21 : :
22 : : module m_optics_vloc
23 : :
24 : : use defs_basis
25 : : use m_abicore
26 : : use m_errors
27 : : use m_wffile
28 : : use m_xmpi
29 : : use m_hdr
30 : : use m_dtset
31 : : use m_dtfil
32 : :
33 : : use defs_abitypes, only : MPI_type
34 : : use m_time, only : timab
35 : : use m_io_tools, only : get_unit
36 : : use m_mpinfo, only : proc_distrb_cycle
37 : :
38 : : implicit none
39 : :
40 : : private
41 : : !!***
42 : :
43 : : public :: optics_vloc
44 : : !!***
45 : :
46 : : contains
47 : : !!***
48 : :
49 : : !!****f* ABINIT/optics_vloc
50 : : !! NAME
51 : : !! optics_vloc
52 : : !!
53 : : !! FUNCTION
54 : : !! Compute matrix elements need for optical conductivity in a LOCAL potential
55 : : !! and store them in a file.
56 : : !! Matrix elements = <Phi_i|Nabla|Phi_j>
57 : : !!
58 : : !! INPUTS
59 : : !! cg(2,mcg)=planewave coefficients of wavefunctions.
60 : : !! dtfil <type(datafiles_type)>=variables related to files
61 : : !! dtset <type(dataset_type)>=all input variables for this dataset
62 : : !! fildata= name of the output file
63 : : !! gprimd(3,3)=dimensional reciprocal space primitive translations
64 : : !! kg(3,mpw*mkmem)=reduced planewave coordinates.
65 : : !! mband=maximum number of bands
66 : : !! mcg=size of wave-functions array (cg) =mpw*nspinor*mband*mkmem*nsppol
67 : : !! mkmem =number of k points treated by this node.
68 : : !! mpi_enreg=information about MPI parallelization
69 : : !! mpw=maximum dimensioned size of npw.
70 : : !! nkpt=number of k points.
71 : : !! npwarr(nkpt)=number of planewaves in basis at this k point
72 : : !! nsppol=1 for unpolarized, 2 for spin-polarized
73 : : !!
74 : : !! OUTPUT
75 : : !! (only writing in a file)
76 : : !!
77 : : !! SIDE EFFECTS
78 : : !!
79 : : !! NOTES
80 : : !!
81 : : !! SOURCE
82 : :
83 : 0 : subroutine optics_vloc(cg,dtfil,dtset,eigen0,gprimd,hdr,kg,mband,mcg,mkmem,mpi_enreg,mpw,&
84 : 0 : & nkpt,npwarr,nsppol)
85 : : !Arguments ------------------------------------
86 : : !scalars
87 : : integer,intent(in) :: mband,mcg,mkmem,mpw,nkpt,nsppol
88 : : type(datafiles_type),intent(in) :: dtfil
89 : : type(dataset_type),intent(in) :: dtset
90 : : type(MPI_type),intent(in) :: mpi_enreg
91 : : type(hdr_type),intent(inout) :: hdr
92 : : !arrays
93 : : integer,intent(in) :: kg(3,mpw*mkmem),npwarr(nkpt)
94 : : real(dp),intent(in) :: gprimd(3,3)
95 : : real(dp),intent(in) :: eigen0(mband*nkpt*nsppol)
96 : : real(dp),intent(inout) :: cg(2,mcg)
97 : :
98 : : !Local variables-------------------------------
99 : : !scalars
100 : : integer :: iomode,bdtot_index,cplex,etiq,fformopt,ib,icg,ierr,ikg,ikpt
101 : : integer :: ipw,isppol,istwf_k,iwavef,jb,jwavef
102 : : integer :: me,me_kpt,my_nspinor,nband_k,npw_k,sender,ount,pnp_size
103 : : integer :: spaceComm_band,spaceComm_bandfftspin,spaceComm_fft,spaceComm_k
104 : : logical :: mykpt
105 : : real(dp) :: cgnm1,cgnm2
106 : : character(len=500) :: msg
107 : : !arrays
108 : : integer :: tmp_shape(3)
109 : 0 : integer,allocatable :: kg_k(:,:)
110 : : real(dp) :: kpoint(3),tsec(2)
111 : 0 : real(dp),allocatable :: eig0_k(:),kpg_k(:,:)
112 : 0 : real(dp),allocatable :: psinablapsi(:,:,:,:),tnm(:,:,:,:)
113 : : type(wffile_type) :: wff1
114 : : ! ************************************************************************
115 : :
116 : : DBG_ENTER("COLL")
117 : :
118 : : !Compatibility tests
119 : :
120 : : !----------------------------------------------------------------------------------
121 : : !2- Computation of <psi_n|-i.nabla|psi_m> for each k
122 : : !----------------------------------------------------------------------------------
123 : :
124 : : !Init parallelism
125 [ # # ]: 0 : if (mpi_enreg%paral_kgb==1) then
126 : 0 : spaceComm_k=mpi_enreg%comm_kpt
127 : 0 : spaceComm_fft=mpi_enreg%comm_fft
128 : 0 : spaceComm_band=mpi_enreg%comm_band
129 : 0 : spaceComm_bandfftspin=mpi_enreg%comm_bandspinorfft
130 : 0 : me_kpt=mpi_enreg%me_kpt
131 : : else
132 : 0 : spaceComm_band=0;spaceComm_fft=0;spaceComm_bandfftspin=0
133 : 0 : spaceComm_k=mpi_enreg%comm_cell
134 : 0 : me=xmpi_comm_rank(spaceComm_k)
135 : 0 : me_kpt=me
136 : : end if
137 : 0 : my_nspinor=max(1,dtset%nspinor/mpi_enreg%nproc_spinor)
138 : :
139 : : !Initialize main variables
140 [ # # # # : 0 : ABI_MALLOC(psinablapsi,(2,3,mband,mband))
# # # # #
# # # # #
# # ]
141 [ # # ]: 0 : pnp_size=size(psinablapsi)
142 [ # # # # : 0 : psinablapsi=zero
# # # # ]
143 : :
144 : 0 : iomode= IO_MODE_FORTRAN_MASTER
145 : 0 : fformopt=612
146 : 0 : ount = get_unit()
147 : 0 : call WffOpen(iomode,spaceComm_k,dtfil%fnameabo_app_opt,ierr,wff1,0,me,ount)
148 : 0 : call hdr_io(fformopt,hdr,2,wff1)
149 : : !if (me == 0) then
150 : : !call hdr_fort_write(hdr, wff1%unwff, fformopt,ierr)
151 : : !ABI_CHECK(ierr /= 0, "hdr_fort_write returned ierr = 0")
152 : : !end if
153 : :
154 : : !LOOP OVER SPINS
155 : 0 : icg=0
156 [ # # ]: 0 : do isppol=1,nsppol
157 : :
158 : : ! LOOP OVER k POINTS
159 : 0 : ikg=0
160 [ # # ]: 0 : do ikpt=1,nkpt
161 : 0 : nband_k=dtset%nband(ikpt+(isppol-1)*nkpt)
162 : 0 : etiq=ikpt+(isppol-1)*nkpt
163 [ # # ]: 0 : if (me==0) then
164 [ # # # # : 0 : ABI_MALLOC(eig0_k,(nband_k))
# # # # #
# # # #
# ]
165 [ # # ]: 0 : eig0_k(:)=eigen0(1+bdtot_index:nband_k+bdtot_index)
166 : : end if
167 : :
168 : : ! Select my k-points
169 : 0 : mykpt=.true.
170 : 0 : mykpt=(.not.(proc_distrb_cycle(mpi_enreg%proc_distrb,ikpt,1,nband_k,isppol,me_kpt)))
171 [ # # ]: 0 : if (mykpt) then
172 : :
173 : : ! Allocations depending on k-point
174 [ # # ]: 0 : kpoint(:)=dtset%kptns(:,ikpt)
175 : 0 : istwf_k=dtset%istwfk(ikpt)
176 : 0 : npw_k=npwarr(ikpt)
177 [ # # ]: 0 : cplex=2;if (istwf_k>1) cplex=1
178 [ # # # # : 0 : ABI_MALLOC(kg_k,(3,npw_k))
# # # # #
# # # ]
179 [ # # # # : 0 : ABI_MALLOC(kpg_k,(npw_k*dtset%nspinor,3))
# # # # #
# # # ]
180 : :
181 : : ! Get G-vectors for this k-point
182 [ # # # # ]: 0 : kg_k(:,1:npw_k)=kg(:,1+ikg:npw_k+ikg)
183 : 0 : ikg=ikg+npw_k
184 : :
185 : : ! Calculation of k+G in cartesian coordinates
186 [ # # ]: 0 : do ipw=1,npw_k
187 : : kpg_k(ipw,1)=(kpoint(1)+kg_k(1,ipw))*gprimd(1,1)&
188 : : & +(kpoint(2)+kg_k(2,ipw))*gprimd(1,2)&
189 : 0 : & +(kpoint(3)+kg_k(3,ipw))*gprimd(1,3)
190 : : kpg_k(ipw,2)=(kpoint(1)+kg_k(1,ipw))*gprimd(2,1)&
191 : : & +(kpoint(2)+kg_k(2,ipw))*gprimd(2,2)&
192 : 0 : & +(kpoint(3)+kg_k(3,ipw))*gprimd(2,3)
193 : : kpg_k(ipw,3)=(kpoint(1)+kg_k(1,ipw))*gprimd(3,1)&
194 : : & +(kpoint(2)+kg_k(2,ipw))*gprimd(3,2)&
195 : 0 : & +(kpoint(3)+kg_k(3,ipw))*gprimd(3,3)
196 : : end do !ipw
197 [ # # # # ]: 0 : kpg_k=two_pi*kpg_k
198 [ # # # # : 0 : if (dtset%nspinor==2) kpg_k(npw_k+1:2*npw_k,1:3)=kpg_k(1:npw_k,1:3)
# # ]
199 [ # # ]: 0 : ABI_FREE(kg_k)
200 : :
201 : : ! 2-A Computation of <psi_tild_n|-i.nabla|psi_tild_m>
202 : : ! ----------------------------------------------------------------------------------
203 : : ! Computation of (C_nk^*)*C_mk*(k+g) in cartesian coordinates
204 : :
205 [ # # # # : 0 : ABI_MALLOC(tnm,(2,3,nband_k,nband_k))
# # # # #
# # # # #
# # # # ]
206 [ # # # # : 0 : tnm=zero
# # # # ]
207 : :
208 : : ! Loops on bands
209 [ # # ]: 0 : do jb=1,nband_k
210 : 0 : jwavef=(jb-1)*npw_k*my_nspinor+icg
211 [ # # ]: 0 : if (mpi_enreg%paral_kgb/=1) then
212 [ # # ]: 0 : tmp_shape = shape(mpi_enreg%proc_distrb)
213 [ # # ]: 0 : if (ikpt > tmp_shape(1)) then
214 : 0 : msg=' ikpt out of bounds '
215 : 0 : ABI_BUG(msg)
216 : : end if
217 [ # # ]: 0 : if (abs(mpi_enreg%proc_distrb(ikpt,jb,isppol)-me_kpt)/=0) cycle
218 : : end if
219 [ # # ]: 0 : do ib=1,jb
220 : 0 : iwavef=(ib-1)*npw_k*my_nspinor+icg
221 : :
222 : : ! Computation of (C_nk^*)*C_mk*(k+g) in cartesian coordinates
223 [ # # ]: 0 : if (cplex==1) then
224 [ # # ]: 0 : do ipw=1,npw_k*my_nspinor
225 : 0 : cgnm1=cg(1,ipw+iwavef)*cg(1,ipw+jwavef)
226 [ # # ]: 0 : tnm(1,1:3,ib,jb)=tnm(1,1:3,ib,jb)+cgnm1*kpg_k(ipw,1:3)
227 : : end do
228 : : else
229 [ # # ]: 0 : do ipw=1,npw_k*my_nspinor
230 : 0 : cgnm1=cg(1,ipw+iwavef)*cg(1,ipw+jwavef)+cg(2,ipw+iwavef)*cg(2,ipw+jwavef)
231 : 0 : cgnm2=cg(1,ipw+iwavef)*cg(2,ipw+jwavef)-cg(2,ipw+iwavef)*cg(1,ipw+jwavef)
232 [ # # ]: 0 : tnm(1,1:3,ib,jb)=tnm(1,1:3,ib,jb)+cgnm1*kpg_k(ipw,1:3)
233 [ # # ]: 0 : tnm(2,1:3,ib,jb)=tnm(2,1:3,ib,jb)+cgnm2*kpg_k(ipw,1:3)
234 : : end do
235 : : end if
236 : :
237 : : ! Second half of the (n,m) matrix
238 [ # # ]: 0 : if (ib/=jb) then
239 [ # # ]: 0 : tnm(1,1:3,jb,ib)= tnm(1,1:3,ib,jb)
240 [ # # ]: 0 : tnm(2,1:3,jb,ib)=-tnm(2,1:3,ib,jb)
241 : : end if
242 : :
243 : : end do ! ib
244 : : end do ! jb
245 : :
246 : : ! Reduction in case of parallelism
247 [ # # ]: 0 : if (mpi_enreg%paral_kgb == 1) then
248 : 0 : call timab(48,1,tsec)
249 : 0 : call xmpi_sum_master(tnm,0,spaceComm_bandfftspin,ierr)
250 : 0 : call timab(48,2,tsec)
251 : : end if
252 : :
253 [ # # # # : 0 : psinablapsi(:,:,:,:)=tnm(:,:,:,:)
# # # # ]
254 : :
255 [ # # ]: 0 : ABI_FREE(tnm)
256 : :
257 [ # # ]: 0 : if (mkmem/=0) then
258 : 0 : icg = icg + npw_k*my_nspinor*nband_k
259 : : end if
260 : :
261 [ # # ]: 0 : ABI_FREE(kpg_k)
262 : :
263 [ # # ]: 0 : if (me==0) then
264 : 0 : write(ount)(eig0_k(ib),ib=1,nband_k)
265 [ # # # # : 0 : write(ount)((psinablapsi(1:2,1,ib,jb),ib=1,nband_k),jb=1,nband_k)
# # # # ]
266 [ # # # # : 0 : write(ount)((psinablapsi(1:2,2,ib,jb),ib=1,nband_k),jb=1,nband_k)
# # # # ]
267 [ # # # # : 0 : write(ount)((psinablapsi(1:2,3,ib,jb),ib=1,nband_k),jb=1,nband_k)
# # # # ]
268 [ # # # # ]: 0 : elseif (mpi_enreg%me_band==0.and.mpi_enreg%me_fft==0) then
269 : 0 : call xmpi_exch(psinablapsi,pnp_size,me_kpt,psinablapsi,0,spaceComm_k,etiq,ierr)
270 : : end if
271 : :
272 [ # # ]: 0 : elseif (me==0) then
273 [ # # ]: 0 : sender=minval(mpi_enreg%proc_distrb(ikpt,1:nband_k,isppol))
274 : 0 : call xmpi_exch(psinablapsi,pnp_size,sender,psinablapsi,0,spaceComm_k,etiq,ierr)
275 : 0 : write(ount)(eig0_k(ib),ib=1,nband_k)
276 [ # # # # : 0 : write(ount)((psinablapsi(1:2,1,ib,jb),ib=1,nband_k),jb=1,nband_k)
# # # # ]
277 [ # # # # : 0 : write(ount)((psinablapsi(1:2,2,ib,jb),ib=1,nband_k),jb=1,nband_k)
# # # # ]
278 [ # # # # : 0 : write(ount)((psinablapsi(1:2,3,ib,jb),ib=1,nband_k),jb=1,nband_k)
# # # # ]
279 : : end if ! mykpt
280 : :
281 : 0 : bdtot_index=bdtot_index+nband_k
282 [ # # ]: 0 : if (me==0) then
283 [ # # ]: 0 : ABI_FREE(eig0_k)
284 : : end if
285 : : ! End loop on spin,kpt
286 : : end do ! ikpt
287 : : end do !isppol
288 : :
289 : : !Close file
290 : 0 : call WffClose(wff1,ierr)
291 : :
292 : : !Datastructures deallocations
293 [ # # ]: 0 : ABI_FREE(psinablapsi)
294 : :
295 : : DBG_EXIT("COLL")
296 : :
297 [ # # # # ]: 0 : end subroutine optics_vloc
298 : : !!***
299 : :
300 : : end module m_optics_vloc
301 : : !!***
|