host->data = data;
}
-smx_action_t SIMIX_host_execute(const char *name, smx_host_t host,
- double computation_amount,
- double priority)
+smx_action_t SIMIX_host_execute(u_smx_scalar_t args[])
{
+ const char *name = args[0].p;
+ smx_host_t host = args[1].p;
+ double computation_amount = args[2].d;
+ double priority = args[3].d;
+
/* alloc structures and initialize */
smx_action_t action = xbt_mallocator_get(simix_global->action_mallocator);
action->type = SIMIX_ACTION_EXECUTE;
double SIMIX_host_get_speed(smx_host_t host);
double SIMIX_host_get_available_speed(smx_host_t host);
int SIMIX_host_get_state(smx_host_t host);
-smx_action_t SIMIX_host_execute(const char *name,
- smx_host_t host, double computation_amount, double priority);
+smx_action_t SIMIX_host_execute(u_smx_scalar_t args[]);
smx_action_t SIMIX_host_parallel_execute(const char *name,
int host_nb, smx_host_t *host_list,
double *computation_amount, double *communication_amount,
return NULL;
}
} else {
- return SIMIX_host_execute("suspend", process->smx_host, 0.0, 1.0);
+ SIMIX_simcall(SIMCALL_HOST_EXECUTE, PTR("suspend"), PTR(process->smx_host), DOUBLE(0.0), DOUBLE(1.0));
+ return process->simcall.host_execute.result;
}
}
break;
case SIMCALL_HOST_EXECUTE:
- simcall->host_execute.result = SIMIX_host_execute(
- simcall->host_execute.name,
- simcall->host_execute.host,
- simcall->host_execute.computation_amount,
- simcall->host_execute.priority);
+ simcall->host_execute.result = simcall_table[simcall->call](simcall->args);
SIMIX_simcall_answer(simcall);
break;
/* New Simcal interface */
/* FIXME: add types for every simcall */
-const char *simcall_types[NUM_SIMCALLS] = {"%d", "%d%f", "%l"};
+const char *simcall_types[NUM_SIMCALLS] = { [SIMCALL_HOST_EXECUTE] = "%s%p%f%f%p" };
+
+simcall_handler_t simcall_table[NUM_SIMCALLS] = {[SIMCALL_HOST_EXECUTE] = &SIMIX_host_execute};
void SIMIX_simcall_typecheck(const char *fmt, ...)
{
return;
}
+void __SIMIX_simcall(e_smx_simcall_t simcall_id, u_smx_scalar_t *args)
+{
+ smx_process_t self = SIMIX_process_self();
+ self->simcall.call = simcall_id;
+ self->simcall.args = args;
+
+ if (self != simix_global->maestro_process) {
+ XBT_DEBUG("Yield process '%s' on simcall %s (%d)", self->name,
+ SIMIX_simcall_name(self->simcall.call), (int)self->simcall.call);
+
+ SIMIX_process_yield(self);
+ } else {
+
+ SIMIX_simcall_pre(&self->simcall, 0);
+ }
+}
typedef struct s_smx_simcall {
e_smx_simcall_t call;
smx_process_t issuer;
+ union u_smx_scalar *args;
+ //FIXME: union u_smx_scalar retval;
union {
/*************************** New simcall interface ****************************/
/* Pack all possible scalar types in an union */
-typedef union {
+typedef union u_smx_scalar {
char c;
short s;
int i;
#define DOUBLE(x) (d,x)
#define PTR(x) (p,x)
+#define MYMACRO(...)
+
/*
* Some macro machinery to get a MAP over the arguments of a variadic macro.
* It uses a FOLD to apply a macro to every argument, and because there is
/* Generate code to initialize the field 'x' with value 'y' of an structure or union */
#define INIT_FIELD_(x,y) {.x = y}
-#define INIT_FIELD(t) INIT_FIELD t
+#define INIT_FIELD(t) INIT_FIELD_ t
/* Project the second element of a tuple */
#define SECOND_(x, y) y
*/
#define SIMIX_simcall(id, ...) \
SIMIX_simcall_typecheck(simcall_types[id], MAP(SECOND, __VA_ARGS__)); \
- __SIMIX_simcall(id, (mytype_t[]){MAP(INIT_FIELD, __VA_ARGS__)})
+ __SIMIX_simcall(id, (u_smx_scalar_t[]){MAP(INIT_FIELD, __VA_ARGS__)})
void __SIMIX_simcall(e_smx_simcall_t simcall_id, u_smx_scalar_t *args);
*/
void SIMIX_simcall_typecheck(const char *fmt, ...) __attribute__ ((format (printf, 1, 2)));
+typedef smx_action_t (*simcall_handler_t)(u_smx_scalar_t *);
+
+extern const char *simcall_types[];
+extern simcall_handler_t simcall_table[];
#endif
* \param priority computation priority
* \return A new SIMIX execution action
*/
+
smx_action_t simcall_host_execute(const char *name, smx_host_t host,
double computation_amount,
double priority)
simcall->host_execute.host = host;
simcall->host_execute.computation_amount = computation_amount;
simcall->host_execute.priority = priority;
+
if(MC_is_active()) /* Initialize result to NULL for snapshot comparison done during simcall */
simcall->host_execute.result = NULL;
- SIMIX_simcall_push(simcall->issuer);
+
+ SIMIX_simcall(SIMCALL_HOST_EXECUTE, PTR(name), PTR(host), DOUBLE(computation_amount), DOUBLE(priority));
+
return simcall->host_execute.result;
}