Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Biggest commit ever (SIMIX2): the user processes can now run in parallel
[simgrid.git] / src / gras / Virtu / sg_emul.c
1 /* sg_emul - Emulation support (simulation)                                 */
2
3 /* Copyright (c) 2005, 2006, 2007, 2009, 2010. The SimGrid Team.
4  * All rights reserved.                                                     */
5
6 /* This program is free software; you can redistribute it and/or modify it
7  * under the terms of the license (GNU LGPL) which comes with this package. */
8
9 #include <stdio.h>              /* sprintf */
10 #include "gras/emul.h"
11 #include "gras/Virtu/virtu_sg.h"
12 #include "gras_modinter.h"
13
14 #include "xbt/xbt_os_time.h"    /* timers */
15 #include "xbt/dict.h"
16 #include "xbt/ex.h"
17
18 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(gras_virtu_emul, gras_virtu,
19                                 "Emulation support");
20 /*** CPU burning */
21 void gras_cpu_burn(double flops)
22 {
23   smx_action_t execution;
24
25   if (flops > 0){
26     execution = SIMIX_req_host_execute("task", SIMIX_host_self(), flops);
27     SIMIX_req_host_execution_wait(execution);
28   }
29 }
30
31 /*** Timing macros ***/
32 static xbt_os_timer_t timer;
33 static int benchmarking = 0;
34 static xbt_dict_t benchmark_set = NULL;
35 static double reference = .00000000523066250047108838;  /* FIXME: we should benchmark host machine to set this; unit=s/flop */
36 static double duration = 0.0;
37
38 static char *locbuf = NULL;
39 static unsigned int locbufsize;
40
41 void gras_emul_init(void)
42 {
43   if (!benchmark_set) {
44     benchmark_set = xbt_dict_new();
45     timer = xbt_os_timer_new();
46   }
47 }
48
49 void gras_emul_exit(void)
50 {
51   if (locbuf)
52     free(locbuf);
53   xbt_dict_free(&benchmark_set);
54   xbt_os_timer_free(timer);
55 }
56
57
58 static void store_in_dict(xbt_dict_t dict, const char *key, double value)
59 {
60   double *ir;
61
62   ir = xbt_dict_get_or_null(dict, key);
63   if (!ir) {
64     ir = xbt_new0(double, 1);
65     xbt_dict_set(dict, key, ir, xbt_free_f);
66   }
67   *ir = value;
68 }
69
70 static double get_from_dict(xbt_dict_t dict, const char *key)
71 {
72   double *ir = xbt_dict_get(dict, key);
73
74   return *ir;
75 }
76
77 int gras_bench_always_begin(const char *location, int line)
78 {
79   xbt_assert0(!benchmarking, "Already benchmarking");
80   benchmarking = 1;
81
82   if (!timer)
83     xbt_os_timer_start(timer);
84   return 0;
85 }
86
87 int gras_bench_always_end(void)
88 {
89   xbt_assert0(benchmarking, "Not benchmarking yet");
90   benchmarking = 0;
91   xbt_os_timer_stop(timer);
92   duration = xbt_os_timer_elapsed(timer);
93
94   gras_cpu_burn(duration / reference);
95
96   return 0;
97 }
98
99 int gras_bench_once_begin(const char *location, int line)
100 {
101   double *ir = NULL;
102   xbt_assert0(!benchmarking, "Already benchmarking");
103   benchmarking = 1;
104
105   if (!locbuf || locbufsize < strlen(location) + 64) {
106     locbufsize = strlen(location) + 64;
107     locbuf = xbt_realloc(locbuf, locbufsize);
108   }
109   sprintf(locbuf, "%s:%d", location, line);
110
111   ir = xbt_dict_get_or_null(benchmark_set, locbuf);
112   if (!ir) {
113     DEBUG1("%s", locbuf);
114     duration = 1;
115     xbt_os_timer_start(timer);
116     return 1;
117   } else {
118     duration = -1.0;
119     return 0;
120   }
121 }
122
123 int gras_bench_once_end(void)
124 {
125   xbt_assert0(benchmarking, "Not benchmarking yet");
126   benchmarking = 0;
127   if (duration > 0) {
128     xbt_os_timer_stop(timer);
129     duration = xbt_os_timer_elapsed(timer);
130     store_in_dict(benchmark_set, locbuf, duration);
131   } else {
132     duration = get_from_dict(benchmark_set, locbuf);
133   }
134   DEBUG2("Simulate the run of a task of %f sec for %s", duration, locbuf);
135   gras_cpu_burn(duration / reference);
136   return 0;
137 }
138
139
140 /*** Conditional execution support ***/
141
142 int gras_if_RL(void)
143 {
144   return 0;
145 }
146
147 int gras_if_SG(void)
148 {
149   return 1;
150 }