run_calculation Subroutine

public subroutine run_calculation(resources, config, sys_geom, bonds, result_out, all_ranks_write_json)

Main calculation dispatcher - routes to fragmented or unfragmented calculation

Determines calculation type based on nlevel and dispatches to appropriate calculation routine with proper MPI setup and validation. If result_out is present, returns result instead of writing JSON (for dynamics/optimization)

Arguments

Type IntentOptional Attributes Name
type(resources_t), intent(in) :: resources

Resources container (MPI comms, etc.)

type(driver_config_t), intent(in) :: config

Driver configuration

type(system_geometry_t), intent(in) :: sys_geom

System geometry and fragment info

type(bond_t), intent(in), optional :: bonds(:)

Bond connectivity information

type(calculation_result_t), intent(out), optional :: result_out

Optional result output

logical, intent(in), optional :: all_ranks_write_json

If true, all ranks write JSON (for multi-molecule)


Calls

proc~~run_calculation~~CallsGraph proc~run_calculation run_calculation info info proc~run_calculation->info omp_set_num_threads omp_set_num_threads proc~run_calculation->omp_set_num_threads proc~config_log_settings method_config_t%config_log_settings proc~run_calculation->proc~config_log_settings proc~json_output_data_destroy json_output_data_t%json_output_data_destroy proc~run_calculation->proc~json_output_data_destroy proc~run_fragmented_calculation run_fragmented_calculation proc~run_calculation->proc~run_fragmented_calculation proc~run_unfragmented_calculation run_unfragmented_calculation proc~run_calculation->proc~run_unfragmented_calculation proc~write_json_output write_json_output proc~run_calculation->proc~write_json_output to_char to_char proc~run_calculation->to_char warning warning proc~run_calculation->warning proc~config_log_settings->info proc~xtb_get_solvation_info xtb_config_t%xtb_get_solvation_info proc~config_log_settings->proc~xtb_get_solvation_info proc~json_output_data_reset json_output_data_t%json_output_data_reset proc~json_output_data_destroy->proc~json_output_data_reset proc~run_fragmented_calculation->info proc~run_fragmented_calculation->to_char abort_comm abort_comm proc~run_fragmented_calculation->abort_comm allgather allgather proc~run_fragmented_calculation->allgather bcast bcast proc~run_fragmented_calculation->bcast destroy destroy proc~run_fragmented_calculation->destroy error error proc~run_fragmented_calculation->error init init proc~run_fragmented_calculation->init proc~apply_distance_screening apply_distance_screening proc~run_fragmented_calculation->proc~apply_distance_screening proc~binomial binomial proc~run_fragmented_calculation->proc~binomial proc~combine combine proc~run_fragmented_calculation->proc~combine proc~create_monomer_list create_monomer_list proc~run_fragmented_calculation->proc~create_monomer_list proc~error_get_message error_t%error_get_message proc~run_fragmented_calculation->proc~error_get_message proc~error_has_error error_t%error_has_error proc~run_fragmented_calculation->proc~error_has_error proc~generate_fragment_list generate_fragment_list proc~run_fragmented_calculation->proc~generate_fragment_list proc~get_nfrags get_nfrags proc~run_fragmented_calculation->proc~get_nfrags proc~gmbe_enumerate_pie_terms gmbe_enumerate_pie_terms proc~run_fragmented_calculation->proc~gmbe_enumerate_pie_terms proc~sort_fragments_by_size sort_fragments_by_size proc~run_fragmented_calculation->proc~sort_fragments_by_size run_distributed run_distributed proc~run_fragmented_calculation->run_distributed run_serial run_serial proc~run_fragmented_calculation->run_serial proc~run_unfragmented_calculation->info proc~run_unfragmented_calculation->to_char interface~distributed_unfragmented_hessian distributed_unfragmented_hessian proc~run_unfragmented_calculation->interface~distributed_unfragmented_hessian interface~unfragmented_calculation unfragmented_calculation proc~run_unfragmented_calculation->interface~unfragmented_calculation proc~calc_type_to_string calc_type_to_string proc~run_unfragmented_calculation->proc~calc_type_to_string verbose verbose proc~run_unfragmented_calculation->verbose proc~write_json_output->error proc~write_gmbe_pie_json_impl write_gmbe_pie_json_impl proc~write_json_output->proc~write_gmbe_pie_json_impl proc~write_mbe_breakdown_json_impl write_mbe_breakdown_json_impl proc~write_json_output->proc~write_mbe_breakdown_json_impl proc~write_unfragmented_json_impl write_unfragmented_json_impl proc~write_json_output->proc~write_unfragmented_json_impl proc~write_vibrational_json_impl write_vibrational_json_impl proc~write_json_output->proc~write_vibrational_json_impl proc~distributed_unfragmented_hessian distributed_unfragmented_hessian interface~distributed_unfragmented_hessian->proc~distributed_unfragmented_hessian proc~unfragmented_calculation unfragmented_calculation interface~unfragmented_calculation->proc~unfragmented_calculation proc~apply_distance_screening->info proc~apply_distance_screening->to_char proc~fragment_should_be_screened fragment_should_be_screened proc~apply_distance_screening->proc~fragment_should_be_screened proc~combine_util combine_util proc~combine->proc~combine_util proc~generate_fragment_list->proc~combine proc~get_nfrags->proc~binomial proc~gmbe_enumerate_pie_terms->info proc~gmbe_enumerate_pie_terms->to_char proc~gmbe_enumerate_pie_terms->proc~error_has_error atom_list atom_list proc~gmbe_enumerate_pie_terms->atom_list proc~compute_polymer_atoms compute_polymer_atoms proc~gmbe_enumerate_pie_terms->proc~compute_polymer_atoms proc~dfs_pie_accumulate dfs_pie_accumulate proc~gmbe_enumerate_pie_terms->proc~dfs_pie_accumulate proc~error_set error_t%error_set proc~gmbe_enumerate_pie_terms->proc~error_set proc~sort_fragments_by_size->info sort_index sort_index proc~sort_fragments_by_size->sort_index proc~write_gmbe_pie_json_impl->info proc~write_gmbe_pie_json_impl->destroy proc~write_gmbe_pie_json_impl->error add add proc~write_gmbe_pie_json_impl->add create_array create_array proc~write_gmbe_pie_json_impl->create_array create_object create_object proc~write_gmbe_pie_json_impl->create_object initialize initialize proc~write_gmbe_pie_json_impl->initialize proc~get_basename get_basename proc~write_gmbe_pie_json_impl->proc~get_basename proc~get_output_json_filename get_output_json_filename proc~write_gmbe_pie_json_impl->proc~get_output_json_filename proc~write_mbe_breakdown_json_impl->info proc~write_mbe_breakdown_json_impl->warning proc~write_mbe_breakdown_json_impl->destroy proc~write_mbe_breakdown_json_impl->error proc~write_mbe_breakdown_json_impl->add proc~write_mbe_breakdown_json_impl->create_array proc~write_mbe_breakdown_json_impl->create_object proc~write_mbe_breakdown_json_impl->initialize proc~write_mbe_breakdown_json_impl->proc~get_basename proc~get_frag_level_name get_frag_level_name proc~write_mbe_breakdown_json_impl->proc~get_frag_level_name proc~write_mbe_breakdown_json_impl->proc~get_output_json_filename proc~write_unfragmented_json_impl->info proc~write_unfragmented_json_impl->destroy proc~write_unfragmented_json_impl->error proc~write_unfragmented_json_impl->add proc~write_unfragmented_json_impl->create_object proc~write_unfragmented_json_impl->initialize proc~write_unfragmented_json_impl->proc~get_basename proc~write_unfragmented_json_impl->proc~get_output_json_filename proc~write_vibrational_json_impl->info proc~write_vibrational_json_impl->destroy proc~write_vibrational_json_impl->error proc~write_vibrational_json_impl->add proc~write_vibrational_json_impl->create_object proc~write_vibrational_json_impl->initialize proc~write_vibrational_json_impl->proc~get_basename proc~write_vibrational_json_impl->proc~get_output_json_filename proc~xtb_get_solvation_info->to_char proc~xtb_has_solvation xtb_config_t%xtb_has_solvation proc~xtb_get_solvation_info->proc~xtb_has_solvation proc~combine_util->proc~combine_util proc~dfs_pie_accumulate->proc~error_has_error proc~dfs_pie_accumulate->proc~dfs_pie_accumulate new_clique new_clique proc~dfs_pie_accumulate->new_clique proc~atom_sets_equal atom_sets_equal proc~dfs_pie_accumulate->proc~atom_sets_equal proc~grow_pie_storage grow_pie_storage proc~dfs_pie_accumulate->proc~grow_pie_storage proc~intersect_atom_lists intersect_atom_lists proc~dfs_pie_accumulate->proc~intersect_atom_lists test_intersect test_intersect proc~dfs_pie_accumulate->test_intersect barrier barrier proc~distributed_unfragmented_hessian->barrier interface~hessian_coordinator hessian_coordinator proc~distributed_unfragmented_hessian->interface~hessian_coordinator interface~hessian_worker hessian_worker proc~distributed_unfragmented_hessian->interface~hessian_worker proc~calculate_monomer_distance calculate_monomer_distance proc~fragment_should_be_screened->proc~calculate_monomer_distance proc~get_next_combination get_next_combination proc~fragment_should_be_screened->proc~get_next_combination proc~unfragmented_calculation->info proc~unfragmented_calculation->to_char proc~unfragmented_calculation->error proc~unfragmented_calculation->proc~error_get_message proc~unfragmented_calculation->proc~error_has_error cart_disp cart_disp proc~unfragmented_calculation->cart_disp configuration configuration proc~unfragmented_calculation->configuration eigenvalues eigenvalues proc~unfragmented_calculation->eigenvalues fc_mdyne fc_mdyne proc~unfragmented_calculation->fc_mdyne force_constants force_constants proc~unfragmented_calculation->force_constants frequencies frequencies proc~unfragmented_calculation->frequencies interface~do_fragment_work do_fragment_work proc~unfragmented_calculation->interface~do_fragment_work ir_intensities ir_intensities proc~unfragmented_calculation->ir_intensities proc~check_duplicate_atoms check_duplicate_atoms proc~unfragmented_calculation->proc~check_duplicate_atoms proc~compute_thermochemistry compute_thermochemistry proc~unfragmented_calculation->proc~compute_thermochemistry proc~compute_vibrational_analysis compute_vibrational_analysis proc~unfragmented_calculation->proc~compute_vibrational_analysis proc~compute_vibrational_frequencies compute_vibrational_frequencies proc~unfragmented_calculation->proc~compute_vibrational_frequencies proc~energy_total energy_t%energy_total proc~unfragmented_calculation->proc~energy_total proc~error_get_full_trace error_t%error_get_full_trace proc~unfragmented_calculation->proc~error_get_full_trace proc~fragment_compute_nelec physical_fragment_t%fragment_compute_nelec proc~unfragmented_calculation->proc~fragment_compute_nelec proc~print_vibrational_analysis print_vibrational_analysis proc~unfragmented_calculation->proc~print_vibrational_analysis proc~result_destroy calculation_result_t%result_destroy proc~unfragmented_calculation->proc~result_destroy projected_hessian projected_hessian proc~unfragmented_calculation->projected_hessian reduced_masses reduced_masses proc~unfragmented_calculation->reduced_masses proc~do_fragment_work do_fragment_work interface~do_fragment_work->proc~do_fragment_work proc~hessian_coordinator hessian_coordinator interface~hessian_coordinator->proc~hessian_coordinator proc~hessian_worker hessian_worker interface~hessian_worker->proc~hessian_worker proc~to_angstrom to_angstrom proc~calculate_monomer_distance->proc~to_angstrom proc~check_duplicate_atoms->to_char proc~check_duplicate_atoms->error proc~check_duplicate_atoms->proc~error_set proc~element_number_to_symbol element_number_to_symbol proc~check_duplicate_atoms->proc~element_number_to_symbol proc~compute_electronic_entropy compute_electronic_entropy proc~compute_thermochemistry->proc~compute_electronic_entropy proc~compute_moments_of_inertia compute_moments_of_inertia proc~compute_thermochemistry->proc~compute_moments_of_inertia proc~compute_partition_functions compute_partition_functions proc~compute_thermochemistry->proc~compute_partition_functions proc~compute_rotational_constants compute_rotational_constants proc~compute_thermochemistry->proc~compute_rotational_constants proc~compute_rotational_thermo compute_rotational_thermo proc~compute_thermochemistry->proc~compute_rotational_thermo proc~compute_translational_thermo compute_translational_thermo proc~compute_thermochemistry->proc~compute_translational_thermo proc~compute_vibrational_thermo compute_vibrational_thermo proc~compute_thermochemistry->proc~compute_vibrational_thermo proc~compute_zpe compute_zpe proc~compute_thermochemistry->proc~compute_zpe proc~compute_vibrational_analysis->proc~compute_vibrational_frequencies proc~compute_cartesian_displacements compute_cartesian_displacements proc~compute_vibrational_analysis->proc~compute_cartesian_displacements proc~compute_force_constants compute_force_constants proc~compute_vibrational_analysis->proc~compute_force_constants proc~compute_ir_intensities compute_ir_intensities proc~compute_vibrational_analysis->proc~compute_ir_intensities proc~compute_reduced_masses compute_reduced_masses proc~compute_vibrational_analysis->proc~compute_reduced_masses proc~compute_vibrational_frequencies->warning proc~compute_vibrational_frequencies->error pic_syev pic_syev proc~compute_vibrational_frequencies->pic_syev proc~mass_weight_hessian mass_weight_hessian proc~compute_vibrational_frequencies->proc~mass_weight_hessian proc~project_translation_rotation project_translation_rotation proc~compute_vibrational_frequencies->proc~project_translation_rotation proc~mp2_total mp2_energy_t%mp2_total proc~energy_total->proc~mp2_total proc~error_get_full_trace->proc~error_has_error proc~grow_pie_storage->to_char proc~grow_pie_storage->proc~error_set proc~print_vibrational_analysis->info proc~print_vibrational_analysis->warning proc~print_vibrational_analysis->proc~compute_thermochemistry proc~print_vibrational_analysis->proc~element_number_to_symbol proc~print_thermochemistry print_thermochemistry proc~print_vibrational_analysis->proc~print_thermochemistry proc~result_reset calculation_result_t%result_reset proc~result_destroy->proc~result_reset

