79 SUBROUTINE force_nonbond(fist_nonbond_env, ewald_env, particle_set, cell, &
80 pot_nonbond, f_nonbond, pv_nonbond, fshell_nonbond, fcore_nonbond, &
81 atprop_env, atomic_kind_set, use_virial)
87 REAL(kind=
dp),
INTENT(OUT) :: pot_nonbond
88 REAL(kind=
dp),
DIMENSION(:, :),
INTENT(INOUT) :: f_nonbond, pv_nonbond
89 REAL(kind=
dp),
DIMENSION(:, :),
INTENT(OUT), &
90 OPTIONAL :: fshell_nonbond, fcore_nonbond
93 LOGICAL,
INTENT(IN) :: use_virial
95 CHARACTER(LEN=*),
PARAMETER :: routinen =
'force_nonbond'
97 INTEGER :: atom_a, atom_b, ewald_type, handle, i, iend, igrp, ikind, ilist, ipair, istart, &
98 j, kind_a, kind_b, nkind, npairs, shell_a, shell_b, shell_type
99 INTEGER,
DIMENSION(:, :),
POINTER ::
list
100 LOGICAL :: all_terms, do_multipoles, full_nl, &
102 LOGICAL,
ALLOCATABLE,
DIMENSION(:) :: is_shell_kind
103 REAL(kind=
dp) :: alpha, beta, beta_a, beta_b, energy, etot, fac_ei, fac_kind, fac_vdw, &
104 fscalar, mm_radius_a, mm_radius_b, qcore_a, qcore_b, qeff_a, qeff_b, qshell_a, qshell_b, &
105 rab2, rab2_com, rab2_max
106 REAL(kind=
dp),
ALLOCATABLE,
DIMENSION(:) :: mm_radius, qcore, qeff, qshell
107 REAL(kind=
dp),
DIMENSION(3) :: cell_v, cvi, fatom_a, fatom_b, fcore_a, &
108 fcore_b, fshell_a, fshell_b, rab, &
109 rab_cc, rab_com, rab_cs, rab_sc, rab_ss
110 REAL(kind=
dp),
DIMENSION(3, 3) :: pv, pv_thread
111 REAL(kind=
dp),
DIMENSION(3, 4) :: rab_list
112 REAL(kind=
dp),
DIMENSION(4) :: rab2_list
113 REAL(kind=
dp),
DIMENSION(:, :),
POINTER :: ij_kind_full_fac
114 REAL(kind=
dp),
DIMENSION(:, :, :),
POINTER :: ei_interaction_cutoffs
121 TYPE(
pos_type),
DIMENSION(:),
POINTER :: r_last_update, r_last_update_pbc, &
122 rcore_last_update_pbc, &
123 rshell_last_update_pbc
128 CALL timeset(routinen, handle)
131 NULLIFY (pot, rshell_last_update_pbc, spl_f, ij_kind_full_fac)
133 potparm14=potparm14, potparm=potparm, r_last_update=r_last_update, &
134 r_last_update_pbc=r_last_update_pbc, natom_types=nkind, &
135 rshell_last_update_pbc=rshell_last_update_pbc, &
136 rcore_last_update_pbc=rcore_last_update_pbc, &
137 ij_kind_full_fac=ij_kind_full_fac)
138 CALL ewald_env_get(ewald_env, alpha=alpha, ewald_type=ewald_type, &
139 do_multipoles=do_multipoles, &
140 interaction_cutoffs=ei_interaction_cutoffs)
144 f_nonbond(:, :) = 0.0_dp
147 pv_nonbond(:, :) = 0.0_dp
149 shell_present = .false.
150 IF (
PRESENT(fshell_nonbond))
THEN
151 cpassert(
PRESENT(fcore_nonbond))
152 fshell_nonbond = 0.0_dp
153 fcore_nonbond = 0.0_dp
154 shell_present = .true.
157 ALLOCATE (mm_radius(nkind))
158 ALLOCATE (qeff(nkind))
159 ALLOCATE (qcore(nkind))
160 ALLOCATE (qshell(nkind))
161 ALLOCATE (is_shell_kind(nkind))
163 atomic_kind => atomic_kind_set(ikind)
166 mm_radius=mm_radius(ikind), &
168 is_shell_kind(ikind) =
ASSOCIATED(shell_kind)
169 IF (
ASSOCIATED(shell_kind))
THEN
171 charge_core=qcore(ikind), &
172 charge_shell=qshell(ikind))
174 qcore(ikind) = 0.0_dp
175 qshell(ikind) = 0.0_dp
179 lists:
DO ilist = 1, nonbonded%nlists
180 neighbor_kind_pair => nonbonded%neighbor_kind_pairs(ilist)
181 npairs = neighbor_kind_pair%npairs
182 IF (npairs == 0) cycle
183 list => neighbor_kind_pair%list
184 cvi = neighbor_kind_pair%cell_vector
185 cell_v = matmul(cell%hmat, cvi)
186 kind_group_loop:
DO igrp = 1, neighbor_kind_pair%ngrp_kind
187 istart = neighbor_kind_pair%grp_kind_start(igrp)
188 iend = neighbor_kind_pair%grp_kind_end(igrp)
208 IF (use_virial) pv_thread(:, :) = 0.0_dp
210 pairs:
DO ipair = istart, iend
211 atom_a =
list(1, ipair)
212 atom_b =
list(2, ipair)
215 kind_a = particle_set(atom_a)%atomic_kind%kind_number
216 kind_b = particle_set(atom_b)%atomic_kind%kind_number
218 fac_kind = ij_kind_full_fac(kind_a, kind_b)
220 pot => potparm%pot(kind_a, kind_b)%pot
221 IF (ipair <= neighbor_kind_pair%nscale)
THEN
222 IF (neighbor_kind_pair%is_onfo(ipair))
THEN
223 pot => potparm14%pot(kind_a, kind_b)%pot
234 IF ((.NOT. full_nl) .AND. (atom_a == atom_b))
THEN
235 fac_ei = 0.5_dp*fac_ei
236 fac_vdw = 0.5_dp*fac_vdw
239 IF (do_multipoles .OR. (.NOT. fist_nonbond_env%do_electrostatics))
THEN
242 IF (ipair <= neighbor_kind_pair%nscale)
THEN
243 fac_ei = fac_ei*neighbor_kind_pair%ei_scale(ipair)
244 fac_vdw = fac_vdw*neighbor_kind_pair%vdw_scale(ipair)
247 IF (fac_ei > 0.0_dp)
THEN
249 mm_radius_a = mm_radius(kind_a)
250 mm_radius_b = mm_radius(kind_b)
251 IF (
ASSOCIATED(fist_nonbond_env%charges))
THEN
252 qeff_a = fist_nonbond_env%charges(atom_a)
253 qeff_b = fist_nonbond_env%charges(atom_b)
255 qeff_a = qeff(kind_a)
256 qeff_b = qeff(kind_b)
258 IF (is_shell_kind(kind_a))
THEN
259 qcore_a = qcore(kind_a)
260 qshell_a = qshell(kind_a)
261 IF ((qcore_a == 0.0_dp) .AND. (qshell_a == 0.0_dp)) fac_ei = 0.0_dp
264 qshell_a = huge(0.0_dp)
265 IF (qeff_a == 0.0_dp) fac_ei = 0.0_dp
267 IF (is_shell_kind(kind_b))
THEN
268 qcore_b = qcore(kind_b)
269 qshell_b = qshell(kind_b)
270 IF ((qcore_b == 0.0_dp) .AND. (qshell_b == 0.0_dp)) fac_ei = 0.0_dp
273 qshell_b = huge(0.0_dp)
274 IF (qeff_b == 0.0_dp) fac_ei = 0.0_dp
280 IF (mm_radius_a > 0)
THEN
283 IF (mm_radius_b > 0)
THEN
286 IF ((mm_radius_a > 0) .OR. (mm_radius_b > 0))
THEN
287 beta =
sqrthalf/sqrt(mm_radius_a*mm_radius_a + mm_radius_b*mm_radius_b)
293 IF (pot%no_pp .AND. (fac_ei == 0.0)) cycle
297 spline_data => pot%pair_spline_data
298 shell_type = pot%shell_type
300 cpassert(.NOT. do_multipoles)
301 cpassert(shell_present)
303 rab2_max = pot%rcutsq
309 IF (shell_type ==
sh_sh)
THEN
310 shell_a = particle_set(atom_a)%shell_index
311 shell_b = particle_set(atom_b)%shell_index
312 rab_cc = rcore_last_update_pbc(shell_b)%r - rcore_last_update_pbc(shell_a)%r
313 rab_cs = rshell_last_update_pbc(shell_b)%r - rcore_last_update_pbc(shell_a)%r
314 rab_sc = rcore_last_update_pbc(shell_b)%r - rshell_last_update_pbc(shell_a)%r
315 rab_ss = rshell_last_update_pbc(shell_b)%r - rshell_last_update_pbc(shell_a)%r
316 rab_list(1:3, 1) = rab_cc(1:3) + cell_v(1:3)
317 rab_list(1:3, 2) = rab_cs(1:3) + cell_v(1:3)
318 rab_list(1:3, 3) = rab_sc(1:3) + cell_v(1:3)
319 rab_list(1:3, 4) = rab_ss(1:3) + cell_v(1:3)
320 ELSE IF ((shell_type ==
nosh_sh) .AND. (particle_set(atom_a)%shell_index /= 0))
THEN
321 shell_a = particle_set(atom_a)%shell_index
323 rab_cc = r_last_update_pbc(atom_b)%r - rcore_last_update_pbc(shell_a)%r
326 rab_ss = r_last_update_pbc(atom_b)%r - rshell_last_update_pbc(shell_a)%r
327 rab_list(1:3, 1) = rab_cc(1:3) + cell_v(1:3)
328 rab_list(1:3, 2) = 0.0_dp
329 rab_list(1:3, 3) = 0.0_dp
330 rab_list(1:3, 4) = rab_ss(1:3) + cell_v(1:3)
331 ELSE IF ((shell_type ==
nosh_sh) .AND. (particle_set(atom_b)%shell_index /= 0))
THEN
332 shell_b = particle_set(atom_b)%shell_index
334 rab_cc = rcore_last_update_pbc(shell_b)%r - r_last_update_pbc(atom_a)%r
337 rab_ss = rshell_last_update_pbc(shell_b)%r - r_last_update_pbc(atom_a)%r
338 rab_list(1:3, 1) = rab_cc(1:3) + cell_v(1:3)
339 rab_list(1:3, 2) = 0.0_dp
340 rab_list(1:3, 3) = 0.0_dp
341 rab_list(1:3, 4) = rab_ss(1:3) + cell_v(1:3)
343 rab_list(:, :) = 0.0_dp
346 check_terms:
DO i = 1, 4
347 rab2_list(i) = rab_list(1, i)**2 + rab_list(2, i)**2 + rab_list(3, i)**2
348 IF (rab2_list(i) >= rab2_max)
THEN
353 rab_com = r_last_update_pbc(atom_b)%r - r_last_update_pbc(atom_a)%r
356 rab_cc = r_last_update_pbc(atom_b)%r - r_last_update_pbc(atom_a)%r
360 rab_list(:, :) = 0.0_dp
362 rab_com = rab_com + cell_v
363 rab2_com = rab_com(1)**2 + rab_com(2)**2 + rab_com(3)**2
373 IF (use_virial) pv(:, :) = 0.0_dp
376 IF ((rab2_com <= rab2_max) .AND. all_terms)
THEN
382 IF (shell_a == 0)
THEN
385 ewald_type, alpha, beta_a, &
386 ei_interaction_cutoffs(2, kind_a, kind_b))
387 CALL add_force_nonbond(fatom_a, fcore_b, pv, fscalar, rab, use_virial)
388 ELSE IF (shell_b == 0)
THEN
391 ewald_type, alpha, beta_b, &
392 ei_interaction_cutoffs(2, kind_b, kind_a))
393 CALL add_force_nonbond(fcore_a, fatom_b, pv, fscalar, rab, use_virial)
397 ewald_type, alpha, 0.0_dp, &
398 ei_interaction_cutoffs(1, kind_a, kind_b))
399 CALL add_force_nonbond(fcore_a, fcore_b, pv, fscalar, rab, use_virial)
404 IF (shell_type ==
sh_sh)
THEN
409 IF (fac_vdw > 0)
THEN
410 energy =
potential_s(spline_data, rab2, fscalar, spl_f, logger)
411 etot = etot + energy*fac_vdw
412 fscalar = fscalar*fac_vdw
417 ewald_type, alpha, beta, &
418 ei_interaction_cutoffs(3, kind_a, kind_b))
421 CALL add_force_nonbond(fshell_a, fshell_b, pv, fscalar, rab, use_virial)
430 ewald_type, alpha, beta_b, &
431 ei_interaction_cutoffs(2, kind_b, kind_a))
433 CALL add_force_nonbond(fcore_a, fshell_b, pv, fscalar, rab, use_virial)
440 ewald_type, alpha, beta_a, &
441 ei_interaction_cutoffs(2, kind_a, kind_b))
443 CALL add_force_nonbond(fshell_a, fcore_b, pv, fscalar, rab, use_virial)
445 ELSE IF ((shell_type ==
nosh_sh) .AND. (shell_a == 0))
THEN
450 IF (fac_vdw > 0)
THEN
451 energy =
potential_s(spline_data, rab2, fscalar, spl_f, logger)
452 etot = etot + energy*fac_vdw
453 fscalar = fscalar*fac_vdw
458 ewald_type, alpha, beta, &
459 ei_interaction_cutoffs(3, kind_a, kind_b))
462 CALL add_force_nonbond(fatom_a, fshell_b, pv, fscalar, rab, use_virial)
463 ELSE IF ((shell_type ==
nosh_sh) .AND. (shell_b == 0))
THEN
468 IF (fac_vdw > 0)
THEN
469 energy =
potential_s(spline_data, rab2, fscalar, spl_f, logger)
470 etot = etot + energy*fac_vdw
471 fscalar = fscalar*fac_vdw
476 ewald_type, alpha, beta, &
477 ei_interaction_cutoffs(3, kind_a, kind_b))
480 CALL add_force_nonbond(fshell_a, fatom_b, pv, fscalar, rab, use_virial)
484 IF (rab2_com <= rab2_max)
THEN
490 IF (fac_vdw > 0)
THEN
491 energy =
potential_s(spline_data, rab2, fscalar, spl_f, logger)
492 etot = etot + energy*fac_vdw
493 fscalar = fscalar*fac_vdw
498 ewald_type, alpha, beta, &
499 ei_interaction_cutoffs(3, kind_a, kind_b))
502 CALL add_force_nonbond(fatom_a, fatom_b, pv, fscalar, rab, use_virial)
507 pot_nonbond = pot_nonbond + etot
508 IF (atprop_env%energy)
THEN
511 atprop_env%atener(atom_a) = atprop_env%atener(atom_a) + 0.5_dp*etot
513 atprop_env%atener(atom_b) = atprop_env%atener(atom_b) + 0.5_dp*etot
518 f_nonbond(i, atom_a) = f_nonbond(i, atom_a) + fatom_a(i)
520 f_nonbond(i, atom_b) = f_nonbond(i, atom_b) + fatom_b(i)
522 IF (shell_a > 0)
THEN
525 fcore_nonbond(i, shell_a) = fcore_nonbond(i, shell_a) + fcore_a(i)
527 fshell_nonbond(i, shell_a) = fshell_nonbond(i, shell_a) + fshell_a(i)
530 IF (shell_b > 0)
THEN
533 fcore_nonbond(i, shell_b) = fcore_nonbond(i, shell_b) + fcore_b(i)
535 fshell_nonbond(i, shell_b) = fshell_nonbond(i, shell_b) + fshell_b(i)
542 pv_thread(j, i) = pv_thread(j, i) + pv(j, i)
552 pv_nonbond(j, i) = pv_nonbond(j, i) + pv_thread(j, i)
557 END DO kind_group_loop
563 DEALLOCATE (mm_radius)
567 DEALLOCATE (is_shell_kind)
569 CALL timestop(handle)
638 local_particles, particle_set, ewald_env, v_bonded_corr, pv_bc, &
639 shell_particle_set, core_particle_set, atprop_env, cell, use_virial)
646 REAL(kind=
dp),
INTENT(OUT) :: v_bonded_corr
647 REAL(kind=
dp),
DIMENSION(:, :),
INTENT(OUT) :: pv_bc
648 TYPE(
particle_type),
OPTIONAL,
POINTER :: shell_particle_set(:), &
652 LOGICAL,
INTENT(IN) :: use_virial
654 CHARACTER(LEN=*),
PARAMETER :: routinen =
'bonded_correct_gaussian'
656 INTEGER :: atom_a, atom_b, handle, iatom, iend, igrp, ilist, ipair, istart, kind_a, kind_b, &
657 natoms_per_kind, nkind, npairs, shell_a, shell_b
658 INTEGER,
DIMENSION(:, :),
POINTER ::
list
659 LOGICAL :: a_is_shell, b_is_shell, do_multipoles, &
660 full_nl, shell_adiabatic
661 REAL(kind=
dp) :: alpha, const, fac_cor, fac_ei, qcore_a, &
662 qcore_b, qeff_a, qeff_b, qshell_a, &
664 REAL(kind=
dp),
DIMENSION(3) :: rca, rcb, rsa, rsb
665 REAL(kind=
dp),
DIMENSION(:, :),
POINTER :: ij_kind_full_fac
674 CALL timeset(routinen, handle)
677 IF (use_virial) pv_bc = 0.0_dp
678 v_bonded_corr = 0.0_dp
681 potparm14=potparm14, potparm=potparm, &
682 ij_kind_full_fac=ij_kind_full_fac)
683 CALL ewald_env_get(ewald_env, alpha=alpha, do_multipoles=do_multipoles, &
689 shell_adiabatic=shell_adiabatic)
691 lists:
DO ilist = 1, nonbonded%nlists
692 neighbor_kind_pair => nonbonded%neighbor_kind_pairs(ilist)
693 npairs = neighbor_kind_pair%nscale
694 IF (npairs == 0) cycle
695 list => neighbor_kind_pair%list
696 kind_group_loop:
DO igrp = 1, neighbor_kind_pair%ngrp_kind
697 istart = neighbor_kind_pair%grp_kind_start(igrp)
698 IF (istart > npairs)
THEN
701 iend = min(npairs, neighbor_kind_pair%grp_kind_end(igrp))
703 pairs:
DO ipair = istart, iend
704 atom_a =
list(1, ipair)
705 atom_b =
list(2, ipair)
708 kind_a = particle_set(atom_a)%atomic_kind%kind_number
709 kind_b = particle_set(atom_b)%atomic_kind%kind_number
712 pot => potparm%pot(kind_a, kind_b)%pot
713 IF (ipair <= neighbor_kind_pair%nscale)
THEN
714 IF (neighbor_kind_pair%is_onfo(ipair))
THEN
715 pot => potparm14%pot(kind_a, kind_b)%pot
720 fac_ei = ij_kind_full_fac(kind_a, kind_b)
725 IF ((.NOT. full_nl) .AND. (atom_a == atom_b))
THEN
726 fac_ei = fac_ei*0.5_dp
728 IF (ipair <= neighbor_kind_pair%nscale)
THEN
729 fac_ei = fac_ei*neighbor_kind_pair%ei_scale(ipair)
733 fac_cor = 1.0_dp - fac_ei
734 IF (fac_cor <= 0.0_dp) cycle
737 atomic_kind => atomic_kind_set(kind_a)
739 IF (
ASSOCIATED(fist_nonbond_env%charges)) qeff_a = fist_nonbond_env%charges(atom_a)
740 a_is_shell =
ASSOCIATED(shell_kind)
742 CALL get_shell(shell=shell_kind, charge_core=qcore_a, &
743 charge_shell=qshell_a)
744 shell_a = particle_set(atom_a)%shell_index
745 rca = core_particle_set(shell_a)%r
746 rsa = shell_particle_set(shell_a)%r
749 qshell_a = huge(0.0_dp)
751 rca = particle_set(atom_a)%r
756 atomic_kind => atomic_kind_set(kind_b)
758 IF (
ASSOCIATED(fist_nonbond_env%charges)) qeff_b = fist_nonbond_env%charges(atom_b)
759 b_is_shell =
ASSOCIATED(shell_kind)
761 CALL get_shell(shell=shell_kind, charge_core=qcore_b, &
762 charge_shell=qshell_b)
763 shell_b = particle_set(atom_b)%shell_index
764 rcb = core_particle_set(shell_b)%r
765 rsb = shell_particle_set(shell_b)%r
768 qshell_b = huge(0.0_dp)
770 rcb = particle_set(atom_b)%r
775 IF (a_is_shell .AND. b_is_shell)
THEN
777 CALL bonded_correct_gaussian_low(rca, rcb, cell, &
778 v_bonded_corr, core_particle_set, core_particle_set, &
779 shell_a, shell_b, .true., alpha, qcore_a, qcore_b, &
780 const, fac_cor, pv_bc, atprop_env, use_virial)
781 ELSE IF (a_is_shell)
THEN
783 CALL bonded_correct_gaussian_low(rca, rcb, cell, &
784 v_bonded_corr, core_particle_set, particle_set, &
785 shell_a, atom_b, .true., alpha, qcore_a, qcore_b, &
786 const, fac_cor, pv_bc, atprop_env, use_virial)
787 ELSE IF (b_is_shell)
THEN
789 CALL bonded_correct_gaussian_low(rca, rcb, cell, &
790 v_bonded_corr, particle_set, core_particle_set, &
791 atom_a, shell_b, .true., alpha, qcore_a, qcore_b, &
792 const, fac_cor, pv_bc, atprop_env, use_virial)
795 CALL bonded_correct_gaussian_low(rca, rcb, cell, &
796 v_bonded_corr, particle_set, particle_set, &
797 atom_a, atom_b, .true., alpha, qcore_a, qcore_b, &
798 const, fac_cor, pv_bc, atprop_env, use_virial)
803 IF (a_is_shell .AND. b_is_shell)
THEN
805 CALL bonded_correct_gaussian_low(rsa, rsa, cell, &
806 v_bonded_corr, shell_particle_set, shell_particle_set, &
807 shell_a, shell_b, shell_adiabatic, alpha, qshell_a, &
808 qshell_b, const, fac_cor, pv_bc, atprop_env, use_virial)
813 CALL bonded_correct_gaussian_low(rsa, rcb, cell, &
814 v_bonded_corr, shell_particle_set, core_particle_set, &
815 shell_a, shell_b, shell_adiabatic, alpha, qshell_a, qcore_b, &
816 const, fac_cor, pv_bc, atprop_env, use_virial)
819 CALL bonded_correct_gaussian_low(rsa, rcb, cell, &
820 v_bonded_corr, shell_particle_set, particle_set, &
821 shell_a, atom_b, shell_adiabatic, alpha, qshell_a, qcore_b, &
822 const, fac_cor, pv_bc, atprop_env, use_virial)
828 CALL bonded_correct_gaussian_low(rca, rsb, cell, &
829 v_bonded_corr, core_particle_set, shell_particle_set, &
830 shell_a, shell_b, shell_adiabatic, alpha, qcore_a, qshell_b, &
831 const, fac_cor, pv_bc, atprop_env, use_virial)
834 CALL bonded_correct_gaussian_low(rca, rsb, cell, &
835 v_bonded_corr, particle_set, shell_particle_set, &
836 atom_a, shell_b, shell_adiabatic, alpha, qcore_a, qshell_b, &
837 const, fac_cor, pv_bc, atprop_env, use_virial)
841 END DO kind_group_loop
845 nkind =
SIZE(atomic_kind_set)
848 atomic_kind => atomic_kind_set(kind_a)
850 IF (
ASSOCIATED(shell_kind))
THEN
851 CALL get_shell(shell=shell_kind, charge_core=qcore_a, &
852 charge_shell=qshell_a)
854 natoms_per_kind = local_particles%n_el(kind_a)
855 DO iatom = 1, natoms_per_kind
858 atom_a = local_particles%list(kind_a)%array(iatom)
859 shell_a = particle_set(atom_a)%shell_index
860 rca = core_particle_set(shell_a)%r
861 rsa = shell_particle_set(shell_a)%r
863 CALL bonded_correct_gaussian_low_sh(rca, rsa, cell, &
864 v_bonded_corr, core_particle_set, shell_particle_set, &
865 shell_a, shell_adiabatic, alpha, qcore_a, qshell_a, &
866 const, pv_bc, atprop_env, use_virial)
872 CALL group%sum(v_bonded_corr)
874 CALL timestop(handle)