74#include "../base/base_uses.f90"
93 SUBROUTINE cp_eval_at(gopt_env, x, f, gradient, master, &
94 final_evaluation, para_env)
100 TYPE(gopt_f_type),
POINTER :: gopt_env
101 REAL(KIND=
dp),
DIMENSION(:),
POINTER :: x
102 REAL(KIND=
dp),
INTENT(out),
OPTIONAL :: f
103 REAL(KIND=
dp),
DIMENSION(:),
OPTIONAL, &
105 INTEGER,
INTENT(IN) :: master
106 LOGICAL,
INTENT(IN),
OPTIONAL :: final_evaluation
107 TYPE(mp_para_env_type),
POINTER :: para_env
113 LOGICAL,
PRIVATE,
PARAMETER :: debug_this_module = .true.
114 CHARACTER(len=*),
PARAMETER,
PRIVATE :: moduleN =
"gopt_f_methods"
133 TYPE(gopt_f_type),
POINTER :: gopt_env
134 REAL(kind=dp),
DIMENSION(:),
POINTER :: x0
136 INTEGER :: i, idg, j, nparticle
143 SELECT CASE (gopt_env%type_id)
147 IF (gopt_env%force_env%in_use ==
use_qmmm) &
149 IF (gopt_env%force_env%in_use ==
use_qmmmx) &
152 ALLOCATE (x0(3*nparticle))
155 CALL force_env_get(gopt_env%force_env, subsys=subsys, cell=cell)
157 gopt_env%h_ref = cell%hmat
159 IF (gopt_env%force_env%in_use ==
use_qmmm) &
161 IF (gopt_env%force_env%in_use ==
use_qmmmx) &
164 ALLOCATE (x0(3*nparticle + 6))
170 x0(idg) = cell%hmat(j, i)
174 cpabort(
"Invalid or not yet implemented type of optimization")
187 INTEGER,
INTENT(IN) :: its, output_unit
189 IF (output_unit > 0)
THEN
190 WRITE (unit=output_unit, fmt=
"(/,T2,26('-'))")
191 WRITE (unit=output_unit, fmt=
"(T2,A,I6)")
"OPTIMIZATION STEP: ", its
192 WRITE (unit=output_unit, fmt=
"(T2,26('-'))")
208 SUBROUTINE gopt_f_io_init(gopt_env, output_unit, opt_energy, wildcard, its, used_time)
210 TYPE(gopt_f_type),
POINTER :: gopt_env
211 INTEGER,
INTENT(IN) :: output_unit
212 REAL(kind=dp) :: opt_energy
213 CHARACTER(LEN=5) :: wildcard
214 INTEGER,
INTENT(IN) :: its
215 REAL(kind=dp) :: used_time
217 TYPE(mp_para_env_type),
POINTER :: para_env
218 CHARACTER(LEN=default_string_length) :: energy_unit, stress_unit
219 REAL(kind=dp) :: pres_int
220 INTEGER(KIND=int_8) :: max_memory
221 LOGICAL :: print_memory
226 IF (print_memory)
THEN
232 "PRINT%PROGRAM_RUN_INFO%ENERGY_UNIT", &
235 "PRINT%STRESS_TENSOR%STRESS_UNIT", &
238 SELECT CASE (gopt_env%type_id)
241 IF (.NOT. gopt_env%dimer_rotation)
THEN
242 CALL write_cycle_infos(output_unit, &
246 used_time=used_time, &
247 max_memory=max_memory, &
248 energy_unit=energy_unit, &
249 stress_unit=stress_unit)
251 CALL write_rot_cycle_infos(output_unit, &
254 dimer_env=gopt_env%dimer_env, &
256 used_time=used_time, &
257 max_memory=max_memory)
261 pres_int = gopt_env%cell_env%pres_int
262 CALL write_cycle_infos(output_unit, &
267 used_time=used_time, &
268 max_memory=max_memory, &
269 energy_unit=energy_unit, &
270 stress_unit=stress_unit)
272 CALL write_cycle_infos(output_unit, &
276 used_time=used_time, &
277 max_memory=max_memory, &
278 energy_unit=energy_unit, &
279 stress_unit=stress_unit)
307 SUBROUTINE gopt_f_io(gopt_env, force_env, root_section, its, opt_energy, &
308 output_unit, eold, emin, wildcard, gopt_param, ndf, dx, xi, conv, pred, rat, &
309 step, rad, used_time)
311 TYPE(gopt_f_type),
POINTER :: gopt_env
314 INTEGER,
INTENT(IN) :: its
315 REAL(kind=dp),
INTENT(IN) :: opt_energy
316 INTEGER,
INTENT(IN) :: output_unit
317 REAL(kind=dp) :: eold, emin
318 CHARACTER(LEN=5) :: wildcard
320 INTEGER,
INTENT(IN),
OPTIONAL :: ndf
321 REAL(kind=dp),
DIMENSION(:),
INTENT(IN),
OPTIONAL :: dx
322 REAL(kind=dp),
DIMENSION(:),
OPTIONAL,
POINTER :: xi
323 LOGICAL,
OPTIONAL :: conv
324 REAL(kind=dp),
INTENT(IN),
OPTIONAL :: pred, rat, step, rad
325 REAL(kind=dp) :: used_time
327 CHARACTER(LEN=default_string_length) :: energy_unit, stress_unit
328 INTEGER(KIND=int_8) :: max_memory
329 LOGICAL :: print_memory
330 REAL(kind=dp) :: pres_diff, pres_diff_constr, pres_int, &
332 TYPE(mp_para_env_type),
POINTER :: para_env
337 IF (print_memory)
THEN
343 "PRINT%PROGRAM_RUN_INFO%ENERGY_UNIT", &
346 "PRINT%STRESS_TENSOR%STRESS_UNIT", &
349 SELECT CASE (gopt_env%type_id)
352 IF (.NOT. gopt_env%dimer_rotation)
THEN
353 CALL geo_opt_io(force_env=force_env, root_section=root_section, &
354 motion_section=gopt_env%motion_section, its=its, opt_energy=opt_energy)
355 CALL write_cycle_infos(output_unit, &
358 ediff=(opt_energy - eold), &
365 used_time=used_time, &
366 max_memory=max_memory, &
367 energy_unit=energy_unit, &
368 stress_unit=stress_unit)
370 IF (
PRESENT(conv))
THEN
371 cpassert(
PRESENT(ndf))
372 cpassert(
PRESENT(dx))
373 cpassert(
PRESENT(xi))
374 CALL check_converg(ndf, dx, xi, output_unit, conv, gopt_param, max_memory, stress_unit)
378 CALL write_restart(force_env=force_env, root_section=root_section)
379 CALL write_rot_cycle_infos(output_unit, its, opt_energy, opt_energy - eold, emin, gopt_env%dimer_env, &
380 wildcard=wildcard, used_time=used_time, max_memory=max_memory)
382 IF (
PRESENT(conv))
THEN
383 cpassert(
ASSOCIATED(gopt_env%dimer_env))
384 CALL check_rot_conv(gopt_env%dimer_env, output_unit, conv)
389 pres_diff = gopt_env%cell_env%pres_int - gopt_env%cell_env%pres_ext
390 pres_int = gopt_env%cell_env%pres_int
391 pres_tol = gopt_env%cell_env%pres_tol
392 CALL geo_opt_io(force_env=force_env, root_section=root_section, &
393 motion_section=gopt_env%motion_section, its=its, opt_energy=opt_energy)
394 CALL write_cycle_infos(output_unit, &
397 ediff=(opt_energy - eold), &
405 used_time=used_time, &
406 max_memory=max_memory, &
407 energy_unit=energy_unit, &
408 stress_unit=stress_unit)
410 IF (
PRESENT(conv))
THEN
411 cpassert(
PRESENT(ndf))
412 cpassert(
PRESENT(dx))
413 cpassert(
PRESENT(xi))
414 IF (gopt_env%cell_env%constraint_id ==
fix_none)
THEN
415 CALL check_converg(ndf, dx, xi, output_unit, conv, gopt_param, max_memory, stress_unit, &
418 pres_diff_constr = gopt_env%cell_env%pres_constr - gopt_env%cell_env%pres_ext
419 CALL check_converg(ndf, dx, xi, output_unit, conv, gopt_param, max_memory, stress_unit, &
420 pres_diff, pres_tol, pres_diff_constr)
424 CALL write_cycle_infos(output_unit, &
427 ediff=(opt_energy - eold), &
434 used_time=used_time, &
435 max_memory=max_memory, &
436 energy_unit=energy_unit, &
437 stress_unit=stress_unit)
439 IF (
PRESENT(conv))
THEN
440 cpassert(
PRESENT(ndf))
441 cpassert(
PRESENT(dx))
442 cpassert(
PRESENT(xi))
443 CALL check_converg(ndf, dx, xi, output_unit, conv, gopt_param, max_memory, stress_unit)
463 para_env, master, output_unit)
464 TYPE(gopt_f_type),
POINTER :: gopt_env
466 REAL(kind=dp),
DIMENSION(:),
POINTER :: x0
470 TYPE(mp_para_env_type),
POINTER :: para_env
471 INTEGER,
INTENT(IN) :: master, output_unit
473 IF (gopt_env%eval_opt_geo)
THEN
474 IF (.NOT. gopt_env%dimer_rotation)
THEN
475 CALL write_final_info(output_unit, conv, its, gopt_env, x0, master, &
476 para_env, force_env, gopt_env%motion_section, root_section)
479 CALL write_restart(force_env=force_env, root_section=root_section)
500 SUBROUTINE write_cycle_infos(output_unit, it, etot, ediff, pred, rat, step, rad, emin, &
501 pres_int, wildcard, used_time, max_memory, energy_unit, stress_unit)
503 INTEGER,
INTENT(IN) :: output_unit, it
504 REAL(kind=dp),
INTENT(IN) :: etot
505 REAL(kind=dp),
INTENT(IN),
OPTIONAL :: ediff, pred, rat, step, rad, emin, &
507 CHARACTER(LEN=5),
INTENT(IN) :: wildcard
508 REAL(kind=dp),
INTENT(IN) :: used_time
509 INTEGER(KIND=int_8),
INTENT(IN) :: max_memory
510 CHARACTER(LEN=default_string_length),
INTENT(IN) :: energy_unit, stress_unit
512 CHARACTER(LEN=5) :: tag
514 IF (output_unit > 0)
THEN
516 WRITE (unit=output_unit, fmt=
"(/,T2,A)") tag//repeat(
"*", 74)
517 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,I25)") &
518 tag//
"Step number", it
519 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,A25)") &
520 tag//
"Optimization method", wildcard
521 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
522 tag//
"Total energy ["//trim(adjustl(energy_unit))//
"]", &
524 IF (
PRESENT(pres_int))
THEN
525 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
526 tag//
"Internal pressure ["//trim(adjustl(stress_unit))//
"]", &
529 IF (
PRESENT(ediff))
THEN
530 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
531 tag//
"Effective energy change ["//trim(adjustl(energy_unit))//
"]", &
534 IF (
PRESENT(pred))
THEN
535 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
536 tag//
"Predicted energy change ["//trim(adjustl(energy_unit))//
"]", &
539 IF (
PRESENT(rat))
THEN
540 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
541 tag//
"Scaling factor", rat
543 IF (
PRESENT(step))
THEN
544 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
545 tag//
"Step size", step
547 IF (
PRESENT(rad))
THEN
548 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
549 tag//
"Trust radius", rad
551 IF (
PRESENT(emin))
THEN
552 IF (etot < emin)
THEN
553 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
554 tag//
"Decrease in energy",
" YES"
556 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
557 tag//
"Decrease in energy",
" NO"
560 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.3)") &
561 tag//
"Used time [s]", used_time
563 WRITE (unit=output_unit, fmt=
"(T2,A)") tag//repeat(
"*", 74)
564 IF (max_memory /= 0)
THEN
565 WRITE (unit=output_unit, fmt=
"(T2,A,T60,1X,I20)") &
566 tag//
"Estimated peak process memory [MiB]", &
567 (max_memory + (1024*1024) - 1)/(1024*1024)
572 END SUBROUTINE write_cycle_infos
587 SUBROUTINE write_rot_cycle_infos(output_unit, it, etot, ediff, emin, dimer_env, used_time, &
588 wildcard, max_memory)
590 INTEGER,
INTENT(IN) :: output_unit, it
591 REAL(kind=dp),
INTENT(IN) :: etot
592 REAL(kind=dp),
INTENT(IN),
OPTIONAL :: ediff, emin
594 REAL(kind=dp),
INTENT(IN) :: used_time
595 CHARACTER(LEN=5),
INTENT(IN) :: wildcard
596 INTEGER(KIND=int_8),
INTENT(IN) :: max_memory
598 CHARACTER(LEN=5) :: tag
600 IF (output_unit > 0)
THEN
602 WRITE (unit=output_unit, fmt=
"(/,T2,A)") tag//repeat(
"*", 74)
603 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,I25)") &
604 tag//
"Rotational step number", it
605 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,A25)") &
606 tag//
"Optimization method", wildcard
607 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
608 tag//
"Local curvature", dimer_env%rot%curvature, &
609 tag//
"Total rotational force", etot
610 IF (
PRESENT(ediff))
THEN
611 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
612 tag//
"Rotational force change", ediff
614 IF (
PRESENT(emin))
THEN
615 IF (etot < emin)
THEN
616 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
617 tag//
"Decrease in rotational force",
" YES"
619 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
620 tag//
"Decrease in rotational force",
" NO"
623 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.3)") &
624 tag//
"Used time [s]", used_time
626 WRITE (unit=output_unit, fmt=
"(T2,A)") tag//repeat(
"*", 74)
627 IF (max_memory /= 0)
THEN
628 WRITE (unit=output_unit, fmt=
"(T2,A,T60,1X,I20)") &
629 tag//
"Estimated peak process memory [MiB]", &
630 (max_memory + (1024*1024) - 1)/(1024*1024)
635 END SUBROUTINE write_rot_cycle_infos
650 SUBROUTINE check_converg(ndf, dr, g, output_unit, conv, gopt_param, max_memory, stress_unit, &
651 pres_diff, pres_tol, pres_diff_constr)
653 INTEGER,
INTENT(IN) :: ndf
654 REAL(kind=dp),
INTENT(IN) :: dr(ndf), g(ndf)
655 INTEGER,
INTENT(IN) :: output_unit
656 LOGICAL,
INTENT(OUT) :: conv
658 INTEGER(KIND=int_8),
INTENT(IN) :: max_memory
659 CHARACTER(LEN=default_string_length),
INTENT(IN) :: stress_unit
660 REAL(kind=dp),
INTENT(IN),
OPTIONAL :: pres_diff, pres_tol, pres_diff_constr
662 CHARACTER(LEN=5) :: tag
664 LOGICAL :: conv_dx, conv_g, conv_p, conv_rdx, &
666 REAL(kind=dp) :: dumm, dxcon, gcon, maxdum(4), rmsgcon, &
669 dxcon = gopt_param%max_dr
670 gcon = gopt_param%max_force
671 rmsgcon = gopt_param%rms_force
672 rmsxcon = gopt_param%rms_dr
683 IF (indf == 1) maxdum(1) = abs(dr(indf))
684 dumm = dumm + dr(indf)**2
685 IF (abs(dr(indf)) > dxcon) conv_dx = .false.
686 IF (abs(dr(indf)) > maxdum(1)) maxdum(1) = abs(dr(indf))
689 IF (dumm > (rmsxcon*rmsxcon*ndf)) conv_rdx = .false.
690 maxdum(2) = sqrt(dumm/ndf)
694 IF (indf == 1) maxdum(3) = abs(g(indf))
695 dumm = dumm + g(indf)**2
696 IF (abs(g(indf)) > gcon) conv_g = .false.
697 IF (abs(g(indf)) > maxdum(3)) maxdum(3) = abs(g(indf))
700 IF (dumm > (rmsgcon*rmsgcon*ndf)) conv_rg = .false.
701 maxdum(4) = sqrt(dumm/ndf)
703 IF (
PRESENT(pres_diff_constr) .AND.
PRESENT(pres_tol))
THEN
704 conv_p = abs(pres_diff_constr) < abs(pres_tol)
705 ELSEIF (
PRESENT(pres_diff) .AND.
PRESENT(pres_tol))
THEN
706 conv_p = abs(pres_diff) < abs(pres_tol)
709 IF (output_unit > 0)
THEN
713 WRITE (unit=output_unit, fmt=
"(T2,A)") trim(tag)
714 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
715 tag//
"Maximum step size", maxdum(1), &
716 tag//
"Convergence limit for maximum step size", dxcon
718 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
719 tag//
"Maximum step size is converged",
" YES"
721 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
722 tag//
"Maximum step size is converged",
" NO"
725 WRITE (unit=output_unit, fmt=
"(T2,A)") trim(tag)
726 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
727 tag//
"RMS step size", maxdum(2), &
728 tag//
"Convergence limit for RMS step size", rmsxcon
730 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
731 tag//
"RMS step size is converged",
" YES"
733 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
734 tag//
"RMS step size is converged",
" NO"
737 WRITE (unit=output_unit, fmt=
"(T2,A)") trim(tag)
738 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
739 tag//
"Maximum gradient", maxdum(3), &
740 tag//
"Convergence limit for maximum gradient", gcon
742 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
743 tag//
"Maximum gradient is converged",
" YES"
745 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
746 tag//
"Maximum gradient is converged",
" NO"
749 WRITE (unit=output_unit, fmt=
"(T2,A)") trim(tag)
750 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
751 tag//
"RMS gradient", maxdum(4), &
752 tag//
"Convergence limit for RMS gradient", rmsgcon
754 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
755 tag//
"RMS gradient is converged",
" YES"
757 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
758 tag//
"RMS gradient is converged",
" NO"
761 IF (
PRESENT(pres_diff) .AND.
PRESENT(pres_tol))
THEN
762 WRITE (unit=output_unit, fmt=
"(T2,A)") trim(tag)
763 IF (
PRESENT(pres_diff_constr))
THEN
764 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
765 tag//
"Pressure deviation without constraint ["// &
766 trim(adjustl(stress_unit))//
"]", &
768 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
769 tag//
"Pressure deviation with constraint ["// &
770 trim(adjustl(stress_unit))//
"]", &
773 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
774 tag//
"Pressure deviation ["//trim(adjustl(stress_unit))//
"]", &
777 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
778 tag//
"Pressure tolerance ["//trim(adjustl(stress_unit))//
"]", &
781 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
782 tag//
"Pressure is converged",
" YES"
784 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
785 tag//
"Pressure is converged",
" NO"
789 WRITE (unit=output_unit, fmt=
"(T2,A)") tag//repeat(
"*", 74)
791 IF (max_memory /= 0)
THEN
792 WRITE (unit=output_unit, fmt=
"(T2,A,T60,1X,I20)") &
793 tag//
"Estimated peak process memory after this step [MiB]", &
794 (max_memory + (1024*1024) - 1)/(1024*1024)
799 IF (conv_dx .AND. conv_rdx .AND. conv_g .AND. conv_rg .AND. conv_p) conv = .true.
801 IF ((conv) .AND. (output_unit > 0))
THEN
802 WRITE (unit=output_unit, fmt=
"(/,T2,A)") repeat(
"*", 79)
803 WRITE (unit=output_unit, fmt=
"(T2,A,T25,A,T78,A)") &
804 "***",
"GEOMETRY OPTIMIZATION COMPLETED",
"***"
805 WRITE (unit=output_unit, fmt=
"(T2,A)") repeat(
"*", 79)
808 END SUBROUTINE check_converg
818 SUBROUTINE check_rot_conv(dimer_env, output_unit, conv)
821 INTEGER,
INTENT(IN) :: output_unit
822 LOGICAL,
INTENT(OUT) :: conv
824 CHARACTER(LEN=5) :: tag
826 conv = (abs(dimer_env%rot%angle2) < dimer_env%rot%angle_tol)
828 IF (output_unit > 0)
THEN
830 WRITE (unit=output_unit, fmt=
"(T2,A)") trim(tag)
831 WRITE (unit=output_unit, fmt=
"(T2,A,T55,1X,F25.10)") &
832 tag//
"Predicted angle step size", dimer_env%rot%angle1, &
833 tag//
"Effective angle step size", dimer_env%rot%angle2, &
834 tag//
"Convergence limit for angle step size", dimer_env%rot%angle_tol
836 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
837 tag//
"Angle step size is converged",
" YES"
839 WRITE (unit=output_unit, fmt=
"(T2,A,T77,A4)") &
840 tag//
"Angle step size is converged",
" NO"
842 WRITE (unit=output_unit, fmt=
"(T2,A)") tag//repeat(
"*", 74)
845 IF ((conv) .AND. (output_unit > 0))
THEN
846 WRITE (unit=output_unit, fmt=
"(/,T2,A)") repeat(
"*", 79)
847 WRITE (unit=output_unit, fmt=
"(T2,A,T25,A,T78,A)") &
848 "***",
"ROTATION OPTIMIZATION COMPLETED",
"***"
849 WRITE (unit=output_unit, fmt=
"(T2,A)") repeat(
"*", 79)
852 END SUBROUTINE check_rot_conv
869 RECURSIVE SUBROUTINE write_final_info(output_unit, conv, it, gopt_env, x0, master, para_env, force_env, &
870 motion_section, root_section)
871 INTEGER,
INTENT(IN) :: output_unit
872 LOGICAL,
INTENT(IN) :: conv
873 INTEGER,
INTENT(INOUT) :: it
874 TYPE(gopt_f_type),
POINTER :: gopt_env
875 REAL(kind=dp),
DIMENSION(:),
POINTER :: x0
876 INTEGER,
INTENT(IN) :: master
877 TYPE(mp_para_env_type),
POINTER :: para_env
881 CHARACTER(LEN=4) :: constraint_label
882 LOGICAL :: keep_angles, keep_symmetry, &
884 REAL(kind=dp) :: etot
892 particle_set => particles%els
898 keep_symmetry = .true.
900 constraint_label =
"NONE"
902 keep_angles = gopt_env%cell_env%keep_angles
903 keep_symmetry = gopt_env%cell_env%keep_symmetry
904 keep_volume = gopt_env%cell_env%keep_volume
905 SELECT CASE (gopt_env%cell_env%constraint_id)
907 constraint_label =
" X"
909 constraint_label =
" Y"
911 constraint_label =
" Z"
913 constraint_label =
" XY"
915 constraint_label =
" XZ"
917 constraint_label =
" YZ"
919 constraint_label =
"NONE"
923 keep_angles, keep_symmetry, keep_volume, &
924 gopt_env%label, constraint_label)
929 CALL write_restart(force_env=force_env, root_section=root_section)
931 IF (output_unit > 0) &
932 WRITE (unit=output_unit, fmt=
"(/,T20,' Reevaluating energy at the minimum')")
934 CALL cp_eval_at(gopt_env, x0, f=etot, master=master, final_evaluation=.true., &
936 CALL write_geo_traj(force_env, root_section, it, etot)
939 END SUBROUTINE write_final_info
952 SUBROUTINE write_geo_traj(force_env, root_section, it, etot)
956 INTEGER,
INTENT(IN) :: it
957 REAL(kind=dp),
INTENT(IN) :: etot
959 LOGICAL :: shell_adiabatic, shell_present
965 NULLIFY (atomic_kinds)
966 NULLIFY (atomic_kind_set)
967 NULLIFY (core_particles)
968 NULLIFY (shell_particles)
973 CALL write_trajectory(force_env, root_section, it, 0.0_dp, 0.0_dp, etot,
"FORCES", middle_name=
"frc")
976 atomic_kind_set => atomic_kinds%els
978 shell_present=shell_present, &
979 shell_adiabatic=shell_adiabatic)
980 IF (shell_present)
THEN
982 core_particles=core_particles, &
983 shell_particles=shell_particles)
984 CALL write_trajectory(force_env, root_section, it=it, time=0.0_dp, dtime=0.0_dp, &
985 etot=etot, pk_name=
"SHELL_TRAJECTORY", middle_name=
"shpos", &
986 particles=shell_particles)
987 IF (shell_adiabatic)
THEN
988 CALL write_trajectory(force_env, root_section, it=it, time=0.0_dp, dtime=0.0_dp, &
989 etot=etot, pk_name=
"SHELL_FORCES", middle_name=
"shfrc", &
990 particles=shell_particles)
991 CALL write_trajectory(force_env, root_section, it=it, time=0.0_dp, dtime=0.0_dp, &
992 etot=etot, pk_name=
"CORE_TRAJECTORY", middle_name=
"copos", &
993 particles=core_particles)
994 CALL write_trajectory(force_env, root_section, it=it, time=0.0_dp, dtime=0.0_dp, &
995 etot=etot, pk_name=
"CORE_FORCES", middle_name=
"cofrc", &
996 particles=core_particles)
1000 END SUBROUTINE write_geo_traj
1012 TYPE(gopt_f_type),
POINTER :: gopt_env
1013 INTEGER,
INTENT(IN) :: output_unit
1014 CHARACTER(LEN=*),
INTENT(IN) :: label
1016 CHARACTER(LEN=default_string_length) :: my_format, my_label
1019 IF (output_unit > 0)
THEN
1020 WRITE (unit=output_unit, fmt=
"(/,T2,A)") repeat(
"*", 79)
1021 IF (gopt_env%dimer_rotation)
THEN
1022 my_label =
"OPTIMIZING DIMER ROTATION"
1024 my_label =
"STARTING "//gopt_env%tag(1:8)//
" OPTIMIZATION"
1027 ix = (80 - 7 - len_trim(my_label))/2
1030 WRITE (unit=output_unit, fmt=trim(my_format))
"***", trim(my_label),
"***"
1032 ix = (80 - 7 - len_trim(label))/2
1035 WRITE (unit=output_unit, fmt=trim(my_format))
"***", trim(label),
"***"
1037 WRITE (unit=output_unit, fmt=
"(T2,A)") repeat(
"*", 79)
1051 TYPE(gopt_f_type),
POINTER :: gopt_env
1052 INTEGER,
INTENT(IN) :: output_unit
1054 IF (output_unit > 0)
THEN
1055 WRITE (unit=output_unit, fmt=
"(/,T2,A)") &
1056 "*** MAXIMUM NUMBER OF OPTIMIZATION STEPS REACHED ***"
1057 IF (.NOT. gopt_env%dimer_rotation)
THEN
1058 WRITE (unit=output_unit, fmt=
"(T2,A)") &
1059 "*** EXITING GEOMETRY OPTIMIZATION ***"
1061 WRITE (unit=output_unit, fmt=
"(T2,A)") &
1062 "*** EXITING ROTATION OPTIMIZATION ***"
1080 SUBROUTINE geo_opt_io(force_env, root_section, motion_section, its, opt_energy)
1084 INTEGER,
INTENT(IN) :: its
1085 REAL(kind=dp),
INTENT(IN) :: opt_energy
1092 TYPE(mp_para_env_type),
POINTER :: para_env
1097 NULLIFY (para_env, atomic_kind_set, subsys, particle_set, &
1098 local_particles, atomic_kinds, particles)
1101 CALL write_restart(force_env=force_env, root_section=root_section)
1104 CALL write_geo_traj(force_env, root_section, its, opt_energy)
1107 CALL force_env_get(force_env, cell=cell, para_env=para_env, &
1109 CALL cp_subsys_get(subsys=subsys, atomic_kinds=atomic_kinds, local_particles=local_particles, &
1110 particles=particles, virial=virial)
1111 atomic_kind_set => atomic_kinds%els
1112 particle_set => particles%els
1113 CALL virial_evaluate(atomic_kind_set, particle_set, local_particles, &
1120 END SUBROUTINE geo_opt_io
1134 TYPE(gopt_f_type),
POINTER :: gopt_env
1136 REAL(kind=dp),
DIMENSION(:),
POINTER :: x
1137 LOGICAL,
INTENT(IN) :: update_forces
1139 INTEGER :: i, iatom, idg, j, natom, nparticle, &
1141 REAL(kind=dp) :: fc, fs, mass
1142 REAL(kind=dp),
DIMENSION(3) :: s
1149 NULLIFY (core_particles)
1151 NULLIFY (shell_particles)
1159 core_particles=core_particles, &
1160 particles=particles, &
1161 shell_particles=shell_particles)
1165 CALL cell_copy(cell, cell_ref, tag=
"CELL_OPT_REF")
1169 CALL init_cell(cell_ref, hmat=gopt_env%h_ref)
1170 cpassert((
SIZE(x) == idg + 6))
1172 IF (update_forces)
THEN
1188 cell%hmat(j, i) = x(idg)
1198 shell_index = particles%els(iatom)%shell_index
1199 IF (shell_index == 0)
THEN
1203 i = 3*(natom + shell_index - 1) + 1
1207 mass = particles%els(iatom)%atomic_kind%mass
1208 fc = core_particles%els(shell_index)%atomic_kind%shell%mass_core/mass
1209 fs = shell_particles%els(shell_index)%atomic_kind%shell%mass_shell/mass
1210 particles%els(iatom)%r(1:3) = fc*core_particles%els(shell_index)%r(1:3) + &
1211 fs*shell_particles%els(shell_index)%r(1:3)
subroutine cp_eval_at(gopt_env, x, f, gradient, master, final_evaluation, para_env)
evaluete the potential energy and its gradients using an array with same dimension as the particle_se...
represent a simple array based list of the given type
Define the atomic kind types and their sub types.
subroutine, public get_atomic_kind_set(atomic_kind_set, atom_of_kind, kind_of, natom_of_kind, maxatom, natom, nshell, fist_potential_present, shell_present, shell_adiabatic, shell_check_distance, damping_present)
Get attributes of an atomic kind set.
Handles all functions related to the CELL.
subroutine, public init_cell(cell, hmat, periodic)
Initialise/readjust a simulation cell after hmat has been changed.
subroutine, public cell_create(cell, hmat, periodic, tag)
allocates and initializes a cell
Handles all functions related to the CELL.
subroutine, public scaled_to_real(r, s, cell)
Transform scaled cell coordinates real coordinates. r=h*s.
subroutine, public real_to_scaled(s, r, cell)
Transform real to scaled cell coordinates. s=h_inv*r.
subroutine, public cell_release(cell)
releases the given cell (see doc/ReferenceCounting.html)
subroutine, public cell_copy(cell_in, cell_out, tag)
Copy cell variable.
various routines to log and control the output. The idea is that decisions about where to log should ...
types that represent a subsys, i.e. a part of the system
subroutine, public cp_subsys_set(subsys, atomic_kinds, particles, local_particles, molecules, molecule_kinds, local_molecules, para_env, colvar_p, shell_particles, core_particles, gci, multipoles, results, cell, cell_ref, use_ref_cell)
sets various propreties of the subsys
subroutine, public cp_subsys_get(subsys, ref_count, atomic_kinds, atomic_kind_set, particles, particle_set, local_particles, molecules, molecule_set, molecule_kinds, molecule_kind_set, local_molecules, para_env, colvar_p, shell_particles, core_particles, gci, multipoles, natom, nparticle, ncore, nshell, nkind, atprop, virial, results, cell, cell_ref, use_ref_cell)
returns information about various attributes of the given subsys
subroutine, public pack_subsys_particles(subsys, f, r, s, v, fscale, cell)
Pack components of a subsystem particle sets into a single vector.
real(kind=dp) function, public cp_unit_from_cp2k(value, unit_str, defaults, power)
converts from the internal cp2k units to the given unit
Contains types used for a Dimer Method calculations.
Contains utilities for a Dimer Method calculations.
subroutine, public update_dimer_vec(dimer_env, motion_section)
Updates the orientation of the dimer vector in the input file.
stores a lists of integer that are local to a processor. The idea is that these integers represent ob...
Interface for the force calculations.
integer function, public force_env_get_natom(force_env)
returns the number of atoms
integer, parameter, public use_qmmm
recursive subroutine, public force_env_get(force_env, in_use, fist_env, qs_env, meta_env, fp_env, subsys, para_env, potential_energy, additional_potential, kinetic_energy, harmonic_shell, kinetic_shell, cell, sub_force_env, qmmm_env, qmmmx_env, eip_env, pwdft_env, globenv, input, force_env_section, method_name_id, root_section, mixed_env, nnp_env, embed_env, ipi_env)
returns various attributes about the force environment
integer, parameter, public use_qmmmx
integer function, public force_env_get_nparticle(force_env)
returns the number of particles in a force environment
contains a functional that calculates the energy and its derivatives for the geometry optimizer
subroutine, public print_geo_opt_header(gopt_env, output_unit, label)
...
subroutine, public gopt_f_io_init(gopt_env, output_unit, opt_energy, wildcard, its, used_time)
Handles the Output during an optimization run.
subroutine, public gopt_f_create_x0(gopt_env, x0)
returns the value of the parameters for the actual configuration
recursive subroutine, public gopt_f_io_finalize(gopt_env, force_env, x0, conv, its, root_section, para_env, master, output_unit)
Handles the Output at the end of an optimization run.
subroutine, public apply_cell_change(gopt_env, cell, x, update_forces)
Apply coordinate transformations after cell (shape) change.
subroutine, public gopt_f_io(gopt_env, force_env, root_section, its, opt_energy, output_unit, eold, emin, wildcard, gopt_param, ndf, dx, xi, conv, pred, rat, step, rad, used_time)
Handles the Output during an optimization run.
subroutine, public print_geo_opt_nc(gopt_env, output_unit)
...
subroutine, public gopt_f_ii(its, output_unit)
Prints iteration step of the optimization procedure on screen.
contains a functional that calculates the energy and its derivatives for the geometry optimizer
contains typo and related routines to handle parameters controlling the GEO_OPT module
Defines the basic variable types.
integer, parameter, public int_8
integer, parameter, public dp
integer, parameter, public default_string_length
Machine interface based on Fortran 2003 and POSIX.
subroutine, public m_flush(lunit)
flushes units if the &GLOBAL flag is set accordingly
prints all energy info per timestep to the screen or to user defined output files
integer(kind=int_8) function, public sample_memory(para_env)
Samples memory usage.
Interface to the message passing library MPI.
Output Utilities for MOTION_SECTION.
subroutine, public write_simulation_cell(cell, motion_section, itimes, time, pos, act)
Prints the Simulation Cell.
subroutine, public write_trajectory(force_env, root_section, it, time, dtime, etot, pk_name, pos, act, middle_name, particles, extended_xmol_title)
Prints the information controlled by the TRAJECTORY section.
subroutine, public write_stress_tensor_to_file(virial, cell, motion_section, itimes, time, pos, act)
Prints the Stress Tensor.
represent a simple array based list of the given type
Define methods related to particle_type.
subroutine, public write_final_structure(particle_set, cell, input_section, conv, keep_angles, keep_symmetry, keep_volume, gopt_env_label, constraint_label)
Write the final geometry and cell information to files.
subroutine, public write_structure_data(particle_set, cell, input_section)
Write structure data requested by a separate structure data input section to the output unit....
Define the data structure for the particle information.
subroutine, public apply_qmmm_translate(qmmm_env)
Apply translation to the full system in order to center the QM system into the QM box.
Routines used for force-mixing QM/MM calculations.
subroutine, public apply_qmmmx_translate(qmmmx_env)
Apply translation to the full system in order to center the QM system into the QM box.
subroutine, public virial_evaluate(atomic_kind_set, particle_set, local_particles, virial, igroup)
Computes the kinetic part of the pressure tensor and updates the full VIRIAL (PV)
represent a list of objects
Provides all information about an atomic kind.
Type defining parameters related to the simulation cell.
represents a system: atoms, molecules, their pos,vel,...
Defines the environment for a Dimer Method calculation.
structure to store local (to a processor) ordered lists of integers.
wrapper to abstract the force evaluation of the various methods
calculates the potential energy of a system, and its derivatives
stores all the informations relevant to an mpi environment
represent a list of objects