-/* Copyright (c) 2007-2021. The SimGrid Team. All rights reserved. */
+/* Copyright (c) 2007-2022. The SimGrid Team. All rights reserved. */
/* This program is free software; you can redistribute it and/or modify it
* under the terms of the license (GNU LGPL) which comes with this package. */
static simgrid::config::Flag<int> smpi_map("smpi/map", "Display the mapping between nodes and processes", 0);
-void (*smpi_comm_copy_data_callback)(simgrid::kernel::activity::CommImpl*, void*,
- size_t) = &smpi_comm_copy_buffer_callback;
+std::function<void(simgrid::kernel::activity::CommImpl*, void*, size_t)> smpi_comm_copy_data_callback =
+ &smpi_comm_copy_buffer_callback;
simgrid::smpi::ActorExt* smpi_process()
{
}
void * smpi_process_get_user_data(){
- return simgrid::s4u::Actor::self()->get_data();
+ return simgrid::s4u::Actor::self()->get_data<void>();
}
void smpi_process_set_user_data(void *data){
void smpi_comm_set_copy_data_callback(void (*callback) (smx_activity_t, void*, size_t))
{
- static void (*saved_callback)(smx_activity_t, void*, size_t);
- saved_callback = callback;
- smpi_comm_copy_data_callback = [](simgrid::kernel::activity::CommImpl* comm, void* buff, size_t size) {
- saved_callback(comm, buff, size);
- };
+ smpi_comm_copy_data_callback = callback;
}
static void memcpy_private(void* dest, const void* src, const std::vector<std::pair<size_t, size_t>>& private_blocks)
{
- for (auto const& block : private_blocks)
- memcpy((uint8_t*)dest+block.first, (uint8_t*)src+block.first, block.second-block.first);
+ for (auto const& [block_begin, block_end] : private_blocks)
+ memcpy((uint8_t*)dest + block_begin, (uint8_t*)src + block_begin, block_end - block_begin);
}
static void check_blocks(const std::vector<std::pair<size_t, size_t>>& private_blocks, size_t buff_size)
{
- for (auto const& block : private_blocks)
- xbt_assert(block.first <= block.second && block.second <= buff_size, "Oops, bug in shared malloc.");
+ for (auto const& [block_begin, block_end] : private_blocks)
+ xbt_assert(block_begin <= block_end && block_end <= buff_size, "Oops, bug in shared malloc.");
}
static void smpi_cleanup_comm_after_copy(simgrid::kernel::activity::CommImpl* comm, void* buff){
- if (comm->detached()) {
+ if (comm->is_detached()) {
// if this is a detached send, the source buffer was duplicated by SMPI
// sender to make the original buffer available to the application ASAP
xbt_free(buff);
/* nothing done in this version */
}
-int smpi_enabled() {
- return MPI_COMM_WORLD != MPI_COMM_UNINITIALIZED;
-}
-
static void smpi_init_papi()
{
#if HAVE_PAPI
std::string unit_name = *(event_tokens.begin());
papi_process_data config = {.counter_data = std::move(counters2values), .event_set = event_set};
- units2papi_setup.insert(std::make_pair(unit_name, std::move(config)));
+ units2papi_setup.try_emplace(unit_name, std::move(config));
}
#endif
}
const std::vector<std::string>& args)
{
// copy C strings, we need them writable
- auto* args4argv = new std::vector<char*>(args.size());
- std::transform(begin(args), end(args), begin(*args4argv), [](const std::string& s) { return xbt_strdup(s.c_str()); });
+ std::vector<char*> args4argv(args.size());
+ std::transform(begin(args) + 1, end(args), begin(args4argv) + 1,
+ [](const std::string& s) { return xbt_strdup(s.c_str()); });
// set argv[0] to executable_path
- xbt_free((*args4argv)[0]);
- (*args4argv)[0] = xbt_strdup(executable_path.c_str());
+ args4argv[0] = xbt_strdup(executable_path.c_str());
+ // add the final NULL
+ args4argv.push_back(nullptr);
-#if !SMPI_IFORT
// take a copy of args4argv to keep reference of the allocated strings
- const std::vector<char*> args2str(*args4argv);
-#endif
- int argc = static_cast<int>(args4argv->size());
- args4argv->push_back(nullptr);
- char** argv = args4argv->data();
-
-#if SMPI_IFORT
- for_rtl_init_ (&argc, argv);
-#elif SMPI_FLANG
- __io_set_argc(argc);
- __io_set_argv(argv);
-#elif SMPI_GFORTRAN
- _gfortran_set_args(argc, argv);
-#endif
+ const std::vector<char*> args2str(args4argv);
try {
+ int argc = static_cast<int>(args4argv.size() - 1);
+ char** argv = args4argv.data();
int res = entry_point(argc, argv);
if (res != 0) {
XBT_WARN("SMPI process did not return 0. Return value : %d", res);
XBT_DEBUG("Caught a ForcefulKillException: %s", e.what());
}
-#if SMPI_IFORT
- for_rtl_finish_ ();
-#else
for (char* s : args2str)
xbt_free(s);
- delete args4argv;
-#endif
return 0;
}
-
-// TODO, remove the number of functions involved here
static smpi_entry_point_type smpi_resolve_function(void* handle)
{
- auto* entry_point_fortran = reinterpret_cast<smpi_fortran_entry_point_type>(dlsym(handle, "user_main_"));
- if (entry_point_fortran != nullptr) {
+ if (auto* entry_point_fortran = reinterpret_cast<smpi_fortran_entry_point_type>(dlsym(handle, "user_main_"))) {
return [entry_point_fortran](int, char**) {
entry_point_fortran();
return 0;
};
}
- auto* entry_point = reinterpret_cast<smpi_c_entry_point_type>(dlsym(handle, "main"));
- if (entry_point != nullptr) {
+ if (auto* entry_point = reinterpret_cast<smpi_c_entry_point_type>(dlsym(handle, "main"))) {
return entry_point;
}
{
auto* libname = static_cast<std::string*>(data);
std::string path = info->dlpi_name;
- if (path.find(*libname) != std::string::npos) {
- *libname = std::move(path);
- return 1;
- }
- return 0;
+ if (path.find(*libname) == std::string::npos)
+ return 0;
+
+ *libname = std::move(path);
+ return 1;
}
#endif
stat(executable.c_str(), &fdin_stat);
off_t fdin_size = fdin_stat.st_size;
- std::string libnames = simgrid::config::get_value<std::string>("smpi/privatize-libs");
- if (not libnames.empty()) {
+ if (std::string libnames = simgrid::config::get_value<std::string>("smpi/privatize-libs"); not libnames.empty()) {
// split option
std::vector<std::string> privatize_libs;
boost::split(privatize_libs, libnames, boost::is_any_of(";"));
simgrid::smpi::colls::set_collectives();
simgrid::smpi::colls::smpi_coll_cleanup_callback = nullptr;
+ std::vector<char*> args4argv(argv + 1, argv + argc + 1); // last element is NULL
+ args4argv[0] = xbt_strdup(executable);
+ int real_argc = argc - 1;
+ char** real_argv = args4argv.data();
+
+ // Setup argc/argv for the Fortran run-time environment
+#if SMPI_IFORT
+ for_rtl_init_(&real_argc, real_argv);
+#elif SMPI_FLANG
+ __io_set_argc(real_argc);
+ __io_set_argv(real_argv);
+#elif SMPI_GFORTRAN
+ _gfortran_set_args(real_argc, real_argv);
+#endif
+
SMPI_init();
- const std::vector<const char*> args(argv + 2, argv + argc);
+ const std::vector<const char*> args(real_argv + 1, real_argv + real_argc);
int rank_counts =
smpi_deployment_smpirun(&engine, smpi_hostfile.get(), smpi_np.get(), smpi_replay.get(), smpi_map.get(), args);
fflush(stdout);
fflush(stderr);
- if (MC_is_active()) {
- MC_run();
- } else {
- engine.get_impl()->run();
+ engine.get_impl()->run(-1);
+
+ xbt_os_walltimer_stop(global_timer);
+ simgrid::smpi::utils::print_time_analysis(xbt_os_timer_elapsed(global_timer));
- xbt_os_walltimer_stop(global_timer);
- simgrid::smpi::utils::print_time_analysis(xbt_os_timer_elapsed(global_timer));
- }
SMPI_finalize();
+#if SMPI_IFORT
+ for_rtl_finish_();
+#endif
+ xbt_free(args4argv[0]);
+
return smpi_exit_status;
}
+int SMPI_is_inited()
+{
+ return MPI_COMM_WORLD != MPI_COMM_UNINITIALIZED;
+}
+
// Called either directly from the user code, or from the code called by smpirun
void SMPI_init(){
smpi_init_options_internal(false);
- simgrid::s4u::Actor::on_creation.connect([](simgrid::s4u::Actor& actor) {
+ simgrid::s4u::Actor::on_creation_cb([](simgrid::s4u::Actor& actor) {
if (not actor.is_daemon())
actor.extension_set<simgrid::smpi::ActorExt>(new simgrid::smpi::ActorExt(&actor));
});
- simgrid::s4u::Host::on_creation.connect(
+ simgrid::s4u::Host::on_creation_cb(
[](simgrid::s4u::Host& host) { host.extension_set(new simgrid::smpi::Host(&host)); });
for (auto const& host : simgrid::s4u::Engine::get_instance()->get_all_hosts())
host->extension_set(new simgrid::smpi::Host(host));
smpi_bench_destroy();
smpi_shared_destroy();
smpi_deployment_cleanup_instances();
+ smpi_cleanup_op_cost_callback();
if (simgrid::smpi::colls::smpi_coll_cleanup_callback != nullptr)
simgrid::smpi::colls::smpi_coll_cleanup_callback();
smpi_init_fortran_types();
if(_smpi_init_sleep > 0)
simgrid::s4u::this_actor::sleep_for(_smpi_init_sleep);
- smpi_deployment_startup_barrier(smpi_process()->get_instance_id());
+ if (not MC_is_active()) {
+ smpi_deployment_startup_barrier(smpi_process()->get_instance_id());
+ }
}
void SMPI_thread_create() {