Called by

proc~~run_calculation~~CalledByGraph proc~run_calculation run_calculation proc~compute_energy_and_forces compute_energy_and_forces proc~compute_energy_and_forces->proc~run_calculation proc~run_multi_molecule_calculations run_multi_molecule_calculations proc~run_multi_molecule_calculations->proc~run_calculation program~main main program~main->proc~run_calculation program~main->proc~run_multi_molecule_calculations

Variables

Type Visibility Attributes Name Initial
integer, private :: i

Loop counter

type(json_output_data_t), private :: json_data

Cached output data for centralized JSON writing

integer, private :: max_level

Maximum fragment level (nlevel from config)

logical, private :: should_write_json

Whether this rank should write JSON


Source Code

   subroutine run_calculation(resources, config, sys_geom, bonds, result_out, all_ranks_write_json)
      !! Main calculation dispatcher - routes to fragmented or unfragmented calculation
      !!
      !! Determines calculation type based on nlevel and dispatches to appropriate
      !! calculation routine with proper MPI setup and validation.
      !! If result_out is present, returns result instead of writing JSON (for dynamics/optimization)
      type(resources_t), intent(in) :: resources  !! Resources container (MPI comms, etc.)
      type(driver_config_t), intent(in) :: config  !! Driver configuration
      type(system_geometry_t), intent(in) :: sys_geom  !! System geometry and fragment info
      type(bond_t), intent(in), optional :: bonds(:)  !! Bond connectivity information
      type(calculation_result_t), intent(out), optional :: result_out  !! Optional result output
      logical, intent(in), optional :: all_ranks_write_json  !! If true, all ranks write JSON (for multi-molecule)

      ! Local variables
      integer :: max_level   !! Maximum fragment level (nlevel from config)
      integer :: i  !! Loop counter
      type(json_output_data_t) :: json_data  !! Cached output data for centralized JSON writing
      logical :: should_write_json  !! Whether this rank should write JSON

      ! Set max_level from config
      max_level = config%nlevel

      ! Log method-specific settings (rank 0 only)
      if (resources%mpi_comms%world_comm%rank() == 0) then
         call config%method_config%log_settings()
      end if

      if (resources%mpi_comms%world_comm%rank() == 0 .and. max_level > 0) then
         call logger%info("============================================")
         call logger%info("Loaded geometry:")
         call logger%info("  Total monomers: "//to_char(sys_geom%n_monomers))
         call logger%info("  Atoms per monomer: "//to_char(sys_geom%atoms_per_monomer))
         call logger%info("  Fragment level: "//to_char(max_level))
         call logger%info("  Total atoms: "//to_char(sys_geom%total_atoms))
         call logger%info("============================================")
      end if

      ! Warn if overlapping fragments flag is set but nlevel=0
      if (config%allow_overlapping_fragments .and. max_level == 0) then
         if (resources%mpi_comms%world_comm%rank() == 0) then
            call logger%warning("allow_overlapping_fragments is set to true, but nlevel=0")
            call logger%warning("Running unfragmented calculation - overlapping fragments flag will be ignored")
         end if
      end if

      ! GMBE (overlapping fragments) with inclusion-exclusion principle
      ! GMBE(1): Base fragments are monomers
      ! GMBE(N): Base fragments are N-mers (e.g., dimers for N=2)
      ! Algorithm: Generate primaries, use DFS to enumerate overlapping cliques,
      ! accumulate PIE coefficients per unique atom set, evaluate each once

      if (max_level == 0) then
         call omp_set_num_threads(1)
         if (present(result_out)) then
            ! For dynamics/optimization: return result directly, no JSON output
            call run_unfragmented_calculation(resources%mpi_comms%world_comm, sys_geom, config, result_out)
         else
            ! Normal mode: collect json_data for centralized output
            call run_unfragmented_calculation(resources%mpi_comms%world_comm, sys_geom, config, json_data=json_data)
         end if
      else
         if (present(result_out)) then
            ! For fragmented calculations with result_out (future use)
            call run_fragmented_calculation(resources, config, sys_geom, bonds)
         else
            ! Normal mode: collect json_data for centralized output
            call run_fragmented_calculation(resources, config, sys_geom, bonds, json_data)
         end if
      end if

      ! Centralized JSON output (rank 0 only by default, or all ranks if all_ranks_write_json is set)
      if (.not. present(result_out)) then
         ! Check if JSON output should be skipped
         if (config%skip_json_output) then
            if (resources%mpi_comms%world_comm%rank() == 0) then
               call logger%info("Skipping JSON output (skip_json_output = true)")
            end if
         else
            ! Determine if this rank should write JSON
            should_write_json = (resources%mpi_comms%world_comm%rank() == 0)
            if (present(all_ranks_write_json)) then
               if (all_ranks_write_json) should_write_json = .true.
            end if

            if (should_write_json) then
               if (json_data%output_mode /= OUTPUT_MODE_NONE) then
                  call write_json_output(json_data)
                  call json_data%destroy()
               end if
            end if
         end if
      end if

   end subroutine run_calculation