(git:ed6f26b)
Loading...
Searching...
No Matches
manybody_nequip.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!> \par History
10!> nequip implementation
11!> \author Gabriele Tocci
12! **************************************************************************************************
14
16 USE cell_types, ONLY: cell_type
24 USE kinds, ONLY: dp,&
25 int_8,&
26 sp
33 USE torch_api, ONLY: &
37 USE util, ONLY: sort
38#include "./base/base_uses.f90"
39
40 IMPLICIT NONE
41
42 PRIVATE
45 CHARACTER(len=*), PARAMETER, PRIVATE :: moduleN = 'manybody_nequip'
46
47CONTAINS
48
49! **************************************************************************************************
50!> \brief ...
51!> \param nonbonded ...
52!> \param potparm ...
53!> \param glob_loc_list ...
54!> \param glob_cell_v ...
55!> \param glob_loc_list_a ...
56!> \param cell ...
57!> \par History
58!> Implementation of the nequip potential - [gtocci] 2022
59!> \author Gabriele Tocci - University of Zurich
60! **************************************************************************************************
61 SUBROUTINE setup_nequip_arrays(nonbonded, potparm, glob_loc_list, glob_cell_v, glob_loc_list_a, cell)
62 TYPE(fist_neighbor_type), POINTER :: nonbonded
63 TYPE(pair_potential_pp_type), POINTER :: potparm
64 INTEGER, DIMENSION(:, :), POINTER :: glob_loc_list
65 REAL(kind=dp), DIMENSION(:, :), POINTER :: glob_cell_v
66 INTEGER, DIMENSION(:), POINTER :: glob_loc_list_a
67 TYPE(cell_type), POINTER :: cell
68
69 CHARACTER(LEN=*), PARAMETER :: routinen = 'setup_nequip_arrays'
70
71 INTEGER :: handle, i, iend, igrp, ikind, ilist, &
72 ipair, istart, jkind, nkinds, npairs, &
73 npairs_tot
74 INTEGER, ALLOCATABLE, DIMENSION(:) :: work_list, work_list2
75 INTEGER, DIMENSION(:, :), POINTER :: list
76 REAL(kind=dp), ALLOCATABLE, DIMENSION(:, :) :: rwork_list
77 REAL(kind=dp), DIMENSION(3) :: cell_v, cvi
78 TYPE(neighbor_kind_pairs_type), POINTER :: neighbor_kind_pair
79 TYPE(pair_potential_single_type), POINTER :: pot
80
81 cpassert(.NOT. ASSOCIATED(glob_loc_list))
82 cpassert(.NOT. ASSOCIATED(glob_loc_list_a))
83 cpassert(.NOT. ASSOCIATED(glob_cell_v))
84 CALL timeset(routinen, handle)
85 npairs_tot = 0
86 nkinds = SIZE(potparm%pot, 1)
87 DO ilist = 1, nonbonded%nlists
88 neighbor_kind_pair => nonbonded%neighbor_kind_pairs(ilist)
89 npairs = neighbor_kind_pair%npairs
90 IF (npairs == 0) cycle
91 kind_group_loop1: DO igrp = 1, neighbor_kind_pair%ngrp_kind
92 istart = neighbor_kind_pair%grp_kind_start(igrp)
93 iend = neighbor_kind_pair%grp_kind_end(igrp)
94 ikind = neighbor_kind_pair%ij_kind(1, igrp)
95 jkind = neighbor_kind_pair%ij_kind(2, igrp)
96 pot => potparm%pot(ikind, jkind)%pot
97 npairs = iend - istart + 1
98 IF (pot%no_mb) cycle
99 DO i = 1, SIZE(pot%type)
100 IF (pot%type(i) == nequip_type) npairs_tot = npairs_tot + npairs
101 END DO
102 END DO kind_group_loop1
103 END DO
104 ALLOCATE (work_list(npairs_tot))
105 ALLOCATE (work_list2(npairs_tot))
106 ALLOCATE (glob_loc_list(2, npairs_tot))
107 ALLOCATE (glob_cell_v(3, npairs_tot))
108 ! Fill arrays with data
109 npairs_tot = 0
110 DO ilist = 1, nonbonded%nlists
111 neighbor_kind_pair => nonbonded%neighbor_kind_pairs(ilist)
112 npairs = neighbor_kind_pair%npairs
113 IF (npairs == 0) cycle
114 kind_group_loop2: DO igrp = 1, neighbor_kind_pair%ngrp_kind
115 istart = neighbor_kind_pair%grp_kind_start(igrp)
116 iend = neighbor_kind_pair%grp_kind_end(igrp)
117 ikind = neighbor_kind_pair%ij_kind(1, igrp)
118 jkind = neighbor_kind_pair%ij_kind(2, igrp)
119 list => neighbor_kind_pair%list
120 cvi = neighbor_kind_pair%cell_vector
121 pot => potparm%pot(ikind, jkind)%pot
122 npairs = iend - istart + 1
123 IF (pot%no_mb) cycle
124 cell_v = matmul(cell%hmat, cvi)
125 DO i = 1, SIZE(pot%type)
126 ! NEQUIP
127 IF (pot%type(i) == nequip_type) THEN
128 DO ipair = 1, npairs
129 glob_loc_list(:, npairs_tot + ipair) = list(:, istart - 1 + ipair)
130 glob_cell_v(1:3, npairs_tot + ipair) = cell_v(1:3)
131 END DO
132 npairs_tot = npairs_tot + npairs
133 END IF
134 END DO
135 END DO kind_group_loop2
136 END DO
137 ! Order the arrays w.r.t. the first index of glob_loc_list
138 CALL sort(glob_loc_list(1, :), npairs_tot, work_list)
139 DO ipair = 1, npairs_tot
140 work_list2(ipair) = glob_loc_list(2, work_list(ipair))
141 END DO
142 glob_loc_list(2, :) = work_list2
143 DEALLOCATE (work_list2)
144 ALLOCATE (rwork_list(3, npairs_tot))
145 DO ipair = 1, npairs_tot
146 rwork_list(:, ipair) = glob_cell_v(:, work_list(ipair))
147 END DO
148 glob_cell_v = rwork_list
149 DEALLOCATE (rwork_list)
150 DEALLOCATE (work_list)
151 ALLOCATE (glob_loc_list_a(npairs_tot))
152 glob_loc_list_a = glob_loc_list(1, :)
153 CALL timestop(handle)
154 END SUBROUTINE setup_nequip_arrays
155
156! **************************************************************************************************
157!> \brief ...
158!> \param glob_loc_list ...
159!> \param glob_cell_v ...
160!> \param glob_loc_list_a ...
161!> \par History
162!> Implementation of the nequip potential - [gtocci] 2022
163!> \author Gabriele Tocci - University of Zurich
164! **************************************************************************************************
165 SUBROUTINE destroy_nequip_arrays(glob_loc_list, glob_cell_v, glob_loc_list_a)
166 INTEGER, DIMENSION(:, :), POINTER :: glob_loc_list
167 REAL(kind=dp), DIMENSION(:, :), POINTER :: glob_cell_v
168 INTEGER, DIMENSION(:), POINTER :: glob_loc_list_a
169
170 IF (ASSOCIATED(glob_loc_list)) THEN
171 DEALLOCATE (glob_loc_list)
172 END IF
173 IF (ASSOCIATED(glob_loc_list_a)) THEN
174 DEALLOCATE (glob_loc_list_a)
175 END IF
176 IF (ASSOCIATED(glob_cell_v)) THEN
177 DEALLOCATE (glob_cell_v)
178 END IF
179
180 END SUBROUTINE destroy_nequip_arrays
181! **************************************************************************************************
182!> \brief ...
183!> \param nonbonded ...
184!> \param particle_set ...
185!> \param cell ...
186!> \param atomic_kind_set ...
187!> \param potparm ...
188!> \param nequip ...
189!> \param glob_loc_list_a ...
190!> \param r_last_update_pbc ...
191!> \param pot_nequip ...
192!> \param fist_nonbond_env ...
193!> \param para_env ...
194!> \param use_virial ...
195!> \par History
196!> Implementation of the nequip potential - [gtocci] 2022
197!> Index mapping of atoms from .xyz to Allegro config.yaml file - [mbilichenko] 2024
198!> \author Gabriele Tocci - University of Zurich
199! **************************************************************************************************
200 SUBROUTINE nequip_energy_store_force_virial(nonbonded, particle_set, cell, atomic_kind_set, &
201 potparm, nequip, glob_loc_list_a, r_last_update_pbc, &
202 pot_nequip, fist_nonbond_env, para_env, use_virial)
203
204 TYPE(fist_neighbor_type), POINTER :: nonbonded
205 TYPE(particle_type), POINTER :: particle_set(:)
206 TYPE(cell_type), POINTER :: cell
207 TYPE(atomic_kind_type), POINTER :: atomic_kind_set(:)
208 TYPE(pair_potential_pp_type), POINTER :: potparm
209 TYPE(nequip_pot_type), POINTER :: nequip
210 INTEGER, DIMENSION(:), POINTER :: glob_loc_list_a
211 TYPE(pos_type), DIMENSION(:), POINTER :: r_last_update_pbc
212 REAL(kind=dp) :: pot_nequip
213 TYPE(fist_nonbond_env_type), POINTER :: fist_nonbond_env
214 TYPE(mp_para_env_type), POINTER :: para_env
215 LOGICAL, INTENT(IN) :: use_virial
216
217 CHARACTER(LEN=*), PARAMETER :: routinen = 'nequip_energy_store_force_virial'
218
219 INTEGER :: atom_a, atom_b, atom_idx, handle, i, iat, iat_use, iend, ifirst, igrp, ikind, &
220 ilast, ilist, ipair, istart, iunique, jkind, junique, mpair, n_atoms, n_atoms_use, &
221 nedges, nedges_tot, nloc_size, npairs, nunique
222 INTEGER(kind=int_8), ALLOCATABLE :: atom_types(:)
223 INTEGER(kind=int_8), ALLOCATABLE, DIMENSION(:, :) :: edge_index, t_edge_index, temp_edge_index
224 INTEGER, ALLOCATABLE, DIMENSION(:) :: displ, displ_cell, edge_count, &
225 edge_count_cell, work_list
226 INTEGER, DIMENSION(:, :), POINTER :: list, sort_list
227 LOGICAL, ALLOCATABLE :: use_atom(:)
228 REAL(kind=dp) :: drij, rab2_max, rij(3)
229 REAL(kind=dp), ALLOCATABLE, DIMENSION(:, :) :: edge_cell_shifts, lattice, pos, &
230 temp_edge_cell_shifts
231 REAL(kind=dp), DIMENSION(3) :: cell_v, cvi
232 REAL(kind=dp), DIMENSION(:, :), POINTER :: atomic_energy, forces, total_energy
233 REAL(kind=dp), DIMENSION(:, :, :), POINTER :: virial3d
234 REAL(kind=sp), ALLOCATABLE, DIMENSION(:, :) :: edge_cell_shifts_sp, lattice_sp, pos_sp
235 REAL(kind=sp), DIMENSION(:, :), POINTER :: atomic_energy_sp, forces_sp, &
236 total_energy_sp
237 TYPE(neighbor_kind_pairs_type), POINTER :: neighbor_kind_pair
238 TYPE(nequip_data_type), POINTER :: nequip_data
239 TYPE(pair_potential_single_type), POINTER :: pot
240 TYPE(torch_dict_type) :: inputs, outputs
241 TYPE(torch_tensor_type) :: atom_types_tensor, atomic_energy_tensor, edge_cell_shifts_tensor, &
242 forces_tensor, lattice_tensor, pos_tensor, t_edge_index_tensor, total_energy_tensor, &
243 virial_tensor
244
245 CALL timeset(routinen, handle)
246
247 NULLIFY (total_energy, atomic_energy, forces, total_energy_sp, atomic_energy_sp, forces_sp, virial3d)
248 n_atoms = SIZE(particle_set)
249 ALLOCATE (use_atom(n_atoms))
250 use_atom = .false.
251
252 DO ikind = 1, SIZE(atomic_kind_set)
253 DO jkind = 1, SIZE(atomic_kind_set)
254 pot => potparm%pot(ikind, jkind)%pot
255 DO i = 1, SIZE(pot%type)
256 IF (pot%type(i) /= nequip_type) cycle
257 DO iat = 1, n_atoms
258 IF (particle_set(iat)%atomic_kind%kind_number == ikind .OR. &
259 particle_set(iat)%atomic_kind%kind_number == jkind) use_atom(iat) = .true.
260 END DO ! iat
261 END DO ! i
262 END DO ! jkind
263 END DO ! ikind
264 n_atoms_use = count(use_atom)
265
266 ! get nequip_data to save force, virial info and to load model
267 CALL fist_nonbond_env_get(fist_nonbond_env, nequip_data=nequip_data)
268 IF (.NOT. ASSOCIATED(nequip_data)) THEN
269 ALLOCATE (nequip_data)
270 CALL fist_nonbond_env_set(fist_nonbond_env, nequip_data=nequip_data)
271 NULLIFY (nequip_data%use_indices, nequip_data%force)
272 CALL torch_model_load(nequip_data%model, pot%set(1)%nequip%nequip_file_name)
273 CALL torch_model_freeze(nequip_data%model)
274 END IF
275 IF (ASSOCIATED(nequip_data%force)) THEN
276 IF (SIZE(nequip_data%force, 2) /= n_atoms_use) THEN
277 DEALLOCATE (nequip_data%force, nequip_data%use_indices)
278 END IF
279 END IF
280 IF (.NOT. ASSOCIATED(nequip_data%force)) THEN
281 ALLOCATE (nequip_data%force(3, n_atoms_use))
282 ALLOCATE (nequip_data%use_indices(n_atoms_use))
283 END IF
284
285 iat_use = 0
286 DO iat = 1, n_atoms_use
287 IF (use_atom(iat)) THEN
288 iat_use = iat_use + 1
289 nequip_data%use_indices(iat_use) = iat
290 END IF
291 END DO
292
293 nedges = 0
294 ALLOCATE (edge_index(2, SIZE(glob_loc_list_a)))
295 ALLOCATE (edge_cell_shifts(3, SIZE(glob_loc_list_a)))
296 DO ilist = 1, nonbonded%nlists
297 neighbor_kind_pair => nonbonded%neighbor_kind_pairs(ilist)
298 npairs = neighbor_kind_pair%npairs
299 IF (npairs == 0) cycle
300 kind_group_loop_nequip: DO igrp = 1, neighbor_kind_pair%ngrp_kind
301 istart = neighbor_kind_pair%grp_kind_start(igrp)
302 iend = neighbor_kind_pair%grp_kind_end(igrp)
303 ikind = neighbor_kind_pair%ij_kind(1, igrp)
304 jkind = neighbor_kind_pair%ij_kind(2, igrp)
305 list => neighbor_kind_pair%list
306 cvi = neighbor_kind_pair%cell_vector
307 pot => potparm%pot(ikind, jkind)%pot
308 DO i = 1, SIZE(pot%type)
309 IF (pot%type(i) /= nequip_type) cycle
310 rab2_max = pot%set(i)%nequip%rcutsq
311 cell_v = matmul(cell%hmat, cvi)
312 pot => potparm%pot(ikind, jkind)%pot
313 nequip => pot%set(i)%nequip
314 npairs = iend - istart + 1
315 IF (npairs /= 0) THEN
316 ALLOCATE (sort_list(2, npairs), work_list(npairs))
317 sort_list = list(:, istart:iend)
318 ! Sort the list of neighbors, this increases the efficiency for single
319 ! potential contributions
320 CALL sort(sort_list(1, :), npairs, work_list)
321 DO ipair = 1, npairs
322 work_list(ipair) = sort_list(2, work_list(ipair))
323 END DO
324 sort_list(2, :) = work_list
325 ! find number of unique elements of array index 1
326 nunique = 1
327 DO ipair = 1, npairs - 1
328 IF (sort_list(1, ipair + 1) /= sort_list(1, ipair)) nunique = nunique + 1
329 END DO
330 ipair = 1
331 junique = sort_list(1, ipair)
332 ifirst = 1
333 DO iunique = 1, nunique
334 atom_a = junique
335 IF (glob_loc_list_a(ifirst) > atom_a) cycle
336 DO mpair = ifirst, SIZE(glob_loc_list_a)
337 IF (glob_loc_list_a(mpair) == atom_a) EXIT
338 END DO
339 ifirst = mpair
340 DO mpair = ifirst, SIZE(glob_loc_list_a)
341 IF (glob_loc_list_a(mpair) /= atom_a) EXIT
342 END DO
343 ilast = mpair - 1
344 nloc_size = 0
345 IF (ifirst /= 0) nloc_size = ilast - ifirst + 1
346 DO WHILE (ipair <= npairs)
347 IF (sort_list(1, ipair) /= junique) EXIT
348 atom_b = sort_list(2, ipair)
349 rij(:) = r_last_update_pbc(atom_b)%r(:) - r_last_update_pbc(atom_a)%r(:) + cell_v
350 drij = dot_product(rij, rij)
351 ipair = ipair + 1
352 IF (drij <= rab2_max) THEN
353 nedges = nedges + 1
354 edge_index(:, nedges) = [atom_a - 1, atom_b - 1]
355 edge_cell_shifts(:, nedges) = cvi
356 END IF
357 END DO
358 ifirst = ilast + 1
359 IF (ipair <= npairs) junique = sort_list(1, ipair)
360 END DO
361 DEALLOCATE (sort_list, work_list)
362 END IF
363 END DO
364 END DO kind_group_loop_nequip
365 END DO
366
367 nequip => pot%set(1)%nequip
368
369 ALLOCATE (edge_count(para_env%num_pe))
370 ALLOCATE (edge_count_cell(para_env%num_pe))
371 ALLOCATE (displ_cell(para_env%num_pe))
372 ALLOCATE (displ(para_env%num_pe))
373
374 CALL para_env%allgather(nedges, edge_count)
375 nedges_tot = sum(edge_count)
376
377 ALLOCATE (temp_edge_index(2, nedges))
378 temp_edge_index(:, :) = edge_index(:, :nedges)
379 DEALLOCATE (edge_index)
380 ALLOCATE (temp_edge_cell_shifts(3, nedges))
381 temp_edge_cell_shifts(:, :) = edge_cell_shifts(:, :nedges)
382 DEALLOCATE (edge_cell_shifts)
383
384 ALLOCATE (edge_index(2, nedges_tot))
385 ALLOCATE (edge_cell_shifts(3, nedges_tot))
386 ALLOCATE (t_edge_index(nedges_tot, 2))
387
388 edge_count_cell(:) = edge_count*3
389 edge_count = edge_count*2
390 displ(1) = 0
391 displ_cell(1) = 0
392 DO ipair = 2, para_env%num_pe
393 displ(ipair) = displ(ipair - 1) + edge_count(ipair - 1)
394 displ_cell(ipair) = displ_cell(ipair - 1) + edge_count_cell(ipair - 1)
395 END DO
396
397 CALL para_env%allgatherv(temp_edge_cell_shifts, edge_cell_shifts, edge_count_cell, displ_cell)
398 CALL para_env%allgatherv(temp_edge_index, edge_index, edge_count, displ)
399
400 t_edge_index(:, :) = transpose(edge_index)
401 DEALLOCATE (temp_edge_index, temp_edge_cell_shifts, edge_index)
402
403 ALLOCATE (lattice(3, 3), lattice_sp(3, 3))
404 lattice(:, :) = cell%hmat/nequip%unit_cell_val
405 lattice_sp(:, :) = real(lattice, kind=sp)
406
407 iat_use = 0
408 ALLOCATE (pos(3, n_atoms_use), atom_types(n_atoms_use))
409
410 DO iat = 1, n_atoms_use
411 IF (.NOT. use_atom(iat)) cycle
412 iat_use = iat_use + 1
413 ! Find index of the element based on its position in config.yaml file to have correct mapping
414 DO i = 1, SIZE(nequip%type_names_torch)
415 IF (particle_set(iat)%atomic_kind%element_symbol == nequip%type_names_torch(i)) THEN
416 atom_idx = i - 1
417 END IF
418 END DO
419 atom_types(iat_use) = atom_idx
420 pos(:, iat) = r_last_update_pbc(iat)%r(:)/nequip%unit_coords_val
421 END DO
422
423 CALL torch_dict_create(inputs)
424 IF (nequip%do_nequip_sp) THEN
425 ALLOCATE (pos_sp(3, n_atoms_use), edge_cell_shifts_sp(3, nedges_tot))
426 pos_sp(:, :) = real(pos(:, :), kind=sp)
427 edge_cell_shifts_sp(:, :) = real(edge_cell_shifts(:, :), kind=sp)
428 CALL torch_tensor_from_array(pos_tensor, pos_sp)
429 CALL torch_tensor_from_array(edge_cell_shifts_tensor, edge_cell_shifts_sp)
430 CALL torch_tensor_from_array(lattice_tensor, lattice_sp)
431 ELSE
432 CALL torch_tensor_from_array(pos_tensor, pos)
433 CALL torch_tensor_from_array(edge_cell_shifts_tensor, edge_cell_shifts)
434 CALL torch_tensor_from_array(lattice_tensor, lattice)
435 END IF
436
437 CALL torch_dict_insert(inputs, "pos", pos_tensor)
438 CALL torch_dict_insert(inputs, "edge_cell_shift", edge_cell_shifts_tensor)
439 CALL torch_dict_insert(inputs, "cell", lattice_tensor)
440 CALL torch_tensor_release(pos_tensor)
441 CALL torch_tensor_release(edge_cell_shifts_tensor)
442 CALL torch_tensor_release(lattice_tensor)
443
444 CALL torch_tensor_from_array(t_edge_index_tensor, t_edge_index)
445 CALL torch_dict_insert(inputs, "edge_index", t_edge_index_tensor)
446 CALL torch_tensor_release(t_edge_index_tensor)
447
448 CALL torch_tensor_from_array(atom_types_tensor, atom_types)
449 CALL torch_dict_insert(inputs, "atom_types", atom_types_tensor)
450 CALL torch_tensor_release(atom_types_tensor)
451
452 CALL torch_dict_create(outputs)
453 CALL torch_model_forward(nequip_data%model, inputs, outputs)
454
455 CALL torch_dict_get(outputs, "total_energy", total_energy_tensor)
456 CALL torch_dict_get(outputs, "atomic_energy", atomic_energy_tensor)
457 CALL torch_dict_get(outputs, "forces", forces_tensor)
458 IF (nequip%do_nequip_sp) THEN
459 CALL torch_tensor_data_ptr(total_energy_tensor, total_energy_sp)
460 CALL torch_tensor_data_ptr(atomic_energy_tensor, atomic_energy_sp)
461 CALL torch_tensor_data_ptr(forces_tensor, forces_sp)
462 pot_nequip = real(total_energy_sp(1, 1), kind=dp)*nequip%unit_energy_val
463 nequip_data%force(:, :) = real(forces_sp(:, :), kind=dp)*nequip%unit_forces_val
464 DEALLOCATE (pos_sp, edge_cell_shifts_sp)
465 ELSE
466 CALL torch_tensor_data_ptr(total_energy_tensor, total_energy)
467 CALL torch_tensor_data_ptr(atomic_energy_tensor, atomic_energy)
468 CALL torch_tensor_data_ptr(forces_tensor, forces)
469 pot_nequip = total_energy(1, 1)*nequip%unit_energy_val
470 nequip_data%force(:, :) = forces(:, :)*nequip%unit_forces_val
471 DEALLOCATE (pos, edge_cell_shifts)
472 END IF
473 CALL torch_tensor_release(total_energy_tensor)
474 CALL torch_tensor_release(atomic_energy_tensor)
475 CALL torch_tensor_release(forces_tensor)
476
477 IF (use_virial) THEN
478 CALL torch_dict_get(outputs, "virial", virial_tensor)
479 CALL torch_tensor_data_ptr(virial_tensor, virial3d)
480 nequip_data%virial(:, :) = reshape(virial3d, (/3, 3/))*nequip%unit_energy_val
481 CALL torch_tensor_release(virial_tensor)
482 END IF
483
484 CALL torch_dict_release(inputs)
485 CALL torch_dict_release(outputs)
486
487 DEALLOCATE (t_edge_index, atom_types)
488
489 ! account for double counting from multiple MPI processes
490 pot_nequip = pot_nequip/real(para_env%num_pe, dp)
491 nequip_data%force = nequip_data%force/real(para_env%num_pe, dp)
492 IF (use_virial) nequip_data%virial(:, :) = nequip_data%virial/real(para_env%num_pe, dp)
493
494 CALL timestop(handle)
496
497! **************************************************************************************************
498!> \brief ...
499!> \param fist_nonbond_env ...
500!> \param f_nonbond ...
501!> \param pv_nonbond ...
502!> \param use_virial ...
503! **************************************************************************************************
504 SUBROUTINE nequip_add_force_virial(fist_nonbond_env, f_nonbond, pv_nonbond, use_virial)
505
506 TYPE(fist_nonbond_env_type), POINTER :: fist_nonbond_env
507 REAL(kind=dp), DIMENSION(:, :), INTENT(INOUT) :: f_nonbond, pv_nonbond
508 LOGICAL, INTENT(IN) :: use_virial
509
510 INTEGER :: iat, iat_use
511 TYPE(nequip_data_type), POINTER :: nequip_data
512
513 CALL fist_nonbond_env_get(fist_nonbond_env, nequip_data=nequip_data)
514
515 IF (use_virial) THEN
516 pv_nonbond = pv_nonbond + nequip_data%virial
517 END IF
518
519 DO iat_use = 1, SIZE(nequip_data%use_indices)
520 iat = nequip_data%use_indices(iat_use)
521 cpassert(iat >= 1 .AND. iat <= SIZE(f_nonbond, 2))
522 f_nonbond(1:3, iat) = f_nonbond(1:3, iat) + nequip_data%force(1:3, iat_use)
523 END DO
524
525 END SUBROUTINE nequip_add_force_virial
526END MODULE manybody_nequip
527
Define the atom type and its sub types.
Definition atom_types.F:15
Define the atomic kind types and their sub types.
Handles all functions related to the CELL.
Definition cell_types.F:15
Define the neighbor list data types and the corresponding functionality.
subroutine, public fist_nonbond_env_get(fist_nonbond_env, potparm14, potparm, nonbonded, rlist_cut, rlist_lowsq, aup, lup, ei_scale14, vdw_scale14, shift_cutoff, do_electrostatics, r_last_update, r_last_update_pbc, rshell_last_update_pbc, rcore_last_update_pbc, cell_last_update, num_update, last_update, counter, natom_types, long_range_correction, ij_kind_full_fac, eam_data, quip_data, nequip_data, allegro_data, deepmd_data, charges)
sets a fist_nonbond_env
subroutine, public fist_nonbond_env_set(fist_nonbond_env, potparm14, potparm, rlist_cut, rlist_lowsq, nonbonded, aup, lup, ei_scale14, vdw_scale14, shift_cutoff, do_electrostatics, r_last_update, r_last_update_pbc, rshell_last_update_pbc, rcore_last_update_pbc, cell_last_update, num_update, last_update, counter, natom_types, long_range_correction, eam_data, quip_data, nequip_data, allegro_data, deepmd_data, charges)
sets a fist_nonbond_env
Defines the basic variable types.
Definition kinds.F:23
integer, parameter, public int_8
Definition kinds.F:54
integer, parameter, public dp
Definition kinds.F:34
integer, parameter, public sp
Definition kinds.F:33
An array-based list which grows on demand. When the internal array is full, a new array of twice the ...
Definition list.F:24
subroutine, public nequip_add_force_virial(fist_nonbond_env, f_nonbond, pv_nonbond, use_virial)
...
subroutine, public destroy_nequip_arrays(glob_loc_list, glob_cell_v, glob_loc_list_a)
...
subroutine, public nequip_energy_store_force_virial(nonbonded, particle_set, cell, atomic_kind_set, potparm, nequip, glob_loc_list_a, r_last_update_pbc, pot_nequip, fist_nonbond_env, para_env, use_virial)
...
subroutine, public setup_nequip_arrays(nonbonded, potparm, glob_loc_list, glob_cell_v, glob_loc_list_a, cell)
...
Interface to the message passing library MPI.
integer, parameter, public nequip_type
Define the data structure for the particle information.
subroutine, public torch_dict_release(dict)
Releases a Torch dictionary and all its ressources.
Definition torch_api.F:1113
subroutine, public torch_dict_get(dict, key, tensor)
Retrieves a Torch tensor from a Torch dictionary.
Definition torch_api.F:1079
subroutine, public torch_model_load(model, filename)
Loads a Torch model from given "*.pth" file. (In Torch lingo models are called modules)
Definition torch_api.F:1137
subroutine, public torch_dict_create(dict)
Creates an empty Torch dictionary.
Definition torch_api.F:1023
subroutine, public torch_model_freeze(model)
Freeze the given Torch model: applies generic optimization that speed up model. See https://pytorch....
Definition torch_api.F:1333
subroutine, public torch_dict_insert(dict, key, tensor)
Inserts a Torch tensor into a Torch dictionary.
Definition torch_api.F:1047
subroutine, public torch_tensor_release(tensor)
Releases a Torch tensor and all its ressources.
Definition torch_api.F:999
subroutine, public torch_model_forward(model, inputs, outputs)
Evaluates the given Torch model.
Definition torch_api.F:1169
All kind of helpful little routines.
Definition util.F:14
Provides all information about an atomic kind.
Type defining parameters related to the simulation cell.
Definition cell_types.F:55
stores all the informations relevant to an mpi environment