illegal to modify any existing tracecut objects. */
static int tc_in_compilation = 0;
+/* Go through the master list of tracecuts and give each a consecutive
+ index. */
+static void
+assign_tracecut_indices ()
+{
+ int next_tracecut_index = 0;
+ struct tc_tracecut *tc;
+
+ for (tc = tracecut_list; tc != NULL; tc = tc->next)
+ tc->index = next_tracecut_index++;
+}
+
+/* Choose an index for every tracecut object. After that, tracecut
+ objects are frozen because setting tc_in_compilation to true makes
+ it illegal to modify them. */
+static void
+freeze_tracecuts (void)
+{
+ if (!tc_in_compilation)
+ {
+ assign_tracecut_indices ();
+ tc_in_compilation = 1;
+ }
+
+}
+
static struct tc_param *
lookup_param (struct tc_tracecut *tc, const char *name)
{
free(tc);
}
-/* Go through the master list of tracecuts and give each a consecutive
- index. */
-static void
-assign_tracecut_indices ()
-{
- int next_tracecut_index = 0;
- struct tc_tracecut *tc;
-
- for (tc = tracecut_list; tc != NULL; tc = tc->next)
- tc->index = next_tracecut_index++;
-}
-
/* Add an advice call to the tracecut runtime notifying it that an
event occurred and that _tc_capture_*_param() calls will follow
to specify the event's params. */
}
}
-static unsigned int
-tracecut_pass (void)
+/* Return the number of tracecuts in the master tracecut list. */
+static int
+get_num_tracecuts()
{
struct tc_tracecut *tc;
+ int num_tracecuts = 0;
- if (!tc_in_compilation)
+ for (tc = tracecut_list; tc != NULL; tc = tc->next)
+ num_tracecuts++;
+
+ return num_tracecuts;
+}
+
+void
+tc_insert_tracecut_init_advice (struct aop_joinpoint *jp)
+{
+ int num_tracecuts;
+ struct tc_tracecut *tc;
+
+ freeze_tracecuts ();
+
+ /* If there are no tracecuts, there's nothing to initialize! */
+ num_tracecuts = get_num_tracecuts();
+ if (num_tracecuts == 0)
+ return;
+
+ /* _tc_init(num_tracecuts); */
+ aop_insert_advice (jp, "_tc_init", AOP_INSERT_BEFORE,
+ AOP_INT_CST (num_tracecuts), AOP_TERM_ARG);
+
+ for (tc = tracecut_list; tc != NULL; tc = tc->next)
{
- /* Choose an index for every tracecut object. After that,
- tracecut objects are frozen because setting tc_in_compilation
- to true makes it illegal to modify them. */
- assign_tracecut_indices ();
- tc_in_compilation = 1;
+ struct tc_call_symbol *symbol;
+ int num_params, num_symbols;
+
+ /* _tc_new_tracecut(tc_index, num_params, num_symbols); */
+ num_params = tc->next_param_index;
+ num_symbols = tc->next_symbol_index;
+ aop_insert_advice (jp, "_tc_new_tracecut", AOP_INSERT_BEFORE,
+ AOP_INT_CST (tc->index), AOP_INT_CST (num_params),
+ AOP_INT_CST (num_symbols), AOP_TERM_ARG);
+
+ for (symbol = tc->symbol_list; symbol != NULL; symbol = symbol->next)
+ {
+ /* _tc_name_symbol(tc_index, symbol_index, symbol_name); */
+ aop_insert_advice (jp, "_tc_name_symbol", AOP_INSERT_BEFORE,
+ AOP_INT_CST (tc->index),
+ AOP_INT_CST (symbol->index),
+ AOP_STR_CST (symbol->name), AOP_TERM_ARG);
+ }
+
+ /* _tc_compile_tracecut(tc_index) */
+ aop_insert_advice (jp, "_tc_compile_tracecut", AOP_INSERT_BEFORE,
+ AOP_INT_CST (tc->index), AOP_TERM_ARG);
}
+}
+
+static unsigned int
+tracecut_pass (void)
+{
+ struct tc_tracecut *tc;
+
+ freeze_tracecuts ();
for (tc = tracecut_list; tc != NULL; tc = tc->next)
add_instrumentation_for_tracecut (tc);