diff --git a/src/array_mod.F90 b/src/array_mod.F90 index 5268f0d9d5e4768dc8b985b1ff491755674cba87..7e2e8ddb14fbe5a62c3ea32d4e81346a5aaa1c53 100644 --- a/src/array_mod.F90 +++ b/src/array_mod.F90 @@ -8,10 +8,14 @@ MODULE array COMPLEX(dp), DIMENSION(:,:,:,:,:), ALLOCATABLE :: moments_rhs_i ! (ip,ij,ikr,ikz,updatetlevel) ! To load collision matrix - REAL(dp), DIMENSION(:,:), ALLOCATABLE :: Ceepj, CeipjT - REAL(dp), DIMENSION(:,:), ALLOCATABLE :: CeipjF - REAL(dp), DIMENSION(:,:), ALLOCATABLE :: Ciipj, CiepjT - REAL(dp), DIMENSION(:,:), ALLOCATABLE :: CiepjF + REAL(dp), DIMENSION(:,:,:,:), ALLOCATABLE :: Ceepj, CeipjT + REAL(dp), DIMENSION(:,:,:,:), ALLOCATABLE :: CeipjF + REAL(dp), DIMENSION(:,:,:,:), ALLOCATABLE :: Ciipj, CiepjT + REAL(dp), DIMENSION(:,:,:,:), ALLOCATABLE :: CiepjF + + ! Collision term + COMPLEX(dp), DIMENSION(:,:,:,:), ALLOCATABLE :: TColl_e, TColl_i + COMPLEX(dp), DIMENSION(:,:,:,:), ALLOCATABLE :: TColl_e_local, TColl_i_local ! dnjs coefficient storage (in, ij, is) COMPLEX(dp), DIMENSION(:,:,:), ALLOCATABLE :: dnjs diff --git a/src/auxval.F90 b/src/auxval.F90 index 56fa89db92885dd11ab3ac73d79a26f6cdc7a6f1..2f57e672c3860f1eb5a2bb0bfcb777163b9d11e9 100644 --- a/src/auxval.F90 +++ b/src/auxval.F90 @@ -23,6 +23,7 @@ subroutine auxval CALL set_krgrid ! MPI Distributed dimension CALL set_kzgrid + CALL set_kpgrid CALL memory ! Allocate memory for global arrays diff --git a/src/collision_mod.F90 b/src/collision_mod.F90 index 406ba4c846ab94b2d4b1874ad455441c0c3fccf0..26b2be7dd5b6b3d38e24f3ca9503bc57b05a911f 100644 --- a/src/collision_mod.F90 +++ b/src/collision_mod.F90 @@ -1,31 +1,28 @@ module collision ! contains the Hermite-Laguerre collision operators. Solved using COSOlver. - -implicit none - -PUBLIC :: load_FC_mat +USE fields +USE array +USE basic +USE grid +USE prec_const +USE time_integration +USE model +IMPLICIT NONE + +PUBLIC :: compute_TColl PUBLIC :: DoughertyGK_e, DoughertyGK_i - +PUBLIC :: load_COSOlver_mat +PUBLIC :: apply_COSOlver_mat_e, apply_COSOlver_mat_i CONTAINS - !******************************************************************************! - SUBROUTINE LenardBernsteinDK - - END SUBROUTINE LenardBernsteinDK !******************************************************************************! !! Doughtery gyrokinetic collision operator for electrons - SUBROUTINE DoughertyGK_e(ip,ij,ikr,ikz,TColl) - USE fields, ONLY: moments_e, phi - USE array, ONLY: Kernel_e - USE basic - USE grid, ONLY: jmaxe, parray_e, jarray_e, krarray, kzarray - USE prec_const - USE time_integration, ONLY: updatetlevel - USE model, ONLY: sigmae2_taue_o2, tau_e, nu_e, q_e + !******************************************************************************! + SUBROUTINE DoughertyGK_e(ip_,ij_,ikr_,ikz_,TColl_) IMPLICIT NONE - INTEGER, INTENT(IN) :: ip,ij,ikr,ikz - COMPLEX(dp), INTENT(INOUT) :: TColl + INTEGER, INTENT(IN) :: ip_,ij_,ikr_,ikz_ + COMPLEX(dp), INTENT(INOUT) :: TColl_ COMPLEX(dp) :: n_,upar_,uperp_,Tpar_, Tperp_ COMPLEX(dp) :: Dpj, Ppj, T_, ibe_ @@ -34,20 +31,20 @@ CONTAINS REAL(dp) :: n_dp, j_dp, p_dp, be_2, q_e_tau_e !** Auxiliary variables ** - p_dp = REAL(parray_e(ip),dp) - j_dp = REAL(jarray_e(ij),dp) - be_2 = (krarray(ikr)**2 + kzarray(ikz)**2) * sigmae2_taue_o2 + p_dp = REAL(parray_e(ip_),dp) + j_dp = REAL(jarray_e(ij_),dp) + be_2 = (krarray(ikr_)**2 + kzarray(ikz_)**2) * sigmae2_taue_o2 ibe_ = imagu*2._dp*SQRT(be_2) q_e_tau_e = q_e/tau_e !** Assembling collison operator ** ! Velocity-space diffusion (similar to Lenhard Bernstein) - TColl = -(p_dp + 2._dp*j_dp + be_2)*moments_e(ip,ij,ikr,ikz,updatetlevel) + TColl_ = -(p_dp + 2._dp*j_dp + be_2)*moments_e(ip_,ij_,ikr_,ikz_,updatetlevel) !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! Non zero term for p = 0 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! IF( p_dp .EQ. 0 ) THEN ! Kronecker p0 ! Get adiabatic moment - TColl = TColl - (p_dp + 2._dp*j_dp + be_2) * q_e_tau_e * Kernel_e(ij,ikr,ikz)*phi(ikr,ikz) + TColl_ = TColl_ - (p_dp + 2._dp*j_dp + be_2) * q_e_tau_e * Kernel_e(ij_,ikr_,ikz_)*phi(ikr_,ikz_) !** build required fluid moments ** n_ = 0._dp upar_ = 0._dp; uperp_ = 0._dp @@ -55,27 +52,27 @@ CONTAINS DO in_ = 1,jmaxe+1 n_dp = REAL(in_-1,dp) ! Nonadiabatic moments (only different from moments when p=0) - nadiab_moment_0j = moments_e(1,in_ ,ikr,ikz,updatetlevel) + q_e_tau_e * kernel_e(in_ ,ikr,ikz)*phi(ikr,ikz) - nadiab_moment_0jp1 = moments_e(1,in_+1,ikr,ikz,updatetlevel) + q_e_tau_e * kernel_e(in_+1,ikr,ikz)*phi(ikr,ikz) - nadiab_moment_0jm1 = moments_e(1,in_-1,ikr,ikz,updatetlevel) + q_e_tau_e * kernel_e(in_-1,ikr,ikz)*phi(ikr,ikz) + nadiab_moment_0j = moments_e(1,in_ ,ikr_,ikz_,updatetlevel) + q_e_tau_e * kernel_e(in_ ,ikr_,ikz_)*phi(ikr_,ikz_) + nadiab_moment_0jp1 = moments_e(1,in_+1,ikr_,ikz_,updatetlevel) + q_e_tau_e * kernel_e(in_+1,ikr_,ikz_)*phi(ikr_,ikz_) + nadiab_moment_0jm1 = moments_e(1,in_-1,ikr_,ikz_,updatetlevel) + q_e_tau_e * kernel_e(in_-1,ikr_,ikz_)*phi(ikr_,ikz_) ! Density - n_ = n_ + Kernel_e(in_,ikr,ikz) * nadiab_moment_0j + n_ = n_ + Kernel_e(in_,ikr_,ikz_) * nadiab_moment_0j ! Perpendicular velocity - uperp_ = uperp_ + ibe_*0.5_dp*Kernel_e(in_,ikr,ikz) * (nadiab_moment_0j - nadiab_moment_0jp1) + uperp_ = uperp_ + ibe_*0.5_dp*Kernel_e(in_,ikr_,ikz_) * (nadiab_moment_0j - nadiab_moment_0jp1) ! Parallel temperature - Tpar_ = Tpar_ + Kernel_e(in_,ikr,ikz) * (SQRT2*moments_e(3,in_,ikr,ikz,updatetlevel) + nadiab_moment_0j) + Tpar_ = Tpar_ + Kernel_e(in_,ikr_,ikz_) * (SQRT2*moments_e(3,in_,ikr_,ikz_,updatetlevel) + nadiab_moment_0j) ! Perpendicular temperature - Tperp_ = Tperp_ + Kernel_e(in_,ikr,ikz) * ((2._dp*n_dp+1._dp)* nadiab_moment_0j & + Tperp_ = Tperp_ + Kernel_e(in_,ikr_,ikz_) * ((2._dp*n_dp+1._dp)* nadiab_moment_0j & - n_dp * nadiab_moment_0jm1 & - (n_dp+1)* nadiab_moment_0jp1) ENDDO T_ = (Tpar_ + 2._dp*Tperp_)/3._dp - n_ ! Add energy restoring term - TColl = TColl + T_* 4._dp * j_dp * Kernel_e(ij ,ikr,ikz) - TColl = TColl - T_* 2._dp * (j_dp + 1._dp) * Kernel_e(ij+1,ikr,ikz) - TColl = TColl - T_* 2._dp * j_dp * Kernel_e(ij-1,ikr,ikz) - TColl = TColl + uperp_*ibe_*((j_dp + 1._dp)* Kernel_e(ij ,ikr,ikz) & - -j_dp * Kernel_e(ij-1,ikr,ikz)) + TColl_ = TColl_ + T_* 4._dp * j_dp * Kernel_e(ij_ ,ikr_,ikz_) + TColl_ = TColl_ - T_* 2._dp * (j_dp + 1._dp) * Kernel_e(ij_+1,ikr_,ikz_) + TColl_ = TColl_ - T_* 2._dp * j_dp * Kernel_e(ij_-1,ikr_,ikz_) + TColl_ = TColl_ + uperp_*ibe_*((j_dp + 1._dp)* Kernel_e(ij_ ,ikr_,ikz_) & + -j_dp * Kernel_e(ij_-1,ikr_,ikz_)) !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! Non zero term for p = 1 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! @@ -84,9 +81,9 @@ CONTAINS upar_ = 0._dp DO in_ = 1,jmaxe+1 ! Parallel velocity - upar_ = upar_ + Kernel_e(in_,ikr,ikz) * moments_e(2,in_,ikr,ikz,updatetlevel) + upar_ = upar_ + Kernel_e(in_,ikr_,ikz_) * moments_e(2,in_,ikr_,ikz_,updatetlevel) ENDDO - TColl = TColl + upar_*Kernel_e(ij,ikr,ikz) + TColl_ = TColl_ + upar_*Kernel_e(ij_,ikr_,ikz_) !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! Non zero term for p = 2 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! @@ -97,39 +94,32 @@ CONTAINS DO in_ = 1,jmaxe+1 n_dp = REAL(in_-1,dp) ! Nonadiabatic moments (only different from moments when p=0) - nadiab_moment_0j = moments_e(1,in_ ,ikr,ikz,updatetlevel) + q_e_tau_e * kernel_e(in_ ,ikr,ikz)*phi(ikr,ikz)/tau_e - nadiab_moment_0jp1 = moments_e(1,in_+1,ikr,ikz,updatetlevel) + q_e_tau_e * kernel_e(in_+1,ikr,ikz)*phi(ikr,ikz)/tau_e - nadiab_moment_0jm1 = moments_e(1,in_-1,ikr,ikz,updatetlevel) + q_e_tau_e * kernel_e(in_-1,ikr,ikz)*phi(ikr,ikz)/tau_e + nadiab_moment_0j = moments_e(1,in_ ,ikr_,ikz_,updatetlevel) + q_e_tau_e * kernel_e(in_ ,ikr_,ikz_)*phi(ikr_,ikz_)/tau_e + nadiab_moment_0jp1 = moments_e(1,in_+1,ikr_,ikz_,updatetlevel) + q_e_tau_e * kernel_e(in_+1,ikr_,ikz_)*phi(ikr_,ikz_)/tau_e + nadiab_moment_0jm1 = moments_e(1,in_-1,ikr_,ikz_,updatetlevel) + q_e_tau_e * kernel_e(in_-1,ikr_,ikz_)*phi(ikr_,ikz_)/tau_e ! Density - n_ = n_ + Kernel_e(in_,ikr,ikz) * nadiab_moment_0j + n_ = n_ + Kernel_e(in_,ikr_,ikz_) * nadiab_moment_0j ! Parallel temperature - Tpar_ = Tpar_ + Kernel_e(in_,ikr,ikz) * (SQRT2*moments_e(3,in_,ikr,ikz,updatetlevel) + nadiab_moment_0j) + Tpar_ = Tpar_ + Kernel_e(in_,ikr_,ikz_) * (SQRT2*moments_e(3,in_,ikr_,ikz_,updatetlevel) + nadiab_moment_0j) ! Perpendicular temperature - Tperp_ = Tperp_ + Kernel_e(in_,ikr,ikz) * ((2._dp*n_dp+1._dp)*nadiab_moment_0j - n_dp*nadiab_moment_0jm1 - (n_dp+1)*nadiab_moment_0jp1) + Tperp_ = Tperp_ + Kernel_e(in_,ikr_,ikz_) * ((2._dp*n_dp+1._dp)*nadiab_moment_0j - n_dp*nadiab_moment_0jm1 - (n_dp+1)*nadiab_moment_0jp1) ENDDO T_ = (Tpar_ + 2._dp*Tperp_)/3._dp - n_ - TColl = TColl + T_*SQRT2*Kernel_e(ij,ikr,ikz) + TColl_ = TColl_ + T_*SQRT2*Kernel_e(ij_,ikr_,ikz_) !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! ENDIF ! Multiply by electron-ion collision coefficient - TColl = nu_e * TColl + TColl_ = nu_e * TColl_ END SUBROUTINE DoughertyGK_e !******************************************************************************! !! Doughtery gyrokinetic collision operator for electrons - SUBROUTINE DoughertyGK_i(ip,ij,ikr,ikz,TColl) - USE fields, ONLY: moments_i, phi - USE array, ONLY: Kernel_i - USE basic - USE grid, ONLY: jmaxi, parray_i, jarray_i, krarray, kzarray - USE prec_const - USE time_integration, ONLY: updatetlevel - USE model, ONLY: sigmai2_taui_o2, tau_i, nu_i, q_i + SUBROUTINE DoughertyGK_i(ip_,ij_,ikr_,ikz_,TColl_) IMPLICIT NONE - INTEGER, INTENT(IN) :: ip,ij,ikr,ikz - COMPLEX(dp), INTENT(INOUT) :: TColl + INTEGER, INTENT(IN) :: ip_,ij_,ikr_,ikz_ + COMPLEX(dp), INTENT(INOUT) :: TColl_ COMPLEX(dp) :: n_,upar_,uperp_,Tpar_, Tperp_ COMPLEX(dp) :: Dpj, Ppj, T_, ibi_ @@ -138,20 +128,20 @@ CONTAINS REAL(dp) :: n_dp, j_dp, p_dp, bi_2, q_i_tau_i !** Auxiliary variables ** - p_dp = REAL(parray_i(ip),dp) - j_dp = REAL(jarray_i(ij),dp) - bi_2 = (krarray(ikr)**2 + kzarray(ikz)**2) * sigmai2_taui_o2 + p_dp = REAL(parray_i(ip_),dp) + j_dp = REAL(jarray_i(ij_),dp) + bi_2 = (krarray(ikr_)**2 + kzarray(ikz_)**2) * sigmai2_taui_o2 ibi_ = imagu*2._dp*SQRT(bi_2) q_i_tau_i = q_i/tau_i !** Assembling collison operator ** ! Velocity-space diffusion (similar to Lenhard Bernstein) - TColl = -(p_dp + 2._dp*j_dp + bi_2)*moments_i(ip,ij,ikr,ikz,updatetlevel) + TColl_ = -(p_dp + 2._dp*j_dp + bi_2)*moments_i(ip_,ij_,ikr_,ikz_,updatetlevel) !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! Non zero term for p = 0 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! IF( p_dp .EQ. 0 ) THEN ! Kronecker p0 ! Get adiabatic moment - TColl = TColl - (p_dp + 2._dp*j_dp + bi_2) * q_i_tau_i * Kernel_i(ij,ikr,ikz)*phi(ikr,ikz) + TColl_ = TColl_ - (p_dp + 2._dp*j_dp + bi_2) * q_i_tau_i * Kernel_i(ij_,ikr_,ikz_)*phi(ikr_,ikz_) !** build required fluid moments ** n_ = 0._dp upar_ = 0._dp; uperp_ = 0._dp @@ -159,27 +149,27 @@ CONTAINS DO in_ = 1,jmaxi+1 n_dp = REAL(in_-1,dp) ! Nonadiabatic moments (only different from moments when p=0) - nadiab_moment_0j = moments_i(1,in_ ,ikr,ikz,updatetlevel) + q_i_tau_i * kernel_i(in_ ,ikr,ikz)*phi(ikr,ikz) - nadiab_moment_0jp1 = moments_i(1,in_+1,ikr,ikz,updatetlevel) + q_i_tau_i * kernel_i(in_+1,ikr,ikz)*phi(ikr,ikz) - nadiab_moment_0jm1 = moments_i(1,in_-1,ikr,ikz,updatetlevel) + q_i_tau_i * kernel_i(in_-1,ikr,ikz)*phi(ikr,ikz) + nadiab_moment_0j = moments_i(1,in_ ,ikr_,ikz_,updatetlevel) + q_i_tau_i * kernel_i(in_ ,ikr_,ikz_)*phi(ikr_,ikz_) + nadiab_moment_0jp1 = moments_i(1,in_+1,ikr_,ikz_,updatetlevel) + q_i_tau_i * kernel_i(in_+1,ikr_,ikz_)*phi(ikr_,ikz_) + nadiab_moment_0jm1 = moments_i(1,in_-1,ikr_,ikz_,updatetlevel) + q_i_tau_i * kernel_i(in_-1,ikr_,ikz_)*phi(ikr_,ikz_) ! Density - n_ = n_ + Kernel_i(in_,ikr,ikz) * nadiab_moment_0j + n_ = n_ + Kernel_i(in_,ikr_,ikz_) * nadiab_moment_0j ! Perpendicular velocity - uperp_ = uperp_ + ibi_*0.5_dp*Kernel_i(in_,ikr,ikz) * (nadiab_moment_0j -nadiab_moment_0jp1) + uperp_ = uperp_ + ibi_*0.5_dp*Kernel_i(in_,ikr_,ikz_) * (nadiab_moment_0j -nadiab_moment_0jp1) ! Parallel temperature - Tpar_ = Tpar_ + Kernel_i(in_,ikr,ikz) * (SQRT2*moments_i(3,in_,ikr,ikz,updatetlevel) + nadiab_moment_0j) + Tpar_ = Tpar_ + Kernel_i(in_,ikr_,ikz_) * (SQRT2*moments_i(3,in_,ikr_,ikz_,updatetlevel) + nadiab_moment_0j) ! Perpendicular temperature - Tperp_ = Tperp_ + Kernel_i(in_,ikr,ikz) * ((2._dp*n_dp+1._dp)* nadiab_moment_0j & + Tperp_ = Tperp_ + Kernel_i(in_,ikr_,ikz_) * ((2._dp*n_dp+1._dp)* nadiab_moment_0j & - n_dp * nadiab_moment_0jm1 & - (n_dp+1)* nadiab_moment_0jp1) ENDDO T_ = (Tpar_ + 2._dp*Tperp_)/3._dp - n_ ! Add energy restoring term - TColl = TColl + T_* 4._dp * j_dp * Kernel_i(ij ,ikr,ikz) - TColl = TColl - T_* 2._dp * (j_dp + 1._dp) * Kernel_i(ij+1,ikr,ikz) - TColl = TColl - T_* 2._dp * j_dp * Kernel_i(ij-1,ikr,ikz) - TColl = TColl + uperp_*ibi_*((j_dp + 1._dp)* Kernel_i(ij ,ikr,ikz) & - -j_dp * Kernel_i(ij-1,ikr,ikz)) + TColl_ = TColl_ + T_* 4._dp * j_dp * Kernel_i(ij_ ,ikr_,ikz_) + TColl_ = TColl_ - T_* 2._dp * (j_dp + 1._dp) * Kernel_i(ij_+1,ikr_,ikz_) + TColl_ = TColl_ - T_* 2._dp * j_dp * Kernel_i(ij_-1,ikr_,ikz_) + TColl_ = TColl_ + uperp_*ibi_*((j_dp + 1._dp)* Kernel_i(ij_ ,ikr_,ikz_) & + -j_dp * Kernel_i(ij_-1,ikr_,ikz_)) !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! Non zero term for p = 1 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! @@ -188,9 +178,9 @@ CONTAINS upar_ = 0._dp DO in_ = 1,jmaxi+1 ! Parallel velocity - upar_ = upar_ + Kernel_i(in_,ikr,ikz) * moments_i(2,in_,ikr,ikz,updatetlevel) + upar_ = upar_ + Kernel_i(in_,ikr_,ikz_) * moments_i(2,in_,ikr_,ikz_,updatetlevel) ENDDO - TColl = TColl + upar_*Kernel_i(ij,ikr,ikz) + TColl_ = TColl_ + upar_*Kernel_i(ij_,ikr_,ikz_) !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! Non zero term for p = 2 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! @@ -201,128 +191,193 @@ CONTAINS DO in_ = 1,jmaxi+1 n_dp = REAL(in_-1,dp) ! Nonadiabatic moments (only different from moments when p=0) - nadiab_moment_0j = moments_i(1,in_ ,ikr,ikz,updatetlevel) + q_i_tau_i * kernel_i(in_ ,ikr,ikz)*phi(ikr,ikz) - nadiab_moment_0jp1 = moments_i(1,in_+1,ikr,ikz,updatetlevel) + q_i_tau_i * kernel_i(in_+1,ikr,ikz)*phi(ikr,ikz) - nadiab_moment_0jm1 = moments_i(1,in_-1,ikr,ikz,updatetlevel) + q_i_tau_i * kernel_i(in_-1,ikr,ikz)*phi(ikr,ikz) + nadiab_moment_0j = moments_i(1,in_ ,ikr_,ikz_,updatetlevel) + q_i_tau_i * kernel_i(in_ ,ikr_,ikz_)*phi(ikr_,ikz_) + nadiab_moment_0jp1 = moments_i(1,in_+1,ikr_,ikz_,updatetlevel) + q_i_tau_i * kernel_i(in_+1,ikr_,ikz_)*phi(ikr_,ikz_) + nadiab_moment_0jm1 = moments_i(1,in_-1,ikr_,ikz_,updatetlevel) + q_i_tau_i * kernel_i(in_-1,ikr_,ikz_)*phi(ikr_,ikz_) ! Density - n_ = n_ + Kernel_i(in_,ikr,ikz) * nadiab_moment_0j + n_ = n_ + Kernel_i(in_,ikr_,ikz_) * nadiab_moment_0j ! Parallel temperature - Tpar_ = Tpar_ + Kernel_i(in_,ikr,ikz) * (SQRT2*moments_i(3,in_,ikr,ikz,updatetlevel) + nadiab_moment_0j) + Tpar_ = Tpar_ + Kernel_i(in_,ikr_,ikz_) * (SQRT2*moments_i(3,in_,ikr_,ikz_,updatetlevel) + nadiab_moment_0j) ! Perpendicular temperature - Tperp_ = Tperp_ + Kernel_i(in_,ikr,ikz) * ((2._dp*n_dp+1._dp)*nadiab_moment_0j - n_dp*nadiab_moment_0jm1 - (n_dp+1)*nadiab_moment_0jp1) + Tperp_ = Tperp_ + Kernel_i(in_,ikr_,ikz_) * ((2._dp*n_dp+1._dp)*nadiab_moment_0j - n_dp*nadiab_moment_0jm1 - (n_dp+1)*nadiab_moment_0jp1) ENDDO T_ = (Tpar_ + 2._dp*Tperp_)/3._dp - n_ - TColl = TColl + T_*SQRT2*Kernel_i(ij,ikr,ikz) + TColl_ = TColl_ + T_*SQRT2*Kernel_i(ij_,ikr_,ikz_) !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! ENDIF ! Multiply by ion-ion collision coefficient - TColl = nu_i * TColl + TColl_ = nu_i * TColl_ END SUBROUTINE DoughertyGK_i !******************************************************************************! - !!!!!!! Compute ion Full Coulomb collision operator + !! compute the collision terms in a (Np x Nj x Nkr x Nkz) matrix all at once + !******************************************************************************! + SUBROUTINE compute_TColl + IMPLICIT NONE + COMPLEX(dp), DIMENSION(1:pmaxe+1) :: local_sum_e, buffer_e, total_sum_e + COMPLEX(dp), DIMENSION(ips_e:ipe_e) :: TColl_distr_e + COMPLEX(dp), DIMENSION(1:pmaxi+1) :: local_sum_i, buffer_i, total_sum_i + COMPLEX(dp), DIMENSION(ips_i:ipe_i) :: TColl_distr_i + COMPLEX(dp) :: TColl + INTEGER :: ikrs_C, ikre_C, ikzs_C, ikze_C + IF (ABS(CO) .GE. 2) THEN !compute only if COSOlver matrices are used + + DO ikr = ikrs,ikre + DO ikz = ikzs,ikze + ! Electrons + DO ij = 1,Jmaxe+1 + ! Loop over all p to compute sub collision term + DO ip = 1,Pmaxe+1 + CALL apply_COSOlver_mat_e(ip,ij,ikr,ikz,TColl) + local_sum_e(ip) = TColl + ENDDO + ! Sum up all the sub collision terms on root 0 + CALL MPI_REDUCE(local_sum_e, buffer_e, pmaxe+1, MPI_DOUBLE_COMPLEX, MPI_SUM, 0, comm_p, ierr) + ! IF(rank_p .EQ. 0) THEN + ! DO ip = 1,Pmaxe+1 + ! total_sum_e(ip) = buffer_e(ip) + ! ENDDO + ! ENDIF + ! distribute the sum over the process among p + CALL MPI_SCATTERV(buffer_e, counts_np_e, displs_np_e, MPI_DOUBLE_COMPLEX,& + TColl_distr_e, local_np_e, MPI_DOUBLE_COMPLEX,& + 0, comm_p, ierr) + DO ip = ips_e,ipe_e + TColl_e(ip,ij,ikr,ikz) = TColl_distr_e(ip) + ENDDO + ENDDO + ! Ions + DO ij = 1,Jmaxi+1 + DO ip = 1,Pmaxi+1 + CALL apply_COSOlver_mat_i(ip,ij,ikr,ikz,TColl) + local_sum_i(ip) = TColl + ENDDO + ! Reduce the local_sums to root = 0 + CALL MPI_REDUCE(local_sum_i, buffer_i, pmaxi+1, MPI_DOUBLE_COMPLEX, MPI_SUM, 0, comm_p, ierr) + ! IF(rank_p .EQ. 0) THEN + ! DO ip = 1,Pmaxi+1 + ! total_sum_i(ip) = buffer_i(ip) + ! ENDDO + ! ENDIF + ! buffer_e contains the entire collision term along p, scatter it among + ! the other processes (use of scatterv since Pmax/Np is not an integer) + CALL MPI_SCATTERV(buffer_i, counts_np_i, displs_np_i, MPI_DOUBLE_COMPLEX,& + TColl_distr_i, local_np_i, MPI_DOUBLE_COMPLEX, & + 0, comm_p, ierr) + DO ip = ips_i,ipe_i + TColl_i(ip,ij,ikr,ikz) = TColl_distr_i(ip) + ENDDO + ENDDO + ENDDO + ENDDO + ENDIF + ! IF(cstep .EQ. 1) THEN + ! write(*,*) rank_p, ': local_sum = ', local_sum_e + ! write(*,*) rank_p, ': buffer = ', buffer_e + ! write(*,*) rank_p, ': dist_sum = ', TColl_distr_e + ! ENDIF + + END SUBROUTINE compute_TColl + + !******************************************************************************! + !!!!!!! Compute ion collision term !******************************************************************************! - SUBROUTINE FullCoulombDK_e(p_int,j_int,ikr,ikz,TColl) - USE basic - USE fields, ONLY: moments_i, moments_e - USE array, ONLY: Ceepj, CeipjT, CeipjF - USE grid, ONLY: pmaxe,jmaxe, pmaxi,jmaxi, parray_e, parray_i, & - jarray_e, jarray_i, bari, bare - USE prec_const - USE time_integration, ONLY: updatetlevel - USE model, ONLY: nu_e, nu_ee + SUBROUTINE apply_COSOlver_mat_e(ip_,ij_,ikr_,ikz_,TColl_) IMPLICIT NONE - INTEGER, INTENT(IN) :: p_int,j_int ,ikr,ikz - COMPLEX(dp), INTENT(INOUT) :: TColl + INTEGER, INTENT(IN) :: ip_, ij_ ,ikr_, ikz_ + COMPLEX(dp), INTENT(OUT) :: TColl_ - INTEGER :: ip2,ij2, p2_int,j2_int + INTEGER :: ip2,ij2, p_int,j_int, p2_int,j2_int, ikr_C, ikz_C + p_int = ip_-1; j_int = ij_-1 - TColl = 0._dp ! Initialization + IF (CO .GT. 0) THEN ! GK operator (k-dependant) + ikr_C = ikr_; ikz_C = ikz_ + ELSEIF (CO .LT. 0) THEN ! DK operator (only one mat for every k) + ikr_C = 1; ikz_C = 1 + ENDIF + + TColl_ = 0._dp ! Initialization of the local sum - ploopee: DO ip2 = 1,pmaxe+1 ! sum the electron-self and electron-ion test terms + ! sum the electron-self and electron-ion test terms + ploopee: DO ip2 = ips_e,ipe_e p2_int = parray_e(ip2) - jloopee: DO ij2 = 1,jmaxe+1 + jloopee: DO ij2 = ijs_e,ije_e j2_int = jarray_e(ij2) - TColl = TColl + moments_e(ip2,ij2,ikr,ikz,updatetlevel) & - *( nu_e * CeipjT(bare(p_int,j_int), bare(p2_int,j2_int)) & - +nu_ee * Ceepj (bare(p_int,j_int), bare(p2_int,j2_int))) + TColl_ = TColl_ + moments_e(ip2,ij2,ikr_,ikz_,updatetlevel) & + *( nu_e * CeipjT(bare(p_int,j_int), bare(p2_int,j2_int),ikr_C, ikz_C) & + +nu_ee * Ceepj (bare(p_int,j_int), bare(p2_int,j2_int),ikr_C, ikz_C)) ENDDO jloopee ENDDO ploopee - ploopei: DO ip2 = 1,pmaxi+1 ! sum the electron-ion field terms + + ! sum the electron-ion field terms + ploopei: DO ip2 = ips_i,ipe_i p2_int = parray_i(ip2) - jloopei: DO ij2 = 1,jmaxi+1 + jloopei: DO ij2 = ijs_i,ije_i j2_int = jarray_i(ij2) - TColl = TColl + moments_i(ip2,ij2,ikr,ikz,updatetlevel) & - *(nu_e * CeipjF(bare(p_int,j_int), bari(p2_int,j2_int))) + TColl_ = TColl_ + moments_i(ip2,ij2,ikr_,ikz_,updatetlevel) & + *(nu_e * CeipjF(bare(p_int,j_int), bari(p2_int,j2_int),ikr_C, ikz_C)) END DO jloopei ENDDO ploopei - END SUBROUTINE FullCoulombDK_e + END SUBROUTINE apply_COSOlver_mat_e !******************************************************************************! - !!!!!!! Compute ion Full Coulomb collision operator + !!!!!!! Compute ion collision term !******************************************************************************! - SUBROUTINE FullCoulombDK_i(p_int,j_int,ikr,ikz,TColl) - USE basic - USE fields, ONLY: moments_i, moments_e - USE array, ONLY: Ciipj, CiepjT, CiepjF - USE grid, ONLY: pmaxe,jmaxe, pmaxi,jmaxi, parray_e, parray_i, & - jarray_e, jarray_i, bari, bare - USE prec_const - USE time_integration, ONLY: updatetlevel - USE model, ONLY: nu_i, nu_ie + SUBROUTINE apply_COSOlver_mat_i(ip_,ij_,ikr_,ikz_,TColl_) IMPLICIT NONE - INTEGER, INTENT(IN) :: p_int,j_int,ikr,ikz - COMPLEX(dp), INTENT(INOUT) :: TColl + INTEGER, INTENT(IN) :: ip_, ij_ ,ikr_, ikz_ + COMPLEX(dp), INTENT(OUT) :: TColl_ - INTEGER :: ip2,ij2, p2_int,j2_int + INTEGER :: ip2,ij2, p_int,j_int, p2_int,j2_int, ikr_C, ikz_C + p_int = ip_-1; j_int = ij_-1 - TColl = 0._dp ! Initialization + IF (CO .GT. 0) THEN ! GK operator (k-dependant) + ikr_C = ikr_; ikz_C = ikz_ + ELSEIF (CO .LT. 0) THEN ! DK operator (only one mat for every k) + ikr_C = 1; ikz_C = 1 + ENDIF - ploopii: DO ip2 = 1,pmaxi+1 ! sum the ion-self and ion-electron test terms + TColl_ = 0._dp ! Initialization + ! sum the ion-self and ion-electron test terms + ploopii: DO ip2 = ips_i,ipe_i p2_int = parray_i(ip2) - jloopii: DO ij2 = 1,jmaxi+1 + jloopii: DO ij2 = ijs_i,ije_i j2_int = jarray_i(ij2) - TColl = TColl + moments_i(ip2,ij2,ikr,ikz,updatetlevel) & - *( nu_ie * CiepjT(bari(p_int,j_int), bari(p2_int,j2_int)) & - +nu_i * Ciipj (bari(p_int,j_int), bari(p2_int,j2_int))) + TColl_ = TColl_ + moments_i(ip2,ij2,ikr_,ikz_,updatetlevel) & + *( nu_ie * CiepjT(bari(p_int,j_int), bari(p2_int,j2_int), ikr_C, ikz_C) & + +nu_i * Ciipj (bari(p_int,j_int), bari(p2_int,j2_int), ikr_C, ikz_C)) ENDDO jloopii ENDDO ploopii - ploopie: DO ip2 = 1,pmaxe+1 ! sum the ion-electron field terms + ploopie: DO ip2 = ips_e,ipe_e ! sum the ion-electron field terms p2_int = parray_e(ip2) - jloopie: DO ij2 = 1,jmaxe+1 + jloopie: DO ij2 = ijs_e,ije_e j2_int = jarray_e(ij2) - TColl = TColl + moments_e(ip2,ij2,ikr,ikz,updatetlevel) & - *(nu_ie * CiepjF(bari(p_int,j_int), bare(p2_int,j2_int))) + TColl_ = TColl_ + moments_e(ip2,ij2,ikr_,ikz_,updatetlevel) & + *(nu_ie * CiepjF(bari(p_int,j_int), bare(p2_int,j2_int), ikr_C, ikz_C)) ENDDO jloopie ENDDO ploopie - END SUBROUTINE FullCoulombDK_i + END SUBROUTINE apply_COSOlver_mat_i !******************************************************************************! - !!!!!!! Load the Full coulomb coefficient table from COSOlver results + !!!!!!! Load the collision matrix coefficient table from COSOlver results !******************************************************************************! - SUBROUTINE load_FC_mat ! Load a sub matrix from iCa files (works for pmaxa,jmaxa<=P_full,J_full) - use prec_const - use fields - use array - use grid - use basic + SUBROUTINE load_COSOlver_mat ! Load a sub matrix from iCa files (works for pmaxa,jmaxa<=P_full,J_full) use futils use initial_par - use model IMPLICIT NONE INTEGER :: irow_sub, irow_full, icol_sub, icol_full INTEGER :: fid1, fid2, fid3, fid4 - INTEGER :: ip_e, ij_e, il_e, ik_e + INTEGER :: ip_e, ij_e, il_e, ik_e, ikrs_C, ikre_C, ikzs_C, ikze_C INTEGER :: pdime, jdime REAL(dp), DIMENSION(:,:), ALLOCATABLE :: Ceepj_full, CeipjT_full REAL(dp), DIMENSION(:,:), ALLOCATABLE :: CeipjF_full @@ -331,141 +386,190 @@ CONTAINS REAL(dp), DIMENSION(:,:), ALLOCATABLE :: Ciipj_full, CiepjT_full REAL(dp), DIMENSION(:,:), ALLOCATABLE :: CiepjF_full - !!!!!!!!!!!! Electron matrices !!!!!!!!!!!! - ! get the self electron colision matrix - CALL openf(selfmat_file,fid1, 'r', 'D',mpicomm=MPI_COMM_WORLD) - - CALL getatt(fid1,'/Caapj/Ceepj/','Pmaxe',pdime) - CALL getatt(fid1,'/Caapj/Ceepj/','Jmaxe',jdime) - - IF ( ((pdime .LT. pmaxe) .OR. (jdime .LT. jmaxe)) .AND. (my_id .EQ. 0)) WRITE(*,*) '!! FC Matrix too small !!' - - CALL allocate_array( Ceepj_full, 1,(pdime+1)*(jdime+1), 1,(pdime+1)*(jdime+1)) - CALL getarr(fid1, '/Caapj/Ceepj', Ceepj_full) ! get array (moli format) - - ! Fill sub array with only usefull polynmials degree - DO ip_e = 0,pmaxe ! Loop over rows - DO ij_e = 0,jmaxe - irow_sub = (jmaxe +1)*ip_e + ij_e +1 - irow_full = (jdime +1)*ip_e + ij_e +1 - DO il_e = 0,pmaxe ! Loop over columns - DO ik_e = 0,jmaxe - icol_sub = (jmaxe +1)*il_e + ik_e +1 - icol_full = (jdime +1)*il_e + ik_e +1 - Ceepj (irow_sub,icol_sub) = Ceepj_full (irow_full,icol_full) - ENDDO - ENDDO - ENDDO - ENDDO - - CALL closef(fid1) - DEALLOCATE(Ceepj_full) - - ! get the Test and Back field electron ion collision matrix - CALL openf(eimat_file,fid2, 'r', 'D'); - - CALL getatt(fid2,'/Ceipj/CeipjT/','Pmaxi',pdimi) - CALL getatt(fid2,'/Ceipj/CeipjT/','Jmaxi',jdimi) - IF ( (pdimi .LT. pmaxi) .OR. (jdimi .LT. jmaxi) ) WRITE(*,*) '!! FC Matrix too small !!' - - CALL allocate_array( CeipjT_full, 1,(pdime+1)*(jdime+1), 1,(pdime+1)*(jdime+1)) - CALL allocate_array( CeipjF_full, 1,(pdime+1)*(jdime+1), 1,(pdimi+1)*(jdimi+1)) - - CALL getarr(fid2, '/Ceipj/CeipjT', CeipjT_full) - CALL getarr(fid2, '/Ceipj/CeipjF', CeipjF_full) - - ! Fill sub array with only usefull polynmials degree - DO ip_e = 0,pmaxe ! Loop over rows - DO ij_e = 0,jmaxe - irow_sub = (jmaxe +1)*ip_e + ij_e +1 - irow_full = (jdime +1)*ip_e + ij_e +1 - DO il_e = 0,pmaxe ! Loop over columns - DO ik_e = 0,jmaxe - icol_sub = (jmaxe +1)*il_e + ik_e +1 - icol_full = (jdime +1)*il_e + ik_e +1 - CeipjT(irow_sub,icol_sub) = CeipjT_full(irow_full,icol_full) - ENDDO - ENDDO - DO il_i = 0,pmaxi ! Loop over columns - DO ik_i = 0,jmaxi - icol_sub = (Jmaxi +1)*il_i + ik_i +1 - icol_full = (jdimi +1)*il_i + ik_i +1 - CeipjF(irow_sub,icol_sub) = CeipjF_full(irow_full,icol_full) - ENDDO - ENDDO - ENDDO - ENDDO - - CALL closef(fid2) - DEALLOCATE(CeipjF_full) - DEALLOCATE(CeipjT_full) - - !!!!!!!!!!!!!!! Ion matrices !!!!!!!!!!!!!! - ! get the self electron colision matrix - CALL openf(selfmat_file, fid3, 'r', 'D',mpicomm=MPI_COMM_WORLD); - - CALL allocate_array( Ciipj_full, 1,(pdimi+1)*(jdimi+1), 1,(pdimi+1)*(jdimi+1)) - - IF ( (pmaxe .EQ. pmaxi) .AND. (jmaxe .EQ. jmaxi) ) THEN ! if same degrees ion and electron matrices are alike so load Ceepj - CALL getarr(fid3, '/Caapj/Ceepj', Ciipj_full) ! get array (moli format) - ELSE - CALL getarr(fid3, '/Caapj/Ciipj', Ciipj_full) ! get array (moli format) + CHARACTER(len=256) :: mat_filename, kperp_string + + !! Some terminal info + IF (CO .EQ. 2) THEN + IF (my_id .EQ. 0) WRITE(*,*) '=== Load GK Sugama matrix ===' + ELSEIF(CO .EQ. 3) THEN + IF (my_id .EQ. 0) WRITE(*,*) '=== Load GK Full Coulomb matrix ===' + ELSEIF(CO .EQ. -2) THEN + IF (my_id .EQ. 0) WRITE(*,*) '=== Load DK Sugama matrix ===' + ELSEIF(CO .EQ. -3) THEN + IF (my_id .EQ. 0) WRITE(*,*) '=== Load DK Full Coulomb matrix ===' ENDIF - ! Fill sub array with only usefull polynmials degree - DO ip_i = 0,Pmaxi ! Loop over rows - DO ij_i = 0,Jmaxi - irow_sub = (Jmaxi +1)*ip_i + ij_i +1 - irow_full = (jdimi +1)*ip_i + ij_i +1 - DO il_i = 0,Pmaxi ! Loop over columns - DO ik_i = 0,Jmaxi - icol_sub = (Jmaxi +1)*il_i + ik_i +1 - icol_full = (jdimi +1)*il_i + ik_i +1 - Ciipj (irow_sub,icol_sub) = Ciipj_full (irow_full,icol_full) - ENDDO - ENDDO - ENDDO - ENDDO - - CALL closef(fid3) - DEALLOCATE(Ciipj_full) - - ! get the Test and Back field electron ion collision matrix - CALL openf(iemat_file,fid4, 'r', 'D'); - - CALL allocate_array( CiepjT_full, 1,(pdimi+1)*(jdimi+1), 1,(pdimi+1)*(jdimi+1)) - CALL allocate_array( CiepjF_full, 1,(pdimi+1)*(jdimi+1), 1,(pdime+1)*(jdime+1)) - - CALL getarr(fid4, '/Ciepj/CiepjT', CiepjT_full) - CALL getarr(fid4, '/Ciepj/CiepjF', CiepjF_full) + IF (CO .GT. 0) THEN ! GK operator (k-dependant) + ikrs_C = ikrs; ikre_C = ikre + ikzs_C = ikzs; ikze_C = ikze + ELSEIF (CO .LT. 0) THEN ! DK operator (only one mat for every k) + ikrs_C = 1; ikre_C = 1 + ikzs_C = 1; ikze_C = 1 + ENDIF - ! Fill sub array with only usefull polynmials degree - DO ip_i = 0,Pmaxi ! Loop over rows - DO ij_i = 0,Jmaxi - irow_sub = (Jmaxi +1)*ip_i + ij_i +1 - irow_full = (jdimi +1)*ip_i + ij_i +1 - DO il_i = 0,Pmaxi ! Loop over columns - DO ik_i = 0,Jmaxi - icol_sub = (Jmaxi +1)*il_i + ik_i +1 - icol_full = (jdimi +1)*il_i + ik_i +1 - CiepjT(irow_sub,icol_sub) = CiepjT_full(irow_full,icol_full) - ENDDO - ENDDO - DO il_e = 0,pmaxe ! Loop over columns - DO ik_e = 0,jmaxe - icol_sub = (jmaxe +1)*il_e + ik_e +1 - icol_full = (jdime +1)*il_e + ik_e +1 - CiepjF(irow_sub,icol_sub) = CiepjF_full(irow_full,icol_full) - ENDDO - ENDDO + DO ikr = ikrs_C,ikre_C ! Loop over everz kperp values + DO ikz = ikzs_C,ikze_C ! Loop over everz kperp values + write(kperp_string,'(f6.4)') kparray_2D(ikr,ikz) + !!!!!!!!!!!! Electron matrices !!!!!!!!!!!! + ! get the self electron colision matrix + IF (CO .GT. 0) THEN + WRITE(mat_filename,'(a,a6,f6.4,a3)') TRIM(selfmat_file),'kperp_',TRIM(ADJUSTL(kperp_string)),'.h5' + ELSE + mat_filename = selfmat_file + ENDIF + + CALL openf(mat_filename,fid1, 'r', 'D', mpicomm=MPI_COMM_WORLD); + CALL getatt(fid1,'/Caapj/Ceepj/','Pmaxe',pdime) + CALL getatt(fid1,'/Caapj/Ceepj/','Jmaxe',jdime) + IF ( ((pdime .LT. pmaxe) .OR. (jdime .LT. jmaxe)) .AND. (my_id .EQ. 0)) WRITE(*,*) '!! Sugama Matrix too small !!' + + CALL allocate_array( Ceepj_full, 1,(pdime+1)*(jdime+1), 1,(pdime+1)*(jdime+1)) + CALL getarr(fid1, '/Caapj/Ceepj', Ceepj_full) ! get array (moli format) + ! Fill sub array with only usefull polynmials degree + DO ip_e = 0,pmaxe ! Loop over rows + DO ij_e = 0,jmaxe + irow_sub = (jmaxe +1)*ip_e + ij_e +1 + irow_full = (jdime +1)*ip_e + ij_e +1 + DO il_e = 0,pmaxe ! Loop over columns + DO ik_e = 0,jmaxe + icol_sub = (jmaxe +1)*il_e + ik_e +1 + icol_full = (jdime +1)*il_e + ik_e +1 + Ceepj (irow_sub,icol_sub,ikr,ikz) = Ceepj_full (irow_full,icol_full) + ENDDO + ENDDO + ENDDO + ENDDO + + CALL closef(fid1) + DEALLOCATE(Ceepj_full) + + ! get the Test and Back field electron ion collision matrix + IF (CO .GT. 0) THEN + WRITE(mat_filename,'(a,a6,f6.4,a3)') TRIM(eimat_file),'kperp_',TRIM(ADJUSTL(kperp_string)),'.h5' + ELSE + mat_filename = eimat_file + ENDIF + + CALL openf(mat_filename,fid2, 'r', 'D', mpicomm=MPI_COMM_WORLD); + + CALL getatt(fid2,'/Ceipj/CeipjT/','Pmaxi',pdimi) + CALL getatt(fid2,'/Ceipj/CeipjT/','Jmaxi',jdimi) + IF ( (pdimi .LT. pmaxi) .OR. (jdimi .LT. jmaxi) ) WRITE(*,*) '!! Sugama Matrix too small !!' + + CALL allocate_array( CeipjT_full, 1,(pdime+1)*(jdime+1), 1,(pdime+1)*(jdime+1)) + CALL allocate_array( CeipjF_full, 1,(pdime+1)*(jdime+1), 1,(pdimi+1)*(jdimi+1)) + + CALL getarr(fid2, '/Ceipj/CeipjT', CeipjT_full) + CALL getarr(fid2, '/Ceipj/CeipjF', CeipjF_full) + + ! Fill sub array with only usefull polynmials degree + DO ip_e = 0,pmaxe ! Loop over rows + DO ij_e = 0,jmaxe + irow_sub = (jmaxe +1)*ip_e + ij_e +1 + irow_full = (jdime +1)*ip_e + ij_e +1 + DO il_e = 0,pmaxe ! Loop over columns + DO ik_e = 0,jmaxe + icol_sub = (jmaxe +1)*il_e + ik_e +1 + icol_full = (jdime +1)*il_e + ik_e +1 + CeipjT(irow_sub,icol_sub,ikr,ikz) = CeipjT_full(irow_full,icol_full) + ENDDO + ENDDO + DO il_i = 0,pmaxi ! Loop over columns + DO ik_i = 0,jmaxi + icol_sub = (Jmaxi +1)*il_i + ik_i +1 + icol_full = (jdimi +1)*il_i + ik_i +1 + CeipjF(irow_sub,icol_sub,ikr,ikz) = CeipjF_full(irow_full,icol_full) + ENDDO + ENDDO + ENDDO + ENDDO + + CALL closef(fid2) + DEALLOCATE(CeipjF_full) + DEALLOCATE(CeipjT_full) + + !!!!!!!!!!!!!!! Ion matrices !!!!!!!!!!!!!! + ! get the self electron colision matrix + IF (CO .GT. 0) THEN + WRITE(mat_filename,'(a,a6,f6.4,a3)') TRIM(selfmat_file),'kperp_',TRIM(ADJUSTL(kperp_string)),'.h5' + ELSE + mat_filename = selfmat_file + ENDIF + + CALL openf(mat_filename, fid3, 'r', 'D', mpicomm=MPI_COMM_WORLD); + + CALL allocate_array( Ciipj_full, 1,(pdimi+1)*(jdimi+1), 1,(pdimi+1)*(jdimi+1)) + + IF ( (pmaxe .EQ. pmaxi) .AND. (jmaxe .EQ. jmaxi) ) THEN ! if same degrees ion and electron matrices are alike so load Ceepj + CALL getarr(fid3, '/Caapj/Ceepj', Ciipj_full) ! get array (moli format) + ELSE + CALL getarr(fid3, '/Caapj/Ciipj', Ciipj_full) ! get array (moli format) + ENDIF + + ! Fill sub array with only usefull polynmials degree + DO ip_i = 0,Pmaxi ! Loop over rows + DO ij_i = 0,Jmaxi + irow_sub = (Jmaxi +1)*ip_i + ij_i +1 + irow_full = (jdimi +1)*ip_i + ij_i +1 + DO il_i = 0,Pmaxi ! Loop over columns + DO ik_i = 0,Jmaxi + icol_sub = (Jmaxi +1)*il_i + ik_i +1 + icol_full = (jdimi +1)*il_i + ik_i +1 + Ciipj (irow_sub,icol_sub,ikr,ikz) = Ciipj_full (irow_full,icol_full) + ENDDO + ENDDO + ENDDO + ENDDO + + CALL closef(fid3) + DEALLOCATE(Ciipj_full) + + ! get the Test and Back field electron ion collision matrix + IF (CO .GT. 0) THEN + WRITE(mat_filename,'(a,a6,f6.4,a3)') TRIM(iemat_file),'kperp_',TRIM(ADJUSTL(kperp_string)),'.h5' + ELSE + mat_filename = iemat_file + ENDIF + write(*,*) 'Loading GK COSOLVER mat : ', mat_filename + + CALL openf(mat_filename,fid4, 'r', 'D', mpicomm=MPI_COMM_WORLD); + + CALL allocate_array( CiepjT_full, 1,(pdimi+1)*(jdimi+1), 1,(pdimi+1)*(jdimi+1)) + CALL allocate_array( CiepjF_full, 1,(pdimi+1)*(jdimi+1), 1,(pdime+1)*(jdime+1)) + + CALL getarr(fid4, '/Ciepj/CiepjT', CiepjT_full) + CALL getarr(fid4, '/Ciepj/CiepjF', CiepjF_full) + + ! Fill sub array with only usefull polynmials degree + DO ip_i = 0,Pmaxi ! Loop over rows + DO ij_i = 0,Jmaxi + irow_sub = (Jmaxi +1)*ip_i + ij_i +1 + irow_full = (jdimi +1)*ip_i + ij_i +1 + DO il_i = 0,Pmaxi ! Loop over columns + DO ik_i = 0,Jmaxi + icol_sub = (Jmaxi +1)*il_i + ik_i +1 + icol_full = (jdimi +1)*il_i + ik_i +1 + CiepjT(irow_sub,icol_sub,ikr,ikz) = CiepjT_full(irow_full,icol_full) + ENDDO + ENDDO + DO il_e = 0,pmaxe ! Loop over columns + DO ik_e = 0,jmaxe + icol_sub = (jmaxe +1)*il_e + ik_e +1 + icol_full = (jdime +1)*il_e + ik_e +1 + CiepjF(irow_sub,icol_sub,ikr,ikz) = CiepjF_full(irow_full,icol_full) + ENDDO + ENDDO + ENDDO + ENDDO + + CALL closef(fid4) + DEALLOCATE(CiepjF_full) + DEALLOCATE(CiepjT_full) ENDDO - ENDDO - - CALL closef(fid4) - DEALLOCATE(CiepjF_full) - DEALLOCATE(CiepjT_full) + ENDDO + IF (my_id .EQ. 0) WRITE(*,*) '============DONE===========' - END SUBROUTINE load_FC_mat - !******************************************************************************! +END SUBROUTINE load_COSOlver_mat + !******************************************************************************! end module collision diff --git a/src/grid_mod.F90 b/src/grid_mod.F90 index 03ad393aada84ae2536ef627192dd8a2361d1132..1ba800c84dbb3c15766e642150634382438cfd73 100644 --- a/src/grid_mod.F90 +++ b/src/grid_mod.F90 @@ -37,16 +37,23 @@ MODULE grid INTEGER, PUBLIC :: ir,iz ! counters integer(C_INTPTR_T), PUBLIC :: local_nkr, local_nz integer(C_INTPTR_T), PUBLIC :: local_nkr_offset, local_nz_offset + INTEGER, PUBLIC :: local_nkp INTEGER, PUBLIC :: local_np_e, local_np_i integer(C_INTPTR_T), PUBLIC :: local_np_e_offset, local_np_i_offset + INTEGER, DIMENSION(:), ALLOCATABLE, PUBLIC :: counts_np_e, counts_np_i + INTEGER, DIMENSION(:), ALLOCATABLE, PUBLIC :: displs_np_e, displs_np_i ! Grids containing position in fourier space - REAL(dp), DIMENSION(:), ALLOCATABLE, PUBLIC :: krarray - REAL(dp), DIMENSION(:), ALLOCATABLE, PUBLIC :: kzarray + REAL(dp), DIMENSION(:), ALLOCATABLE, PUBLIC :: krarray + REAL(dp), DIMENSION(:), ALLOCATABLE, PUBLIC :: kzarray + REAL(dp), DIMENSION(:), ALLOCATABLE, PUBLIC :: kparray ! kperp array + REAL(dp), DIMENSION(:,:), ALLOCATABLE, PUBLIC :: kparray_2D ! kperp array in 2D + INTEGER, DIMENSION(:), ALLOCATABLE, PUBLIC :: ikparray ! kperp indices array + INTEGER, DIMENSION(:,:), ALLOCATABLE, PUBLIC :: ikparray_2D ! to convert (ikr,ikz) -> ikp REAL(dp), PUBLIC, PROTECTED :: deltakr, deltakz - INTEGER, PUBLIC, PROTECTED :: ikrs, ikre, ikzs, ikze, a + INTEGER, PUBLIC, PROTECTED :: ikrs, ikre, ikzs, ikze, ikps, ikpe INTEGER, PUBLIC, PROTECTED :: ikr_0, ikz_0 ! Indices of k-grid origin - INTEGER, PUBLIC :: ikr, ikz, ip, ij ! counters + INTEGER, PUBLIC :: ikr, ikz, ip, ij, ikp ! counters ! Grid containing the polynomials degrees INTEGER, DIMENSION(:), ALLOCATABLE, PUBLIC :: parray_e @@ -61,7 +68,7 @@ MODULE grid ! Public Functions PUBLIC :: init_1Dgrid_distr PUBLIC :: set_pgrid, set_jgrid - PUBLIC :: set_krgrid, set_kzgrid + PUBLIC :: set_krgrid, set_kzgrid, set_kpgrid PUBLIC :: grid_readinputs, grid_outputinputs PUBLIC :: bare, bari @@ -84,11 +91,30 @@ CONTAINS SUBROUTINE set_pgrid USE prec_const IMPLICIT NONE - INTEGER :: ip + INTEGER :: ip, istart, iend, in + ! Local data distribution CALL decomp1D(pmaxe+1, num_procs_p, rank_p, ips_e, ipe_e) CALL decomp1D(pmaxi+1, num_procs_p, rank_p, ips_i, ipe_i) - + local_np_e = ipe_e - ips_e + 1 + local_np_i = ipe_i - ips_i + 1 + ! List of shift and local numbers between the different processes (used in scatterv and gatherv) + ALLOCATE(counts_np_e (1:num_procs_p)) + ALLOCATE(counts_np_i (1:num_procs_p)) + ALLOCATE(displs_np_e (1:num_procs_p)) + ALLOCATE(displs_np_i (1:num_procs_p)) + DO in = 0,num_procs_p-1 + CALL decomp1D(pmaxe+1, num_procs_p, in, istart, iend) + counts_np_e(in+1) = iend-istart+1 + displs_np_e(in+1) = istart-1 + CALL decomp1D(pmaxi+1, num_procs_p, in, istart, iend) + counts_np_i(in+1) = iend-istart+1 + displs_np_i(in+1) = istart-1 + ENDDO + write(*,*) rank_p, ': counts = ', counts_np_e + write(*,*) rank_p, ': disps = ', displs_np_e + + ! local grid computation ALLOCATE(parray_e(ips_e:ipe_e)) ALLOCATE(parray_i(ips_i:ipe_i)) DO ip = ips_e,ipe_e; parray_e(ip) = (ip-1); END DO @@ -100,7 +126,6 @@ CONTAINS ! Precomputations pmaxe_dp = real(pmaxe,dp) pmaxi_dp = real(pmaxi,dp) - END SUBROUTINE set_pgrid SUBROUTINE set_jgrid @@ -123,7 +148,6 @@ CONTAINS ! Precomputations jmaxe_dp = real(jmaxe,dp) jmaxi_dp = real(jmaxi,dp) - END SUBROUTINE set_jgrid @@ -166,7 +190,7 @@ CONTAINS SUBROUTINE set_kzgrid USE prec_const IMPLICIT NONE - INTEGER :: i_ + INTEGER :: i_, counter Nkz = Nz; ! Start and END indices of grid @@ -200,6 +224,41 @@ CONTAINS END DO END SUBROUTINE set_kzgrid + SUBROUTINE set_kpgrid !Precompute the grid of kperp + IMPLICIT NONE + INTEGER :: ikz_sym, tmp_, counter + ! 2D to 1D indices array convertor + ALLOCATE(ikparray_2D(ikrs:ikre,ikzs:ikze)) + ALLOCATE( kparray_2D(ikrs:ikre,ikzs:ikze)) + ! local number of different kperp + local_nkp = local_nkr * (local_nkr-1)/2 + 1 + ! Allocate 1D array of kperp values and indices + ALLOCATE(ikparray(1:local_nkr)) + ALLOCATE( kparray(1:local_nkr)) + + ! Fill the arrays + tmp_ = 0; counter = 1 + DO ikz = ikzs,ikze + DO ikr = ikrs,ikre + ! Set a symmetry on kz + IF (ikz .LE. Nkz/2+1) THEN + ikz_sym = ikz + ELSE + ikz_sym = Nkz+2 - ikz + ENDIF + ! Formula to find the 2D to 1D kperp equivalences ordered as + ! 10 + ! 6 9 + ! 3 5 8 + !1 2 4 7 etc... + ikp = MAX(ikr-1,ikz_sym-1)*MIN(ikr-1,ikz_sym-1)/2 + min(ikr-1,ikz_sym-1) + ikparray_2D(ikr,ikz) = ikp + kparray_2D(ikr,ikz) = SQRT(krarray(ikr)**2 + kzarray(ikz)**2) + ENDDO + ENDDO + + END SUBROUTINE + SUBROUTINE grid_readinputs ! Read the input parameters USE prec_const diff --git a/src/inital.F90 b/src/inital.F90 index f2768f6241fac64ac663b9df17a5b46ee8cdd61e..7aa10a3497a839b44929a4eb2c66aeccdbe4b0ca 100644 --- a/src/inital.F90 +++ b/src/inital.F90 @@ -58,11 +58,9 @@ SUBROUTINE inital CALL build_dnjs_table ENDIF - !!!!!! Load the full coulomb collision operator coefficients !!!!!! - IF (CO .EQ. -1) THEN - IF (my_id .EQ. 0) WRITE(*,*) '=== Load Full Coulomb matrix ===' - CALL load_FC_mat - IF (my_id .EQ. 0) WRITE(*,*) '..done' + !!!!!! Load the COSOlver collision operator coefficients !!!!!! + IF (ABS(CO) .GT. 1) THEN + CALL load_COSOlver_mat ENDIF END SUBROUTINE inital diff --git a/src/memory.F90 b/src/memory.F90 index 60b52058384a8e6d99c8f2e889d9e1aaea5f860f..8215f48a59cff9fe2c9baf45efcfc3c716d7c4bd 100644 --- a/src/memory.F90 +++ b/src/memory.F90 @@ -21,7 +21,7 @@ SUBROUTINE memory ! Electrostatic potential CALL allocate_array(phi, ikrs,ikre, ikzs,ikze) - + ! Gyrocenter density *for 2D output* CALL allocate_array(Ne00, ikrs,ikre, ikzs,ikze) CALL allocate_array(Ni00, ikrs,ikre, ikzs,ikze) @@ -31,16 +31,26 @@ SUBROUTINE memory CALL allocate_array(Kernel_i, ijsg_i,ijeg_i, ikrs,ikre, ikzs,ikze) ! Collision matrix - IF (CO .EQ. -1) THEN - CALL allocate_array( Ceepj, 1,(pmaxe+1)*(jmaxe+1), 1,(pmaxe+1)*(jmaxe+1)) - CALL allocate_array( CeipjT, 1,(pmaxe+1)*(jmaxe+1), 1,(pmaxe+1)*(jmaxe+1)) - CALL allocate_array( CeipjF, 1,(pmaxe+1)*(jmaxe+1), 1,(pmaxi+1)*(jmaxi+1)) - - CALL allocate_array( Ciipj, 1,(pmaxi+1)*(jmaxi+1), 1,(pmaxi+1)*(jmaxi+1)) - CALL allocate_array( CiepjT, 1,(pmaxi+1)*(jmaxi+1), 1,(pmaxi+1)*(jmaxi+1)) - CALL allocate_array( CiepjF, 1,(pmaxi+1)*(jmaxi+1), 1,(pmaxe+1)*(jmaxe+1)) + IF (CO .LT. -1) THEN !DK collision matrix (same for every k) + CALL allocate_array( Ceepj, 1,(pmaxe+1)*(jmaxe+1), 1,(pmaxe+1)*(jmaxe+1), 1,1, 1,1) + CALL allocate_array( CeipjT, 1,(pmaxe+1)*(jmaxe+1), 1,(pmaxe+1)*(jmaxe+1), 1,1, 1,1) + CALL allocate_array( CeipjF, 1,(pmaxe+1)*(jmaxe+1), 1,(pmaxi+1)*(jmaxi+1), 1,1, 1,1) + CALL allocate_array( Ciipj, 1,(pmaxi+1)*(jmaxi+1), 1,(pmaxi+1)*(jmaxi+1), 1,1, 1,1) + CALL allocate_array( CiepjT, 1,(pmaxi+1)*(jmaxi+1), 1,(pmaxi+1)*(jmaxi+1), 1,1, 1,1) + CALL allocate_array( CiepjF, 1,(pmaxi+1)*(jmaxi+1), 1,(pmaxe+1)*(jmaxe+1), 1,1, 1,1) + ELSEIF (CO .GT. 1) THEN !GK collision matrices (one for each kperp) + CALL allocate_array( Ceepj, 1,(pmaxe+1)*(jmaxe+1), 1,(pmaxe+1)*(jmaxe+1), ikrs,ikre, ikzs,ikze) + CALL allocate_array( CeipjT, 1,(pmaxe+1)*(jmaxe+1), 1,(pmaxe+1)*(jmaxe+1), ikrs,ikre, ikzs,ikze) + CALL allocate_array( CeipjF, 1,(pmaxe+1)*(jmaxe+1), 1,(pmaxi+1)*(jmaxi+1), ikrs,ikre, ikzs,ikze) + CALL allocate_array( Ciipj, 1,(pmaxi+1)*(jmaxi+1), 1,(pmaxi+1)*(jmaxi+1), ikrs,ikre, ikzs,ikze) + CALL allocate_array( CiepjT, 1,(pmaxi+1)*(jmaxi+1), 1,(pmaxi+1)*(jmaxi+1), ikrs,ikre, ikzs,ikze) + CALL allocate_array( CiepjF, 1,(pmaxi+1)*(jmaxi+1), 1,(pmaxe+1)*(jmaxe+1), ikrs,ikre, ikzs,ikze) ENDIF + ! Collision term + CALL allocate_array( TColl_e, ips_e,ipe_e, ijs_e,ije_e , ikrs,ikre, ikzs,ikze) + CALL allocate_array( TColl_i, ips_i,ipe_i, ijs_i,ije_i , ikrs,ikre, ikzs,ikze) + ! Non linear terms and dnjs table CALL allocate_array( Sepj, ips_e,ipe_e, ijs_e,ije_e, ikrs,ikre, ikzs,ikze ) CALL allocate_array( Sipj, ips_i,ipe_i, ijs_i,ije_i, ikrs,ikre, ikzs,ikze ) diff --git a/src/model_mod.F90 b/src/model_mod.F90 index 00fb21cbeca0ba33921e506c8264aa847ed72dc9..eda2577064393a05453882ce587e1996533bb392 100644 --- a/src/model_mod.F90 +++ b/src/model_mod.F90 @@ -6,7 +6,8 @@ MODULE model PRIVATE INTEGER, PUBLIC, PROTECTED :: CO = 0 ! Collision Operator - INTEGER, PUBLIC, PROTECTED :: CLOS = 0 ! Truncation method + INTEGER, PUBLIC, PROTECTED :: CLOS = 0 ! linear truncation method + INTEGER, PUBLIC, PROTECTED :: NL_CLOS = 0 ! nonlinear truncation method INTEGER, PUBLIC, PROTECTED :: KERN = 0 ! Kernel model LOGICAL, PUBLIC, PROTECTED :: NON_LIN = .true. ! To turn on non linear bracket term REAL(dp), PUBLIC, PROTECTED :: mu = 0._dp ! spatial Hyperdiffusivity coefficient (for num. stability) @@ -42,12 +43,11 @@ CONTAINS SUBROUTINE model_readinputs ! Read the input parameters - USE basic, ONLY : lu_in USE prec_const IMPLICIT NONE - NAMELIST /MODEL_PAR/ CO, CLOS, KERN, NON_LIN, mu, mu_p, mu_j, nu, tau_e, tau_i, sigma_e, sigma_i, & + NAMELIST /MODEL_PAR/ CO, CLOS, NL_CLOS, KERN, NON_LIN, mu, mu_p, mu_j, nu, tau_e, tau_i, sigma_e, sigma_i, & q_e, q_i, eta_n, eta_T, eta_B, lambdaD READ(lu_in,model_par) @@ -77,7 +77,6 @@ CONTAINS nu_i = nu * sigma_e * (tau_i)**(-3._dp/2._dp)/SQRT2 ! ion-ion collision frequ. nu_ee = nu_e/SQRT2 ! e-e coll. frequ. nu_ie = nu*sigma_e**2 ! i-e coll. frequ. - END SUBROUTINE model_readinputs diff --git a/src/moments_eq_rhs.F90 b/src/moments_eq_rhs.F90 index 5f3411dcfe1a6b08dd130b47ef4ebb0889e8129b..d667d1867a7c856fe3478f157202f0203a8aa6bb 100644 --- a/src/moments_eq_rhs.F90 +++ b/src/moments_eq_rhs.F90 @@ -115,10 +115,10 @@ SUBROUTINE moments_eq_rhs_e TNapjm1 = xNapjm1 * moments_e(ip,ij-1,ikr,ikz,updatetlevel) !! Collision - IF (CO .EQ. -3) THEN ! GK Dougherty - CALL DoughertyGK_e(ip,ij,ikr,ikz,TColl) + IF (CO .EQ. 0) THEN ! Lenard Bernstein + TColl = xCapj * moments_e(ip,ij,ikr,ikz,updatetlevel) - ELSEIF (CO .EQ. -2) THEN ! DK Dougherty + ELSEIF (CO .EQ. -1) THEN ! DK Dougherty TColl20 = 0._dp; TColl01 = 0._dp; TColl10 = 0._dp IF ( (pmaxe .GE. 2) ) TColl20 = xCa20 * moments_e(3,1,ikr,ikz,updatetlevel) IF ( (jmaxe .GE. 1) ) TColl01 = xCa01 * moments_e(1,2,ikr,ikz,updatetlevel) @@ -127,13 +127,12 @@ SUBROUTINE moments_eq_rhs_e TColl = xCapj* moments_e(ip,ij,ikr,ikz,updatetlevel)& + TColl20 + TColl01 + TColl10 - ELSEIF (CO .EQ. -1) THEN ! Full Coulomb for electrons (COSOlver matrix) - CALL FullCoulombDK_e(p_int,j_int,ikr,ikz,TColl) - - ELSEIF (CO .EQ. 0) THEN ! Lenard Bernstein - TColl = xCapj * moments_e(ip,ij,ikr,ikz,updatetlevel) + ELSEIF (CO .EQ. 1) THEN ! GK Dougherty + CALL DoughertyGK_e(ip,ij,ikr,ikz,TColl) - ENDIF + ELSE ! COSOLver matrix + TColl = TColl_e(ip,ij,ikr,ikz) + ENDIF !! Electrical potential term IF ( p_int .LE. 2 ) THEN ! kronecker p0 p1 p2 @@ -303,24 +302,22 @@ SUBROUTINE moments_eq_rhs_i TNapjm1 = xNapjm1 * moments_i(ip,ij-1,ikr,ikz,updatetlevel) !! Collision - IF (CO .EQ. -3) THEN ! Gyrokin. Dougherty Collision terms - CALL DoughertyGK_i(ip,ij,ikr,ikz,TColl) + IF (CO .EQ. 0) THEN ! Lenard Bernstein + TColl = xCapj * moments_i(ip,ij,ikr,ikz,updatetlevel) - ELSEIF (CO .EQ. -2) THEN ! Dougherty Collision terms + ELSEIF (CO .EQ. -1) THEN ! DK Dougherty TColl20 = 0._dp; TColl01 = 0._dp; TColl10 = 0._dp - IF ( (pmaxe .GE. 2) ) TColl20 = xCa20 * moments_i(3,1,ikr,ikz,updatetlevel) - IF ( (jmaxe .GE. 1) ) TColl01 = xCa01 * moments_i(1,2,ikr,ikz,updatetlevel) - IF ( (pmaxe .GE. 1) ) TColl10 = xCa10 * moments_i(2,1,ikr,ikz,updatetlevel) + IF ( (pmaxi .GE. 2) ) TColl20 = xCa20 * moments_i(3,1,ikr,ikz,updatetlevel) + IF ( (jmaxi .GE. 1) ) TColl01 = xCa01 * moments_i(1,2,ikr,ikz,updatetlevel) + IF ( (pmaxi .GE. 1) ) TColl10 = xCa10 * moments_i(2,1,ikr,ikz,updatetlevel) ! Total collisional term TColl = xCapj* moments_i(ip,ij,ikr,ikz,updatetlevel)& + TColl20 + TColl01 + TColl10 - ELSEIF (CO .EQ. -1) THEN !!! Full Coulomb for ions (COSOlver matrix) !!! - CALL FullCoulombDK_i(p_int,j_int,ikr,ikz,TColl) - - ELSEIF (CO .EQ. 0) THEN! Lenhard Bernstein - TColl = xCapj * moments_i(ip,ij,ikr,ikz,updatetlevel) - + ELSEIF (CO .EQ. 1) THEN ! GK Dougherty + CALL DoughertyGK_i(ip,ij,ikr,ikz,TColl) + ELSE! COSOLver matrix (Sugama, Coulomb) + TColl = TColl_i(ip,ij,ikr,ikz) ENDIF !! Electrical potential term diff --git a/src/stepon.F90 b/src/stepon.F90 index f3933416a2ba905aaccbb78462a07537c8de731c..af5ee588c8ac22a503f678f200d9d548487bd66d 100644 --- a/src/stepon.F90 +++ b/src/stepon.F90 @@ -1,17 +1,17 @@ SUBROUTINE stepon ! Advance one time step, (num_step=4 for Runge Kutta 4 scheme) - + USE advance_field_routine, ONLY: advance_time_level, advance_field + USE array , ONLY: moments_rhs_e, moments_rhs_i, Sepj, Sipj USE basic - USE time_integration + USE closure + USE collision, ONLY : compute_TColl USE fields, ONLY: moments_e, moments_i, phi - USE array , ONLY: moments_rhs_e, moments_rhs_i, Sepj, Sipj + USE ghosts USE grid - USE advance_field_routine, ONLY: advance_time_level, advance_field USE model - USE closure - USE utility, ONLY: checkfield use prec_const - USE ghosts + USE time_integration + USE utility, ONLY: checkfield IMPLICIT NONE @@ -26,6 +26,9 @@ SUBROUTINE stepon ! Exchanges the ghosts values updated CALL update_ghosts + ! Compute collision + CALL compute_TColl + ! Compute right hand side of moments hierarchy equation CALL moments_eq_rhs_e CALL moments_eq_rhs_i