43#include "./base/base_uses.f90"
47 CHARACTER(len=*),
PARAMETER,
PRIVATE :: moduleN =
'topology_util'
50 INTEGER,
POINTER,
DIMENSION(:) :: array1 => null()
54 INTEGER,
POINTER,
DIMENSION(:) :: array1 => null()
55 INTEGER,
POINTER,
DIMENSION(:) :: array2 => null()
72 MODULE PROCEDURE reorder_structure1d, reorder_structure2d
89 LOGICAL,
INTENT(in),
OPTIONAL :: qmmm
93 CHARACTER(len=*),
PARAMETER :: routinen =
'topology_reorder_atoms'
95 CHARACTER(LEN=default_string_length) :: mol_id
96 CHARACTER(LEN=default_string_length),
POINTER :: molname(:), telement(:), &
97 tlabel_atmname(:), tlabel_molname(:), &
99 INTEGER :: handle, i, iatm, iindex, ikind, imol, imol_ref, iref, iund, iw, j, k, location, &
100 max_mol_num, mm_index, n, n_rep, n_var, natom, natom_loc, nkind, nlinks, old_hash, &
101 old_mol, output_unit, qm_index, unique_mol
102 INTEGER,
DIMENSION(:),
POINTER :: mm_link_atoms, qm_atom_index
103 INTEGER,
POINTER :: atm_map1(:), atm_map2(:), atm_map3(:), map_atom_type(:), &
104 map_mol_hash(:), mm_indexes_n(:), mm_indexes_v(:), mol_bnd(:, :), mol_hash(:), &
105 mol_num(:), new_position(:), order(:), tmp_n(:), tmp_v(:), wrk(:)
106 LOGICAL :: explicit, matches, my_qmmm
107 REAL(kind=
dp),
DIMENSION(:, :),
POINTER :: tr
108 REAL(kind=
dp),
POINTER :: tatm_charge(:), tatm_mass(:)
113 TYPE(
graph_type),
DIMENSION(:),
POINTER :: reference_set
115 qm_kinds, qmmm_link_section, &
117 TYPE(
vertex),
DIMENSION(:),
POINTER :: reference, unordered
119 NULLIFY (logger, generate_section, isolated_section, tmp_v, tmp_n)
122 extension=
".subsysLog")
123 CALL timeset(routinen, handle)
125 IF (output_unit > 0)
WRITE (output_unit,
'(T2,"REORDER | ")')
128 IF (
PRESENT(qmmm) .AND.
PRESENT(qmmm_env_mm)) my_qmmm = qmmm
134 NULLIFY (new_position, reference_set)
135 NULLIFY (tlabel_atmname, telement, mol_num, tlabel_molname, tlabel_resname)
136 NULLIFY (tr, tatm_charge, tatm_mass, atm_map1, atm_map2, atm_map3)
139 cpassert(.NOT.
ASSOCIATED(atom_info%map_mol_num))
140 cpassert(.NOT.
ASSOCIATED(atom_info%map_mol_typ))
141 cpassert(.NOT.
ASSOCIATED(atom_info%map_mol_res))
143 ALLOCATE (new_position(natom))
144 ALLOCATE (mol_num(natom))
145 ALLOCATE (molname(natom))
146 ALLOCATE (tlabel_atmname(natom))
147 ALLOCATE (tlabel_molname(natom))
148 ALLOCATE (tlabel_resname(natom))
149 ALLOCATE (tr(3, natom))
150 ALLOCATE (tatm_charge(natom))
151 ALLOCATE (tatm_mass(natom))
152 ALLOCATE (telement(natom))
153 ALLOCATE (atm_map1(natom))
154 ALLOCATE (atm_map2(natom))
158 ALLOCATE (map_atom_type(natom))
160 ALLOCATE (atom_bond_list(natom))
162 map_atom_type(i) = atom_info%id_atmname(i)
163 ALLOCATE (atom_bond_list(i)%array1(0))
166 IF (
ASSOCIATED(conn_info%bond_a)) n =
SIZE(conn_info%bond_a)
168 ALLOCATE (atom_info%map_mol_num(natom))
169 atom_info%map_mol_num = -1
170 CALL find_molecule(atom_bond_list, atom_info%map_mol_num, atom_info%id_molname)
171 max_mol_num = maxval(atom_info%map_mol_num)
173 ALLOCATE (mol_bnd(2, max_mol_num))
174 ALLOCATE (mol_hash(max_mol_num))
175 ALLOCATE (map_mol_hash(max_mol_num))
178 CALL sort(atom_info%map_mol_num, natom, atm_map1)
183 IF (old_mol .NE. atom_info%map_mol_num(i))
THEN
184 old_mol = atom_info%map_mol_num(i)
187 mol_bnd(2, imol) = i - 1
193 atm_map2(atm_map1(i)) = iindex
195 mol_bnd(2, imol) = natom
198 iund = max_mol_num/2 + 1
200 NULLIFY (reference, unordered)
202 DO j = 1, max_mol_num
203 CALL setup_graph(j, reference, map_atom_type, &
204 atom_bond_list, mol_bnd, atm_map1, atm_map2)
206 ALLOCATE (order(
SIZE(reference)))
210 DO i = 1,
SIZE(reference)
211 DEALLOCATE (reference(i)%bonds)
213 DEALLOCATE (reference)
216 CALL sort(mol_hash, max_mol_num, map_mol_hash)
221 IF (output_unit > 0)
THEN
222 WRITE (output_unit,
'(T2,"REORDER | ",A)') &
223 "Reordering Molecules. The Reordering of molecules will override all", &
224 "information regarding molecule names and residue names.", &
225 "New ones will be provided on the basis of the connectivity!"
227 DO j = 1, max_mol_num
228 IF (mol_hash(j) .NE. old_hash)
THEN
229 unique_mol = unique_mol + 1
230 old_hash = mol_hash(j)
231 CALL setup_graph_set(reference_set, unique_mol, map_mol_hash(j), &
232 map_atom_type, atom_bond_list, mol_bnd, atm_map1, atm_map2, &
236 DO i = 1,
SIZE(atm_map3)
237 natom_loc = natom_loc + 1
238 new_position(natom_loc) = atm_map3(i)
239 molname(natom_loc) = mol_id
240 mol_num(natom_loc) = unique_mol
242 DEALLOCATE (atm_map3)
244 CALL setup_graph(map_mol_hash(j), unordered, map_atom_type, &
245 atom_bond_list, mol_bnd, atm_map1, atm_map2, atm_map3)
246 DO imol_ref = 1, unique_mol
248 reference => reference_set(imol_ref)%graph
249 ALLOCATE (order(
SIZE(reference)))
256 ALLOCATE (wrk(
SIZE(order)))
257 CALL sort(order,
SIZE(order), wrk)
258 DO i = 1,
SIZE(order)
259 natom_loc = natom_loc + 1
260 new_position(natom_loc) = atm_map3(wrk(i))
261 molname(natom_loc) = mol_id
262 mol_num(natom_loc) = unique_mol
268 unique_mol = unique_mol + 1
269 CALL setup_graph_set(reference_set, unique_mol, map_mol_hash(j), &
270 map_atom_type, atom_bond_list, mol_bnd, atm_map1, atm_map2, &
274 DO i = 1,
SIZE(atm_map3)
275 natom_loc = natom_loc + 1
276 new_position(natom_loc) = atm_map3(i)
277 molname(natom_loc) = mol_id
278 mol_num(natom_loc) = unique_mol
280 DEALLOCATE (atm_map3)
282 DO i = 1,
SIZE(unordered)
283 DEALLOCATE (unordered(i)%bonds)
285 DEALLOCATE (unordered)
286 DEALLOCATE (atm_map3)
289 IF (output_unit > 0)
THEN
290 WRITE (output_unit,
'(T2,"REORDER | ",A,I7,A)')
"Number of unique molecules found:", unique_mol,
"."
292 cpassert(natom_loc == natom)
293 DEALLOCATE (map_atom_type)
294 DEALLOCATE (atm_map1)
295 DEALLOCATE (atm_map2)
297 DEALLOCATE (mol_hash)
298 DEALLOCATE (map_mol_hash)
301 DEALLOCATE (atom_bond_list(i)%array1)
303 DEALLOCATE (atom_bond_list)
304 DEALLOCATE (atom_info%map_mol_num)
306 DO i = 1,
SIZE(reference_set)
307 DO j = 1,
SIZE(reference_set(i)%graph)
308 DEALLOCATE (reference_set(i)%graph(j)%bonds)
310 DEALLOCATE (reference_set(i)%graph)
312 DEALLOCATE (reference_set)
315 location = new_position(iatm)
316 tlabel_molname(iatm) =
id2str(atom_info%id_molname(location))
317 tlabel_resname(iatm) =
id2str(atom_info%id_resname(location))
318 tlabel_atmname(iatm) =
id2str(atom_info%id_atmname(location))
319 telement(iatm) =
id2str(atom_info%id_element(location))
320 tr(1, iatm) = atom_info%r(1, location)
321 tr(2, iatm) = atom_info%r(2, location)
322 tr(3, iatm) = atom_info%r(3, location)
323 tatm_charge(iatm) = atom_info%atm_charge(location)
324 tatm_mass(iatm) = atom_info%atm_mass(location)
328 tlabel_molname(iatm) =
"MOL"//trim(molname(iatm))
329 tlabel_resname(iatm) =
"R"//trim(molname(iatm))
334 atom_info%id_molname(iatm) =
str2id(tlabel_molname(iatm))
335 atom_info%id_resname(iatm) =
str2id(tlabel_resname(iatm))
336 atom_info%id_atmname(iatm) =
str2id(tlabel_atmname(iatm))
337 atom_info%id_element(iatm) =
str2id(telement(iatm))
338 atom_info%resid(iatm) = mol_num(iatm)
339 atom_info%r(1, iatm) = tr(1, iatm)
340 atom_info%r(2, iatm) = tr(2, iatm)
341 atom_info%r(3, iatm) = tr(3, iatm)
342 atom_info%atm_charge(iatm) = tatm_charge(iatm)
343 atom_info%atm_mass(iatm) = tatm_mass(iatm)
347 ALLOCATE (wrk(
SIZE(new_position)))
348 CALL sort(new_position,
SIZE(new_position), wrk)
355 cpassert(
SIZE(qmmm_env_mm%qm_atom_index) /= 0)
356 cpassert(all(qmmm_env_mm%qm_atom_index /= 0))
357 ALLOCATE (qm_atom_index(
SIZE(qmmm_env_mm%qm_atom_index)))
358 DO iatm = 1,
SIZE(qmmm_env_mm%qm_atom_index)
359 qm_atom_index(iatm) = wrk(qmmm_env_mm%qm_atom_index(iatm))
361 qmmm_env_mm%qm_atom_index = qm_atom_index
362 cpassert(all(qmmm_env_mm%qm_atom_index /= 0))
363 DEALLOCATE (qm_atom_index)
373 ALLOCATE (mm_indexes_n(
SIZE(mm_indexes_v)))
374 DO j = 1,
SIZE(mm_indexes_v)
375 mm_indexes_n(j) = wrk(mm_indexes_v(j))
378 i_vals_ptr=mm_indexes_n, i_rep_val=k)
382 IF (qmmm_env_mm%qmmm_link)
THEN
384 cpassert(
SIZE(qmmm_env_mm%mm_link_atoms) > 0)
385 ALLOCATE (mm_link_atoms(
SIZE(qmmm_env_mm%mm_link_atoms)))
386 DO iatm = 1,
SIZE(qmmm_env_mm%mm_link_atoms)
387 mm_link_atoms(iatm) = wrk(qmmm_env_mm%mm_link_atoms(iatm))
389 qmmm_env_mm%mm_link_atoms = mm_link_atoms
390 cpassert(all(qmmm_env_mm%mm_link_atoms /= 0))
391 DEALLOCATE (mm_link_atoms)
395 cpassert(nlinks /= 0)
399 mm_index = wrk(mm_index)
400 qm_index = wrk(qm_index)
416 ALLOCATE (tmp_n(
SIZE(tmp_v)))
417 DO j = 1,
SIZE(tmp_v)
418 tmp_n(j) = wrk(tmp_v(j))
425 DEALLOCATE (new_position)
426 DEALLOCATE (tlabel_atmname)
427 DEALLOCATE (tlabel_molname)
428 DEALLOCATE (tlabel_resname)
429 DEALLOCATE (telement)
431 DEALLOCATE (tatm_charge)
432 DEALLOCATE (tatm_mass)
437 DEALLOCATE (conn_info%bond_a)
438 DEALLOCATE (conn_info%bond_b)
439 IF (output_unit > 0)
WRITE (output_unit,
'(T2,"REORDER | ")')
440 CALL timestop(handle)
442 "PRINT%TOPOLOGY_INFO/UTIL_INFO")
458 SUBROUTINE setup_graph_set(graph_set, idim, ind, array2, atom_bond_list, map_mol, &
459 atm_map1, atm_map2, atm_map3)
460 TYPE(
graph_type),
DIMENSION(:),
POINTER :: graph_set
461 INTEGER,
INTENT(IN) :: idim, ind
462 INTEGER,
DIMENSION(:),
POINTER :: array2
464 INTEGER,
DIMENSION(:, :),
POINTER :: map_mol
465 INTEGER,
DIMENSION(:),
POINTER :: atm_map1, atm_map2, atm_map3
468 TYPE(
graph_type),
DIMENSION(:),
POINTER :: tmp_graph_set
471 NULLIFY (tmp_graph_set)
472 IF (
ASSOCIATED(graph_set))
THEN
473 ldim =
SIZE(graph_set)
474 cpassert(ldim + 1 == idim)
476 NULLIFY (tmp_graph_set)
477 CALL allocate_graph_set(graph_set, tmp_graph_set)
479 CALL allocate_graph_set(tmp_graph_set, graph_set, ldim, ldim + 1)
480 CALL setup_graph(ind, graph_set(ldim + 1)%graph, array2, &
481 atom_bond_list, map_mol, atm_map1, atm_map2, atm_map3)
483 END SUBROUTINE setup_graph_set
493 SUBROUTINE allocate_graph_set(graph_set_in, graph_set_out, ldim_in, ldim_out)
494 TYPE(
graph_type),
DIMENSION(:),
POINTER :: graph_set_in, graph_set_out
495 INTEGER,
INTENT(IN),
OPTIONAL :: ldim_in, ldim_out
497 INTEGER :: b_dim, i, j, mydim_in, mydim_out, v_dim
499 cpassert(.NOT.
ASSOCIATED(graph_set_out))
502 IF (
ASSOCIATED(graph_set_in))
THEN
503 mydim_in =
SIZE(graph_set_in)
504 mydim_out =
SIZE(graph_set_in)
506 IF (
PRESENT(ldim_in)) mydim_in = ldim_in
507 IF (
PRESENT(ldim_out)) mydim_out = ldim_out
508 ALLOCATE (graph_set_out(mydim_out))
510 NULLIFY (graph_set_out(i)%graph)
514 v_dim =
SIZE(graph_set_in(i)%graph)
515 ALLOCATE (graph_set_out(i)%graph(v_dim))
517 graph_set_out(i)%graph(j)%kind = graph_set_in(i)%graph(j)%kind
518 b_dim =
SIZE(graph_set_in(i)%graph(j)%bonds)
519 ALLOCATE (graph_set_out(i)%graph(j)%bonds(b_dim))
520 graph_set_out(i)%graph(j)%bonds = graph_set_in(i)%graph(j)%bonds
521 DEALLOCATE (graph_set_in(i)%graph(j)%bonds)
523 DEALLOCATE (graph_set_in(i)%graph)
525 IF (
ASSOCIATED(graph_set_in))
THEN
526 DEALLOCATE (graph_set_in)
529 END SUBROUTINE allocate_graph_set
543 SUBROUTINE setup_graph(ind, graph, array2, atom_bond_list, map_mol, &
544 atm_map1, atm_map2, atm_map3)
545 INTEGER,
INTENT(IN) :: ind
547 INTEGER,
DIMENSION(:),
POINTER :: array2
549 INTEGER,
DIMENSION(:, :),
POINTER :: map_mol
550 INTEGER,
DIMENSION(:),
POINTER :: atm_map1, atm_map2
551 INTEGER,
DIMENSION(:),
OPTIONAL,
POINTER :: atm_map3
553 INTEGER :: i, idim, ifirst, ilast, j, nbonds, &
556 IF (
PRESENT(atm_map3))
THEN
557 cpassert(.NOT.
ASSOCIATED(atm_map3))
559 cpassert(.NOT.
ASSOCIATED(
graph))
562 ifirst = map_mol(1, ind)
563 ilast = map_mol(2, ind)
564 nelement = ilast - ifirst + 1
565 ALLOCATE (
graph(nelement))
566 IF (
PRESENT(atm_map3))
THEN
567 ALLOCATE (atm_map3(nelement))
571 graph(idim)%kind = array2(atm_map1(i))
572 nbonds =
SIZE(atom_bond_list(atm_map1(i))%array1)
573 ALLOCATE (
graph(idim)%bonds(nbonds))
575 graph(idim)%bonds(j) = atm_map2(atom_bond_list(atm_map1(i))%array1(j))
577 IF (
PRESENT(atm_map3))
THEN
578 atm_map3(idim) = atm_map1(i)
582 END SUBROUTINE setup_graph
595 INTEGER,
DIMENSION(:),
POINTER :: ilist1
596 INTEGER,
DIMENSION(:),
OPTIONAL,
POINTER :: ilist2, ilist3, ilist4
597 INTEGER,
INTENT(IN) :: nsize, ndim
599 INTEGER :: i, iend, istart, ldim
600 INTEGER,
DIMENSION(:),
POINTER :: tmp, wrk
604 CALL sort(ilist1, ndim, wrk)
609 ilist2(i) = tmp(wrk(i))
615 ilist3(i) = tmp(wrk(i))
620 ilist3(i) = tmp(wrk(i))
624 ilist4(i) = tmp(wrk(i))
630 IF (ilist1(i) /= ilist1(istart))
THEN
632 ldim = iend - istart + 1
633 CALL reorder_list_array_low(ilist2, ilist3, ilist4, nsize, &
640 ldim = iend - istart + 1
641 CALL reorder_list_array_low(ilist2, ilist3, ilist4, nsize, &
658 RECURSIVE SUBROUTINE reorder_list_array_low(Ilist2, Ilist3, Ilist4, nsize, &
660 INTEGER,
DIMENSION(:),
OPTIONAL,
POINTER :: ilist2, ilist3, ilist4
661 INTEGER,
INTENT(IN) :: nsize, ldim, istart, iend
663 INTEGER,
DIMENSION(:),
POINTER :: tmp_2, tmp_3, tmp_4
667 ALLOCATE (tmp_2(ldim))
668 tmp_2(:) = ilist2(istart:iend)
670 ilist2(istart:iend) = tmp_2(:)
673 ALLOCATE (tmp_2(ldim))
674 ALLOCATE (tmp_3(ldim))
675 tmp_2(:) = ilist2(istart:iend)
676 tmp_3(:) = ilist3(istart:iend)
678 ilist2(istart:iend) = tmp_2(:)
679 ilist3(istart:iend) = tmp_3(:)
683 ALLOCATE (tmp_2(ldim))
684 ALLOCATE (tmp_3(ldim))
685 ALLOCATE (tmp_4(ldim))
686 tmp_2(:) = ilist2(istart:iend)
687 tmp_3(:) = ilist3(istart:iend)
688 tmp_4(:) = ilist4(istart:iend)
690 ilist2(istart:iend) = tmp_2(:)
691 ilist3(istart:iend) = tmp_3(:)
692 ilist4(istart:iend) = tmp_4(:)
698 END SUBROUTINE reorder_list_array_low
711 LOGICAL,
DIMENSION(:),
POINTER :: icheck
713 INTEGER,
INTENT(IN) :: i
714 INTEGER,
INTENT(INOUT) :: mol_natom
715 INTEGER,
DIMENSION(:),
POINTER :: mol_map
716 INTEGER,
INTENT(IN) :: my_mol
720 IF (mol_map(i) == my_mol)
THEN
722 DO j = 1,
SIZE(bond_list(i)%array1)
723 k = bond_list(i)%array1(j)
725 mol_natom = mol_natom + 1
744 INTEGER,
DIMENSION(:),
POINTER :: icheck
746 INTEGER,
INTENT(IN) :: i, my_mol
751 DO j = 1,
SIZE(bond_list(i)%array1)
752 k = bond_list(i)%array1(j)
768 SUBROUTINE reorder_structure1d(work, list1, list2, N)
770 INTENT(INOUT) :: work
771 INTEGER,
DIMENSION(:),
INTENT(IN) :: list1, list2
772 INTEGER,
INTENT(IN) :: N
774 INTEGER :: I, index1, index2, Nsize
775 INTEGER,
DIMENSION(:),
POINTER :: wrk_tmp
781 wrk_tmp => work(index1)%array1
782 nsize =
SIZE(wrk_tmp)
783 ALLOCATE (work(index1)%array1(nsize + 1))
784 work(index1)%array1(1:nsize) = wrk_tmp
785 work(index1)%array1(nsize + 1) = index2
788 wrk_tmp => work(index2)%array1
789 nsize =
SIZE(wrk_tmp)
790 ALLOCATE (work(index2)%array1(nsize + 1))
791 work(index2)%array1(1:nsize) = wrk_tmp
792 work(index2)%array1(nsize + 1) = index1
796 END SUBROUTINE reorder_structure1d
808 SUBROUTINE reorder_structure2d(work, list1, list2, list3, N)
810 INTENT(INOUT) :: work
811 INTEGER,
DIMENSION(:),
INTENT(IN) :: list1, list2, list3
812 INTEGER,
INTENT(IN) :: N
814 INTEGER :: I, index1, index2, index3, Nsize
815 INTEGER,
DIMENSION(:),
POINTER :: wrk_tmp
822 wrk_tmp => work(index1)%array1
823 nsize =
SIZE(wrk_tmp)
824 ALLOCATE (work(index1)%array1(nsize + 1))
825 work(index1)%array1(1:nsize) = wrk_tmp
826 work(index1)%array1(nsize + 1) = index2
829 wrk_tmp => work(index2)%array1
830 nsize =
SIZE(wrk_tmp)
831 ALLOCATE (work(index2)%array1(nsize + 1))
832 work(index2)%array1(1:nsize) = wrk_tmp
833 work(index2)%array1(nsize + 1) = index1
836 wrk_tmp => work(index1)%array2
837 nsize =
SIZE(wrk_tmp)
838 ALLOCATE (work(index1)%array2(nsize + 1))
839 work(index1)%array2(1:nsize) = wrk_tmp
840 work(index1)%array2(nsize + 1) = index3
843 wrk_tmp => work(index2)%array2
844 nsize =
SIZE(wrk_tmp)
845 ALLOCATE (work(index2)%array2(nsize + 1))
846 work(index2)%array2(1:nsize) = wrk_tmp
847 work(index2)%array2(nsize + 1) = -index3
851 END SUBROUTINE reorder_structure2d
864 INTEGER,
DIMENSION(:),
POINTER :: mol_info, mol_name
866 INTEGER :: i, my_mol_name, n, nmol
868 n =
SIZE(atom_bond_list)
871 IF (mol_info(i) == -1)
THEN
873 my_mol_name = mol_name(i)
874 CALL spread_mol(atom_bond_list, mol_info, i, nmol, my_mol_name, &
890 RECURSIVE SUBROUTINE spread_mol(atom_bond_list, mol_info, iatom, imol, &
891 my_mol_name, mol_name)
893 INTEGER,
DIMENSION(:),
POINTER :: mol_info
894 INTEGER,
INTENT(IN) :: iatom, imol, my_mol_name
895 INTEGER,
DIMENSION(:),
POINTER :: mol_name
899 mol_info(iatom) = imol
900 DO i = 1,
SIZE(atom_bond_list(iatom)%array1)
901 atom_b = atom_bond_list(iatom)%array1(i)
905 IF (mol_info(atom_b) == -1 .AND. my_mol_name == mol_name(atom_b))
THEN
906 CALL spread_mol(atom_bond_list, mol_info, atom_b, imol, my_mol_name, mol_name)
907 IF (mol_info(atom_b) /= imol) cpabort(
"internal error")
910 END SUBROUTINE spread_mol
921 CHARACTER(len=*),
PARAMETER :: routinen =
'topology_set_atm_mass'
923 CHARACTER(LEN=2) :: upper_sym_1
924 CHARACTER(LEN=default_string_length) :: atmname_upper
925 CHARACTER(LEN=default_string_length), &
926 DIMENSION(:),
POINTER :: keyword
927 INTEGER :: handle, i, i_rep, iatom, ielem_found, &
929 LOGICAL :: user_defined
930 REAL(kind=
dp),
DIMENSION(:),
POINTER :: mass
938 extension=
".subsysLog")
939 CALL timeset(routinen, handle)
947 ALLOCATE (keyword(n_rep))
948 ALLOCATE (mass(n_rep))
952 c_val=keyword(i_rep), i_rep_section=i_rep)
955 keyword_name=
"MASS", n_rep_val=i)
957 keyword_name=
"MASS", r_val=mass(i_rep))
963 user_defined = .false.
964 DO i = 1,
SIZE(keyword)
965 atmname_upper =
id2str(atom_info%id_atmname(iatom))
967 IF (trim(atmname_upper) == trim(keyword(i)) .AND. mass(i) /= huge(0.0_dp))
THEN
968 atom_info%atm_mass(iatom) = mass(i)
969 user_defined = .true.
974 IF (.NOT. user_defined)
THEN
975 upper_sym_1 = trim(
id2str(atom_info%id_element(iatom)))
976 CALL get_ptable_info(symbol=upper_sym_1, ielement=ielem_found, amass=atom_info%atm_mass(iatom))
978 IF (iw > 0)
WRITE (iw,
'(7X,A,A5,A,F12.5)')
"In topology_set_atm_mass :: element = ", &
979 id2str(atom_info%id_element(iatom)),
" a_mass ", atom_info%atm_mass(iatom)
984 CALL timestop(handle)
986 "PRINT%TOPOLOGY_INFO/UTIL_INFO")
999 CHARACTER(len=*),
PARAMETER :: routinen =
'topology_molecules_check'
1001 INTEGER :: counter, first, first_loc, handle, i, &
1002 iatom, iw, k, loc_counter, mol_num, &
1004 LOGICAL :: icheck_num, icheck_typ
1010 CALL timeset(routinen, handle)
1015 extension=
".subsysLog")
1022 WRITE (unit=iw, fmt=
"(/,T2,A)") &
1023 "FORCEFIELD| Checking consistency of the generated molecules"
1026 ALLOCATE (atom_bond_list(natom))
1029 ALLOCATE (atom_bond_list(i)%array1(0))
1032 IF (
ASSOCIATED(conn_info%bond_a)) n =
SIZE(conn_info%bond_a)
1035 mol_typ = atom_info%map_mol_typ(1)
1036 mol_num = atom_info%map_mol_num(1)
1042 icheck_num = (atom_info%map_mol_num(iatom) == mol_num)
1043 icheck_typ = (atom_info%map_mol_typ(iatom) == mol_typ)
1044 IF ((icheck_typ .AND. (.NOT. icheck_num)) .OR. (.NOT. icheck_typ))
THEN
1048 IF (counter /= loc_counter)
THEN
1049 CALL cp_abort(__location__, &
1050 "Different number of atoms for the same molecule kind found "// &
1051 "(molecule type = "//trim(adjustl(
cp_to_string(mol_typ)))// &
1052 ", molecule number = "//trim(adjustl(
cp_to_string(mol_num)))// &
1053 ", expected number of atoms = "// &
1055 ", number of atoms found = "// &
1059 IF (.NOT. icheck_typ)
THEN
1064 mol_typ = atom_info%map_mol_typ(iatom)
1066 IF (icheck_num)
THEN
1067 IF (icheck_typ) loc_counter = loc_counter + 1
1071 IF (atom_info%id_atmname(iatom) /= &
1072 atom_info%id_atmname(first + loc_counter - 1))
THEN
1073 CALL cp_abort(__location__, &
1074 "Different atom names for the same molecule kind found "// &
1075 "(atom number = "//trim(adjustl(
cp_to_string(iatom)))// &
1076 ", molecule type = "//trim(adjustl(
cp_to_string(mol_typ)))// &
1077 ", molecule number = "//trim(adjustl(
cp_to_string(mol_num)))// &
1078 ", expected atom name = "// &
1079 trim(adjustl(
id2str(atom_info%id_atmname(first + loc_counter - 1))))// &
1080 ", atom name found = "// &
1081 trim(adjustl(
id2str(atom_info%id_atmname(iatom))))//
").")
1086 IF (
SIZE(atom_bond_list(iatom)%array1) /=
SIZE(atom_bond_list(first + loc_counter - 1)%array1))
THEN
1087 CALL cp_abort(__location__, &
1088 "Different number of bonds for the same molecule kind found "// &
1089 "(molecule type = "//trim(adjustl(
cp_to_string(mol_typ)))// &
1090 ", molecule number = "//trim(adjustl(
cp_to_string(mol_num)))// &
1091 ", expected number of bonds = "// &
1092 trim(adjustl(
cp_to_string(
SIZE(atom_bond_list(first + loc_counter - 1)%array1))))// &
1093 ", number of bonds found = "// &
1094 trim(adjustl(
cp_to_string(
SIZE(atom_bond_list(iatom)%array1))))// &
1095 "). Check the connectivity of your system.")
1097 DO k = 1,
SIZE(atom_bond_list(iatom)%array1)
1098 IF (all(atom_bond_list(first + loc_counter - 1)%array1 - first /= &
1099 atom_bond_list(iatom)%array1(k) - first_loc))
THEN
1100 CALL cp_abort(__location__, &
1101 "Different sequence of bonds for the same molecule kind found "// &
1102 "(molecule type = "//trim(adjustl(
cp_to_string(mol_typ)))// &
1103 ", molecule number = "//trim(adjustl(
cp_to_string(mol_num)))// &
1104 "). Check the connectivity of your system.")
1108 mol_num = atom_info%map_mol_num(iatom)
1112 IF (mol_num == 1 .AND. icheck_typ) counter = counter + 1
1116 WRITE (unit=iw, fmt=
"(T2,A)") &
1117 "FORCEFIELD| Consistency check for molecules completed"
1121 DEALLOCATE (atom_bond_list(i)%array1)
1123 DEALLOCATE (atom_bond_list)
1126 "PRINT%TOPOLOGY_INFO/UTIL_INFO")
1128 CALL timestop(handle)
1144 CHARACTER(len=*),
INTENT(IN) :: element_in, atom_name_in
1145 CHARACTER(len=default_string_length),
INTENT(OUT) :: element_out
1147 LOGICAL :: use_mm_map_first
1149 CHARACTER(len=default_string_length) :: atom_name, element_symbol, keyword
1150 INTEGER :: i, i_rep, n_rep
1151 LOGICAL :: defined_kind_section, found, in_ptable
1155 element_symbol = element_in
1156 atom_name = atom_name_in
1158 defined_kind_section = .false.
1167 c_val=keyword, i_rep_section=i_rep)
1169 IF (trim(keyword) == trim(atom_name))
THEN
1171 keyword_name=
"ELEMENT", n_rep_val=i)
1174 keyword_name=
"ELEMENT", c_val=element_symbol)
1175 defined_kind_section = .true.
1178 element_symbol = element_in
1179 defined_kind_section = .true.
1188 IF (defined_kind_section .OR. .NOT. use_mm_map_first)
THEN
1191 IF (len_trim(element_symbol) <= 2)
CALL get_ptable_info(element_symbol, found=in_ptable)
1193 element_out = trim(element_symbol)
1199 IF (.NOT. found .AND. defined_kind_section) &
1200 CALL cp_abort(__location__,
"Element <"//trim(element_symbol)// &
1201 "> provided for KIND <"//trim(atom_name_in)//
"> "// &
1202 "which cannot be mapped with any standard element label. Please correct your "// &
1207 IF ((.NOT. found) .AND. (
ASSOCIATED(
amber_map)))
THEN
1210 IF (element_symbol ==
amber_map%kind(i))
THEN
1219 IF ((.NOT. found) .AND. (
ASSOCIATED(
charmm_map)))
THEN
1222 IF (element_symbol ==
charmm_map%kind(i))
THEN
1231 IF ((.NOT. found) .AND. (
ASSOCIATED(
gromos_map)))
THEN
1234 IF (element_symbol ==
gromos_map%kind(i))
THEN
1246 IF (.NOT. found)
THEN
1248 IF (len_trim(element_symbol) <= 2)
CALL get_ptable_info(element_symbol, found=in_ptable)
1250 element_out = trim(element_symbol)
1256 IF (.NOT. found)
THEN
1257 CALL cp_abort(__location__, &
1258 " Unknown element for KIND <"//trim(atom_name_in)//
">."// &
1259 " This problem can be fixed specifying properly elements in PDB"// &
1260 " or specifying a KIND section or getting in touch with one of"// &
program graph
Program to Map on grid the hills spawned during a metadynamics run.
various routines to log and control the output. The idea is that decisions about where to log should ...
integer function, public cp_logger_get_default_io_unit(logger)
returns the unit nr for the ionode (-1 on all other processors) skips as well checks if the procs cal...
type(cp_logger_type) function, pointer, public cp_get_default_logger()
returns the default logger
routines to handle the output, The idea is to remove the decision of wheter to output and what to out...
integer function, public cp_print_key_unit_nr(logger, basis_section, print_key_path, extension, middle_name, local, log_filename, ignore_should_output, file_form, file_position, file_action, file_status, do_backup, on_file, is_new_file, mpi_io, fout)
...
subroutine, public cp_print_key_finished_output(unit_nr, logger, basis_section, print_key_path, local, ignore_should_output, on_file, mpi_io)
should be called after you finish working with a unit obtained with cp_print_key_unit_nr,...
uses a combination of graphs and hashing to determine if two molecules are topologically equivalent,...
subroutine, public hash_molecule(reference, kind_ref, hash)
hashes a molecule to a number. Molecules that are the (topologically) the same have the same hash....
subroutine, public reorder_graph(reference, unordered, order, matches)
If two molecules are topologically the same, finds the ordering that maps the unordered one on the or...
Defines the basic variable types.
integer, parameter, public dp
integer, parameter, public default_string_length
Contains the mapping ATOM_KIND -> ELEMENT for the most common cases in CHARMM and AMBER This should a...
type(ff_map_type), pointer, public charmm_map
type(ff_map_type), pointer, public gromos_map
type(ff_map_type), pointer, public amber_map
Periodic Table related data definitions.
subroutine, public get_ptable_info(symbol, number, amass, ielement, covalent_radius, metallic_radius, vdw_radius, found)
Pass information about the kind given the element symbol.
generates a unique id number for a string (str2id) that can be used two compare two strings....
integer function, public str2id(str)
returns a unique id for a given string, and stores the string for later retrieval using the id.
character(len=default_string_length) function, public id2str(id)
returns the string associated with a given id
Utilities for string manipulations.
elemental subroutine, public uppercase(string)
Convert all lower case characters in a string to upper case.
Collection of subroutine needed for topology related things.
subroutine, public topology_molecules_check(topology, subsys_section)
Check and verify that all molecules of the same kind are bonded the same.
subroutine, public find_molecule(atom_bond_list, mol_info, mol_name)
each atom will be assigned a molecule number based on bonded fragments The array mol_info should be i...
recursive subroutine, public give_back_molecule(icheck, bond_list, i, mol_natom, mol_map, my_mol)
...
subroutine, public topology_reorder_atoms(topology, qmmm, qmmm_env_mm, subsys_section, force_env_section)
...
recursive subroutine, public reorder_list_array(ilist1, ilist2, ilist3, ilist4, nsize, ndim)
Order arrays of lists.
subroutine, public topology_set_atm_mass(topology, subsys_section)
Use info from periodic table and set atm_mass.
recursive subroutine, public tag_molecule(icheck, bond_list, i, my_mol)
gives back a mapping of molecules.. icheck needs to be initialized with -1
subroutine, public check_subsys_element(element_in, atom_name_in, element_out, subsys_section, use_mm_map_first)
Check and returns the ELEMENT label.
Control for reading in different topologies and coordinates.
All kind of helpful little routines.
type of a logger, at the moment it contains just a print level starting at which level it should be l...