Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
Factorize some code in SURF
[simgrid.git] / src / surf / surf_timer.c
1 /*      $Id$     */
2
3 /* Copyright (c) 2005 Arnaud Legrand. All rights reserved.                  */
4
5 /* This program is free software; you can redistribute it and/or modify it
6  * under the terms of the license (GNU LGPL) which comes with this package. */
7
8 #include "xbt/ex.h"
9 #include "surf_timer_private.h"
10
11 XBT_LOG_NEW_DEFAULT_SUBCATEGORY(surf_timer, surf,
12                                 "Logging specific to SURF (timer)");
13
14 surf_timer_model_t surf_timer_model = NULL;
15 static tmgr_trace_t empty_trace = NULL;
16 static xbt_swag_t command_pending = NULL;
17 static xbt_swag_t command_to_run = NULL;
18 static xbt_heap_t timer_heap = NULL;
19
20 static void timer_free(void *timer)
21 {
22   free(timer);
23 }
24
25 static command_t command_new(void *fun, void *args)
26 {
27   command_t command = xbt_new0(s_command_t, 1);
28
29   command->model = (surf_model_t) surf_timer_model;
30   command->function = fun;
31   command->args = args;
32   xbt_swag_insert(command, command_pending);
33   return command;
34 }
35
36 static void command_free(command_t command)
37 {
38   free(command);
39
40   if (xbt_swag_belongs(command, command_to_run)) {
41     xbt_swag_remove(command, command_to_run);
42   } else if (xbt_swag_belongs(command, command_pending)) {
43     xbt_swag_remove(command, command_pending);
44   }
45   return;
46 }
47
48 static void parse_timer(void)
49 {
50 }
51
52 static void parse_file(const char *file)
53 {
54 }
55
56 static void *name_service(const char *name)
57 {
58   DIE_IMPOSSIBLE;
59   return NULL;
60 }
61
62 static const char *get_resource_name(void *resource_id)
63 {
64   DIE_IMPOSSIBLE;
65   return "";
66 }
67
68 static int resource_used(void *resource_id)
69 {
70   return 1;
71 }
72
73 static void action_change_state(surf_action_t action,
74                                 e_surf_action_state_t state)
75 {
76   DIE_IMPOSSIBLE;
77   return;
78 }
79
80 static double share_resources(double now)
81 {
82   if (xbt_heap_size(timer_heap))
83     return (xbt_heap_maxkey(timer_heap));
84   else
85     return -1.0;
86 }
87
88 static void update_actions_state(double now, double delta)
89 {
90   if (xbt_heap_size(timer_heap)) {
91     if (xbt_heap_maxkey(timer_heap) <= now + delta) {
92       xbt_heap_pop(timer_heap);
93     }
94   }
95   return;
96 }
97
98 static void update_resource_state(void *id,
99                                   tmgr_trace_event_t event_type,
100                                   double value, double date)
101 {
102   command_t command = id;
103
104   /* Move this command to the list of commands to execute */
105   xbt_swag_remove(command, command_pending);
106   xbt_swag_insert(command, command_to_run);
107
108   return;
109 }
110
111 static void set(double date, void *function, void *arg)
112 {
113   command_t command = NULL;
114
115   command = command_new(function, arg);
116
117   tmgr_history_add_trace(history, empty_trace, date, 0, command);
118   xbt_heap_push(timer_heap, NULL, date);
119 }
120
121
122 static int get(void **function, void **arg)
123 {
124   command_t command = NULL;
125
126   command = xbt_swag_extract(command_to_run);
127   if (command) {
128     *function = command->function;
129     *arg = command->args;
130     return 1;
131   } else {
132     return 0;
133   }
134 }
135
136 static void action_suspend(surf_action_t action)
137 {
138   DIE_IMPOSSIBLE;
139 }
140
141 static void action_resume(surf_action_t action)
142 {
143   DIE_IMPOSSIBLE;
144 }
145
146 static int action_is_suspended(surf_action_t action)
147 {
148   DIE_IMPOSSIBLE;
149   return 0;
150 }
151
152 static void finalize(void)
153 {
154   xbt_heap_free(timer_heap);
155   timer_heap = NULL;
156
157   tmgr_trace_free(empty_trace);
158   empty_trace = NULL;
159
160   xbt_swag_free(command_pending);
161   xbt_swag_free(command_to_run);
162
163   surf_model_exit((surf_model_t)surf_timer_model);
164
165   free(surf_timer_model->extension_public);
166
167   free(surf_timer_model);
168   surf_timer_model = NULL;
169 }
170
171 static void surf_timer_model_init_internal(void)
172 {
173   surf_timer_model = xbt_new0(s_surf_timer_model_t, 1);
174
175   surf_model_init((surf_model_t)surf_timer_model);
176
177   surf_timer_model->extension_public =
178     xbt_new0(s_surf_timer_model_extension_public_t, 1);
179
180   surf_timer_model->common_public.name_service = name_service;
181   surf_timer_model->common_public.get_resource_name = get_resource_name;
182   surf_timer_model->common_public.action_get_state = surf_action_get_state;
183   surf_timer_model->common_public.action_change_state = action_change_state;
184   surf_timer_model->common_public.action_set_data = surf_action_set_data;
185   surf_timer_model->common_public.name = "TIMER";
186
187   surf_timer_model->common_private->resource_used = resource_used;
188   surf_timer_model->common_private->share_resources = share_resources;
189   surf_timer_model->common_private->update_actions_state =
190     update_actions_state;
191   surf_timer_model->common_private->update_resource_state =
192     update_resource_state;
193   surf_timer_model->common_private->finalize = finalize;
194
195   surf_timer_model->common_public.suspend = action_suspend;
196   surf_timer_model->common_public.resume = action_resume;
197   surf_timer_model->common_public.is_suspended = action_is_suspended;
198
199   surf_timer_model->extension_public->set = set;
200   surf_timer_model->extension_public->get = get;
201
202   {
203     s_command_t var;
204     command_pending = xbt_swag_new(xbt_swag_offset(var, command_set_hookup));
205     command_to_run = xbt_swag_new(xbt_swag_offset(var, command_set_hookup));
206   }
207
208   empty_trace = tmgr_empty_trace_new();
209   timer_heap = xbt_heap_new(8, NULL);
210 }
211
212 void surf_timer_model_init(const char *filename)
213 {
214   if (surf_timer_model)
215     return;
216   surf_timer_model_init_internal();
217   xbt_dynar_push(model_list, &surf_timer_model);
218 }