From: Gabriel Corona Date: Wed, 22 Jun 2016 08:35:39 +0000 (+0200) Subject: [simix] More generic mapping between function name and actor code X-Git-Tag: v3_14~892^2~4 X-Git-Url: http://info.iut-bm.univ-fcomte.fr/pub/gitweb/simgrid.git/commitdiff_plain/b9684d3607aa558c95b7185ddf147b478a7e367f [simix] More generic mapping between function name and actor code It was only possible to associate main() style function to function names. Now we can associate any kind of function which will be useful in order for S4U-style code registration. --- diff --git a/include/simgrid/msg.h b/include/simgrid/msg.h index 27594822dd..681572d9b2 100644 --- a/include/simgrid/msg.h +++ b/include/simgrid/msg.h @@ -197,7 +197,6 @@ XBT_PUBLIC(msg_error_t) MSG_main(void); XBT_PUBLIC(void) MSG_function_register(const char *name, xbt_main_func_t code); XBT_PUBLIC(void) MSG_function_register_default(xbt_main_func_t code); -XBT_PUBLIC(xbt_main_func_t) MSG_get_registered_function(const char *name); XBT_PUBLIC(void) MSG_launch_application(const char *file); /*Bypass the parser */ XBT_PUBLIC(void) MSG_set_function(const char *host_id, diff --git a/include/simgrid/simix.h b/include/simgrid/simix.h index 9beaaf80c3..87ba0bc851 100644 --- a/include/simgrid/simix.h +++ b/include/simgrid/simix.h @@ -177,7 +177,6 @@ XBT_PUBLIC(void) SIMIX_create_environment(const char *file); XBT_PUBLIC(void) SIMIX_function_register(const char *name, xbt_main_func_t code); XBT_PUBLIC(void) SIMIX_function_register_default(xbt_main_func_t code); -XBT_PUBLIC(xbt_main_func_t) SIMIX_get_registered_function(const char *name); XBT_PUBLIC(void) SIMIX_init_application(void); XBT_PUBLIC(void) SIMIX_launch_application(const char *file); diff --git a/src/mc/mc_smx.cpp b/src/mc/mc_smx.cpp index daf6b83ab8..b7135d6a59 100644 --- a/src/mc/mc_smx.cpp +++ b/src/mc/mc_smx.cpp @@ -84,7 +84,7 @@ void Process::refresh_simix() this->read_variable("simix_global", &simix_global_p, sizeof(simix_global_p)); // simix_global = REMOTE(*simix_global) - s_smx_global_t simix_global; + simgrid::simix::Global simix_global; this->read_bytes(&simix_global, sizeof(simix_global), remote(simix_global_p)); diff --git a/src/msg/msg_deployment.cpp b/src/msg/msg_deployment.cpp index af82087e81..015d748e8c 100644 --- a/src/msg/msg_deployment.cpp +++ b/src/msg/msg_deployment.cpp @@ -52,18 +52,6 @@ void MSG_function_register_default(xbt_main_func_t code) SIMIX_function_register_default(code); } -/** \ingroup msg_simulation - * \brief Retrieves a registered main function - * - * Registers a code function in a global table. - * This table is then used by #MSG_launch_application. - * \param name the reference name of the function. - */ -xbt_main_func_t MSG_get_registered_function(const char *name) -{ - return SIMIX_get_registered_function(name); -} - /** * \brief register functions bypassing the parser */ diff --git a/src/simix/smx_deployment.cpp b/src/simix/smx_deployment.cpp index 44ccbb8956..b5e84b1669 100644 --- a/src/simix/smx_deployment.cpp +++ b/src/simix/smx_deployment.cpp @@ -56,6 +56,14 @@ void SIMIX_launch_application(const char *file) } } +// Wrap a main() function into a ActorCodeFactory: +static simgrid::simix::ActorCodeFactory toActorCodeFactory(xbt_main_func_t code) +{ + return [code](simgrid::xbt::args args) { + return simgrid::xbt::wrapMain(code, std::move(args)); + }; +} + /** * \brief Registers a #xbt_main_func_t code in a global table. * @@ -66,11 +74,11 @@ void SIMIX_launch_application(const char *file) */ void SIMIX_function_register(const char *name, xbt_main_func_t code) { - xbt_assert(simix_global, "SIMIX_global_init has to be called before SIMIX_function_register."); - xbt_dict_set(simix_global->registered_functions, name, (void*) code, nullptr); + xbt_assert(simix_global, + "SIMIX_global_init has to be called before SIMIX_function_register."); + simix_global->registered_functions[name] = toActorCodeFactory(code); } -static xbt_main_func_t default_function = nullptr; /** * \brief Registers a #xbt_main_func_t code as default value. * @@ -80,8 +88,7 @@ static xbt_main_func_t default_function = nullptr; void SIMIX_function_register_default(xbt_main_func_t code) { xbt_assert(simix_global, "SIMIX_global_init has to be called before SIMIX_function_register."); - - default_function = code; + simix_global->default_function = toActorCodeFactory(code); } /** @@ -92,17 +99,18 @@ void SIMIX_function_register_default(xbt_main_func_t code) * \param name the reference name of the function. * \return The #smx_process_t or nullptr. */ -xbt_main_func_t SIMIX_get_registered_function(const char *name) +simgrid::simix::ActorCodeFactory& SIMIX_get_actor_code_factory(const char *name) { - xbt_main_func_t res = nullptr; xbt_assert(simix_global, - "SIMIX_global_init has to be called before SIMIX_get_registered_function."); + "SIMIX_global_init has to be called before SIMIX_get_actor_code_factory."); - res = (xbt_main_func_t)xbt_dict_get_or_null(simix_global->registered_functions, name); - return res ? res : default_function; + auto i = simix_global->registered_functions.find(name); + if (i == simix_global->registered_functions.end()) + return simix_global->default_function; + else + return i->second; } - /** * \brief Bypass the parser, get arguments, and set function to each process */ @@ -132,14 +140,14 @@ void SIMIX_process_set_function(const char *process_host, } process.argv[process.argc] = nullptr; - xbt_main_func_t parse_code = SIMIX_get_registered_function(process_function); + // Check we know how to handle this function name: + simgrid::simix::ActorCodeFactory& parse_code = SIMIX_get_actor_code_factory(process_function); xbt_assert(parse_code, "Function '%s' unknown", process_function); - process.function = process_function; + process.function = process_function; process.host = process_host; process.kill_time = process_kill_time; process.start_time = process_start_time; process.on_failure = SURF_PROCESS_ON_FAILURE_DIE; - sg_platf_new_process(&process); } diff --git a/src/simix/smx_global.cpp b/src/simix/smx_global.cpp index ab8d5956ad..6549bdba26 100644 --- a/src/simix/smx_global.cpp +++ b/src/simix/smx_global.cpp @@ -44,7 +44,7 @@ XBT_LOG_NEW_CATEGORY(simix, "All SIMIX categories"); XBT_LOG_NEW_DEFAULT_SUBCATEGORY(simix_kernel, simix, "Logging specific to SIMIX (kernel)"); -smx_global_t simix_global = nullptr; +std::unique_ptr simix_global; static xbt_heap_t simix_timers = nullptr; /** @brief Timer datatype */ @@ -194,17 +194,14 @@ void SIMIX_global_init(int *argc, char **argv) #endif if (!simix_global) { - simix_global = xbt_new0(s_smx_global_t, 1); + simix_global = std::unique_ptr(new simgrid::simix::Global()); simgrid::simix::Process proc; simix_global->process_to_run = xbt_dynar_new(sizeof(smx_process_t), nullptr); simix_global->process_that_ran = xbt_dynar_new(sizeof(smx_process_t), nullptr); simix_global->process_list = xbt_swag_new(xbt_swag_offset(proc, process_hookup)); simix_global->process_to_destroy = xbt_swag_new(xbt_swag_offset(proc, destroy_hookup)); - simix_global->maestro_process = nullptr; - simix_global->registered_functions = xbt_dict_new_homogeneous(nullptr); - simix_global->create_process_function = &SIMIX_process_create; simix_global->kill_process_function = &kill_process; simix_global->cleanup_process_function = &SIMIX_process_cleanup; @@ -299,7 +296,6 @@ void SIMIX_clean(void) xbt_swag_free(simix_global->process_list); simix_global->process_list = nullptr; simix_global->process_to_destroy = nullptr; - xbt_dict_free(&(simix_global->registered_functions)); xbt_os_mutex_destroy(simix_global->mutex); simix_global->mutex = nullptr; @@ -315,9 +311,7 @@ void SIMIX_clean(void) surf_exit(); - xbt_free(simix_global); simix_global = nullptr; - return; } diff --git a/src/simix/smx_private.h b/src/simix/smx_private.h index feb99909eb..6906a08b6d 100644 --- a/src/simix/smx_private.h +++ b/src/simix/smx_private.h @@ -8,6 +8,10 @@ #define _SIMIX_PRIVATE_H #include +#include +#include + +#include #include "src/internal_config.h" #include "simgrid/simix.h" @@ -58,26 +62,46 @@ typedef struct s_smx_context_factory *smx_context_factory_t; #endif -SG_BEGIN_DECL() - /********************************** Simix Global ******************************/ -typedef struct s_smx_global { - smx_context_factory_t context_factory; - xbt_dynar_t process_to_run; - xbt_dynar_t process_that_ran; - xbt_swag_t process_list; - xbt_swag_t process_to_destroy; - smx_process_t maestro_process; - xbt_dict_t registered_functions; - smx_creation_func_t create_process_function; - void_pfn_smxprocess_t kill_process_function; + +namespace simgrid { +namespace simix { + +// What's executed as SIMIX actor code: +typedef std::function ActorCode; + +// Create ActorCode based on argv: +typedef std::function ActorCodeFactory; + +class Global { +public: + smx_context_factory_t context_factory = nullptr; + xbt_dynar_t process_to_run = nullptr; + xbt_dynar_t process_that_ran = nullptr; + xbt_swag_t process_list = nullptr; + xbt_swag_t process_to_destroy = nullptr; + smx_process_t maestro_process = nullptr; + + // Maps function names to actor code: + std::unordered_map registered_functions; + + // This might be used when no corresponding function name is registered: + simgrid::simix::ActorCodeFactory default_function; + + smx_creation_func_t create_process_function = nullptr; + void_pfn_smxprocess_t kill_process_function = nullptr; /** Callback used when killing a SMX_process */ - void_pfn_smxprocess_t cleanup_process_function; + void_pfn_smxprocess_t cleanup_process_function = nullptr; + xbt_os_mutex_t mutex = nullptr; +}; - xbt_os_mutex_t mutex; -} s_smx_global_t, *smx_global_t; +} +} + +SG_BEGIN_DECL() + +XBT_PUBLIC_DATA(std::unique_ptr) simix_global; -XBT_PUBLIC_DATA(smx_global_t) simix_global; extern XBT_PRIVATE unsigned long simix_process_maxpid; XBT_PUBLIC(void) SIMIX_clean(void); @@ -153,6 +177,8 @@ XBT_PRIVATE void SIMIX_post_create_environment(void); // FIXME, Dirty hack for SMPI+MSG XBT_PRIVATE void SIMIX_process_set_cleanup_function(smx_process_t process, void_pfn_smxprocess_t cleanup); +XBT_PRIVATE simgrid::simix::ActorCodeFactory& SIMIX_get_actor_code_factory(const char *name); + SG_END_DECL() #endif diff --git a/src/surf/sg_platf.cpp b/src/surf/sg_platf.cpp index 036b9ca4a7..7b85965e5d 100644 --- a/src/surf/sg_platf.cpp +++ b/src/surf/sg_platf.cpp @@ -570,14 +570,14 @@ void sg_platf_new_process(sg_platf_process_cbarg_t process) msg->data[msg->used-3]='\0'; xbt_die("%s", msg->data); } - xbt_main_func_t parse_code = SIMIX_get_registered_function(process->function); - xbt_assert(parse_code, "Function '%s' unknown", process->function); + simgrid::simix::ActorCodeFactory& factory = SIMIX_get_actor_code_factory(process->function); + xbt_assert(factory, "Function '%s' unknown", process->function); double start_time = process->start_time; double kill_time = process->kill_time; int auto_restart = process->on_failure == SURF_PROCESS_ON_FAILURE_DIE ? 0 : 1; - std::function code = simgrid::xbt::wrapMain(parse_code, process->argc, process->argv); + std::function code = factory(simgrid::xbt::args(process->argc, process->argv)); smx_process_arg_t arg = nullptr; smx_process_t process_created = nullptr;