1 /* This file is part of the Linux Trace Toolkit viewer
2 * Copyright (C) 2009 Benjamin Poirier <benjamin.poirier@polymtl.ca>
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License Version 2 as
6 * published by the Free Software Foundation;
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
13 * You should have received a copy of the GNU General Public License
14 * along with this program; if not, write to the Free Software
15 * Foundation, Inc., 59 Temple Place - Suite 330, Boston,
27 #include "event_analysis.h"
28 #include "sync_chain.h"
30 #include "event_matching_distributor.h"
36 GQueue
* matchingModules
;
42 /* Offset whithin Matching module of the field* containing the function
49 // Functions common to all matching modules
50 static void initMatchingDistributor(SyncState
* const syncState
);
51 static void destroyMatchingDistributor(SyncState
* const syncState
);
53 static void matchEventDistributor(SyncState
* const syncState
, Event
* const
55 static GArray
* finalizeMatchingDistributor(SyncState
* const syncState
);
56 static void printMatchingStatsDistributor(SyncState
* const syncState
);
57 static void writeMatchingTraceTracePlotsDistributor(SyncState
* const
58 syncState
, const unsigned int i
, const unsigned int j
);
59 static void writeMatchingTraceTraceOptionsDistributor(SyncState
* const
60 syncState
, const unsigned int i
, const unsigned int j
);
61 static void writeMatchingTraceTimePlotsDistributor(SyncState
* const
62 syncState
, const unsigned int i
, const unsigned int j
);
63 static void writeMatchingTraceTimeOptionsDistributor(SyncState
* const
64 syncState
, const unsigned int i
, const unsigned int j
);
66 // Functions specific to this module
67 static void registerMatchingDistributor() __attribute__((constructor (101)));
69 void gfInitModule(gpointer data
, gpointer user_data
);
70 void gfDestroyModule(gpointer data
, gpointer user_data
);
71 void gfMatchEvent(gpointer data
, gpointer user_data
);
72 void gfFinalize(gpointer data
, gpointer user_data
);
73 void gfPrintStats(gpointer data
, gpointer user_data
);
74 void gfGraphFunctionCall(gpointer data
, gpointer user_data
);
77 static MatchingModule matchingModuleDistributor
= {
81 .initMatching
= &initMatchingDistributor
,
82 .destroyMatching
= &destroyMatchingDistributor
,
83 .matchEvent
= &matchEventDistributor
,
84 .finalizeMatching
= &finalizeMatchingDistributor
,
85 .printMatchingStats
= &printMatchingStatsDistributor
,
87 .writeTraceTracePlots
= &writeMatchingTraceTracePlotsDistributor
,
88 .writeTraceTraceOptions
= &writeMatchingTraceTraceOptionsDistributor
,
89 .writeTraceTimePlots
= &writeMatchingTraceTimePlotsDistributor
,
90 .writeTraceTimeOptions
= &writeMatchingTraceTimeOptionsDistributor
,
96 * Matching module registering function
98 static void registerMatchingDistributor()
100 g_queue_push_tail(&matchingModules
, &matchingModuleDistributor
);
105 * Matching init function
107 * This function is called at the beginning of a synchronization run for a set
110 * Build the list and initialize other matching Modules
113 * syncState container for synchronization data.
115 static void initMatchingDistributor(SyncState
* const syncState
)
117 MatchingDataDistributor
* matchingData
;
119 matchingData
= malloc(sizeof(MatchingDataDistributor
));
120 syncState
->matchingData
= matchingData
;
122 matchingData
->distributedModules
= g_queue_new();
123 g_queue_foreach(&matchingModules
, &gfInitModule
, &(struct InitAggregate
)
124 {syncState
, matchingData
->distributedModules
});
129 * Matching destroy function
131 * Destroy other modules and free the matching specific data structures
134 * syncState container for synchronization data.
136 static void destroyMatchingDistributor(SyncState
* const syncState
)
138 MatchingDataDistributor
* matchingData
= syncState
->matchingData
;
140 g_queue_foreach(matchingData
->distributedModules
, &gfDestroyModule
, NULL
);
142 g_queue_clear(matchingData
->distributedModules
);
143 free(syncState
->matchingData
);
144 syncState
->matchingData
= NULL
;
150 * Copy event and distribute to matching modules
153 * syncState container for synchronization data.
154 * event new event to match
156 static void matchEventDistributor(SyncState
* const syncState
, Event
* const event
)
158 MatchingDataDistributor
* matchingData
= syncState
->matchingData
;
160 g_queue_foreach(matchingData
->distributedModules
, &gfMatchEvent
, event
);
161 event
->destroy(event
);
166 * Call the distributed finalization functions and return identity factors
169 * syncState container for synchronization data.
172 * Factors[traceNb] identity factors for each trace
174 static GArray
* finalizeMatchingDistributor(SyncState
* const syncState
)
178 MatchingDataDistributor
* matchingData
= syncState
->matchingData
;
180 g_queue_foreach(matchingData
->distributedModules
, &gfFinalize
, NULL
);
182 factors
= g_array_sized_new(FALSE
, FALSE
, sizeof(Factors
),
184 g_array_set_size(factors
, syncState
->traceNb
);
185 for (i
= 0; i
< syncState
->traceNb
; i
++)
189 e
= &g_array_index(factors
, Factors
, i
);
199 * Call the distributed statistics functions (when they exist). Must be called
200 * after finalizeMatching.
203 * syncState container for synchronization data.
205 static void printMatchingStatsDistributor(SyncState
* const syncState
)
207 MatchingDataDistributor
* matchingData
= syncState
->matchingData
;
209 g_queue_foreach(matchingData
->distributedModules
, &gfPrintStats
, NULL
);
214 * Call the distributed graph lines functions (when they exist).
217 * syncState: container for synchronization data
218 * i: first trace number
219 * j: second trace number, garanteed to be larger than i
221 static void writeMatchingTraceTracePlotsDistributor(SyncState
* const
222 syncState
, const unsigned int i
, const unsigned int j
)
224 MatchingDataDistributor
* matchingData
= syncState
->matchingData
;
226 g_queue_foreach(matchingData
->distributedModules
, &gfGraphFunctionCall
,
227 &(struct GraphAggregate
) {offsetof(MatchingModule
,
228 graphFunctions
.writeTraceTracePlots
), i
, j
});
233 * Call the distributed graph lines functions (when they exist).
236 * syncState: container for synchronization data
237 * i: first trace number
238 * j: second trace number, garanteed to be larger than i
240 static void writeMatchingTraceTimePlotsDistributor(SyncState
* const
241 syncState
, const unsigned int i
, const unsigned int j
)
243 MatchingDataDistributor
* matchingData
= syncState
->matchingData
;
245 g_queue_foreach(matchingData
->distributedModules
, &gfGraphFunctionCall
,
246 &(struct GraphAggregate
) {offsetof(MatchingModule
,
247 graphFunctions
.writeTraceTimePlots
), i
, j
});
252 * Call the distributed graph options functions (when they exist).
255 * syncState: container for synchronization data
256 * i: first trace number
257 * j: second trace number, garanteed to be larger than i
259 static void writeMatchingTraceTraceOptionsDistributor(SyncState
* const syncState
,
260 const unsigned int i
, const unsigned int j
)
262 MatchingDataDistributor
* matchingData
= syncState
->matchingData
;
264 g_queue_foreach(matchingData
->distributedModules
, &gfGraphFunctionCall
,
265 &(struct GraphAggregate
) {offsetof(MatchingModule
,
266 graphFunctions
.writeTraceTraceOptions
), i
, j
});
271 * Call the distributed graph options functions (when they exist).
274 * syncState: container for synchronization data
275 * i: first trace number
276 * j: second trace number, garanteed to be larger than i
278 static void writeMatchingTraceTimeOptionsDistributor(SyncState
* const syncState
,
279 const unsigned int i
, const unsigned int j
)
281 MatchingDataDistributor
* matchingData
= syncState
->matchingData
;
283 g_queue_foreach(matchingData
->distributedModules
, &gfGraphFunctionCall
,
284 &(struct GraphAggregate
) {offsetof(MatchingModule
,
285 graphFunctions
.writeTraceTimeOptions
), i
, j
});
290 * A GFunc for g_queue_foreach()
292 * Add and initialize matching module
295 * data MatchingModule*, module to add
296 * user_data InitAggregate*
298 void gfInitModule(gpointer data
, gpointer user_data
)
300 SyncState
* parallelSS
;
301 struct InitAggregate
* aggregate
= user_data
;
302 MatchingModule
* matchingModule
= data
;
304 if (strcmp(matchingModule
->name
, matchingModuleDistributor
.name
) == 0)
309 parallelSS
= malloc(sizeof(SyncState
));
310 memcpy(parallelSS
, aggregate
->syncState
, sizeof(SyncState
));
311 g_queue_push_tail(aggregate
->matchingModules
, parallelSS
);
313 parallelSS
->matchingModule
= matchingModule
;
314 parallelSS
->matchingModule
->initMatching(parallelSS
);
319 * A GFunc for g_queue_foreach()
321 * Destroy and remove matching module
324 * data SyncState* containing the module to destroy
327 void gfDestroyModule(gpointer data
, gpointer user_data
)
329 SyncState
* parallelSS
= data
;
331 parallelSS
->matchingModule
->destroyMatching(parallelSS
);
337 * A GFunc for g_queue_foreach()
340 * data SyncState* containing the distributed matching module
341 * user_data Event* original event
343 void gfMatchEvent(gpointer data
, gpointer user_data
)
345 SyncState
* parallelSS
= data
;
346 const Event
* event
= user_data
;
349 if (parallelSS
->matchingModule
->canMatch
[event
->type
])
351 event
->copy(event
, &newEvent
);
352 parallelSS
->matchingModule
->matchEvent(parallelSS
, newEvent
);
358 * A GFunc for g_queue_foreach()
361 * data SyncState* containing the distributed matching module
364 void gfFinalize(gpointer data
, gpointer user_data
)
367 SyncState
* parallelSS
= data
;
369 factors
= parallelSS
->matchingModule
->finalizeMatching(parallelSS
);
370 g_array_free(factors
, TRUE
);
375 * A GFunc for g_queue_foreach()
378 * data SyncState* containing the distributed matching module
381 void gfPrintStats(gpointer data
, gpointer user_data
)
383 SyncState
* parallelSS
= data
;
385 if (parallelSS
->matchingModule
->printMatchingStats
!= NULL
)
387 parallelSS
->matchingModule
->printMatchingStats(parallelSS
);
393 * A GFunc for g_queue_foreach()
395 * Call a certain matching function
398 * data SyncState* containing the distributed matching module
401 void gfGraphFunctionCall(gpointer data
, gpointer user_data
)
403 SyncState
* parallelSS
= data
;
404 struct GraphAggregate
* aggregate
= user_data
;
405 typedef void (*GraphFunction
)(struct _SyncState
*, const unsigned int,
407 GraphFunction graphFunction
= *(GraphFunction
*)((void*)
408 parallelSS
->matchingModule
+ (size_t) aggregate
->offset
);
410 if (graphFunction
!= NULL
)
412 graphFunction(parallelSS
, aggregate
->i
, aggregate
->j
);