@@ -13,6 +13,7 @@ libcacard/trace/generated-tracers.c
instrument/generated-tracers.h
instrument/generated-tracers.c
instrument/qemu-instr/events.h
+instrument/qemu-instr/events-list.h
*-timestamp
*-softmmu
*-darwin-user
@@ -40,6 +40,7 @@ ifdef CONFIG_TRACE_INSTRUMENT_DYNAMIC
GENERATED_SOURCES += instrument/generated-tracers.c
endif
GENERATED_HEADERS += instrument/qemu-instr/events.h
+GENERATED_HEADERS += instrument/qemu-instr/events-list.h
GENERATED_HEADERS += trace/generated-events.h
GENERATED_SOURCES += trace/generated-events.c
@@ -301,6 +301,7 @@ QEMU_CFLAGS="-fno-strict-aliasing $QEMU_CFLAGS"
QEMU_CFLAGS="-Wall -Wundef -Wwrite-strings -Wmissing-prototypes $QEMU_CFLAGS"
QEMU_CFLAGS="-Wstrict-prototypes -Wredundant-decls $QEMU_CFLAGS"
QEMU_CFLAGS="-D_GNU_SOURCE -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE $QEMU_CFLAGS"
+QEMU_CFLAGS="-DBUILDING_QEMU $QEMU_CFLAGS"
QEMU_INCLUDES="-I. -I\$(SRC_PATH) -I\$(SRC_PATH)/include"
if test "$debug_info" = "yes"; then
CFLAGS="-g $CFLAGS"
@@ -41,6 +41,15 @@ $(obj)/qemu-instr/events.h-timestamp: $(TRACE_EVENTS) $(BUILD_DIR)/config-host.m
< $< > $@," GEN $(patsubst %-timestamp,%,$@)")
@cmp -s $@ $(patsubst %-timestamp,%,$@) || cp $@ $(patsubst %-timestamp,%,$@)
+$(obj)/qemu-instr/events-list.h: $(obj)/qemu-instr/events-list.h-timestamp
+$(obj)/qemu-instr/events-list.h-timestamp: $(TRACE_EVENTS) $(BUILD_DIR)/config-host.mak
+ $(call quiet-command,$(TRACETOOL) \
+ --format=api-events-h \
+ --backend=$(TRACE_INSTRUMENT_BACKEND) \
+ $(TRACETOOL_INSTR_STATIC) \
+ < $< > $@," GEN $(patsubst %-timestamp,%,$@)")
+ @cmp -s $@ $(patsubst %-timestamp,%,$@) || cp $@ $(patsubst %-timestamp,%,$@)
+
######################################################################
# User code (static instrumentation)
@@ -71,3 +80,7 @@ target-obj-y += control.o
common-obj-$(CONFIG_SOFTMMU) += hmp.o
common-obj-$(CONFIG_SOFTMMU) += qmp.o
+
+target-obj-y += api-control.o
+
+QEMU_CFLAGS += -I$(BUILD_DIR)/instrument -I$(SRC_PATH)/instrument
new file mode 100644
@@ -0,0 +1,14 @@
+/*
+ * Interface for controlling the state of events.
+ *
+ * Copyright (C) 2012-2013 Lluís Vilanova <vilanova@ac.upc.edu>
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
+ * See the COPYING file in the top-level directory.
+ */
+
+#include "instrument/qemu-instr/control.h"
+
+#if defined(QI_TYPE_DYNAMIC)
+#include "instrument/qemu-instr/control-internal.h"
+#endif
new file mode 100644
@@ -0,0 +1,53 @@
+/*
+ * Interface for controlling the state of events.
+ *
+ * Copyright (C) 2012-2013 Lluís Vilanova <vilanova@ac.upc.edu>
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
+ * See the COPYING file in the top-level directory.
+ */
+
+#ifndef QI__CONTROL_INTERNAL_H
+#define QI__CONTROL_INTERNAL_H
+
+#include "trace/control.h"
+
+
+QI_IDEF QIEvent* qi_ctrl_event_id(QIEventID id)
+{
+ return (QIEvent*)trace_event_id(id);
+}
+
+QI_IDEF QIEvent* qi_ctrl_event_name(const char *name)
+{
+ return (QIEvent*)trace_event_name(name);
+}
+
+QI_IDEF QIEvent* qi_ctrl_event_pattern(const char *pat, QIEvent *ev)
+{
+ return (QIEvent*)trace_event_pattern(pat, (TraceEvent*)ev);
+}
+
+QI_IDEF bool qi_ctrl_event_is_pattern(const char *str)
+{
+ return trace_event_is_pattern(str);
+}
+
+QI_IDEF QIEventID qi_ctrl_event_count(void)
+{
+ return (QIEventID)trace_event_count();
+}
+
+
+
+QI_IDEF QIEventID qi_ctrl_event_get_id(QIEvent *ev)
+{
+ return (QIEventID)trace_event_get_id((TraceEvent*)ev);
+}
+
+QI_IDEF const char * qi_ctrl_event_get_name(QIEvent *ev)
+{
+ return trace_event_get_name((TraceEvent*)ev);
+}
+
+#endif /* QI__CONTROL_INTERNAL_H */
new file mode 100644
@@ -0,0 +1,124 @@
+/*
+ * Interface for controlling the state of events.
+ *
+ * Copyright (C) 2012-2013 Lluís Vilanova <vilanova@ac.upc.edu>
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
+ * See the COPYING file in the top-level directory.
+ */
+
+#ifndef QI__CONTROL_H
+#define QI__CONTROL_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <stdbool.h>
+
+#include <qemu-instr/config.h>
+#include <qemu-instr/visibility-internal.h>
+#include <qemu-instr/events-list.h>
+
+
+/**
+ * SECTION:control
+ * @section_id: qi-control
+ * @title: QEMU instrumentation event control interface
+ */
+
+/**
+ * QIEvent:
+ *
+ * Opaque structure defining an instrumentation event.
+ */
+struct QIEvent;
+typedef struct QIEvent QIEvent;
+
+/**
+ * QIEventID:
+ *
+ * Unique instrumentation event identifier.
+ *
+ * These are named as 'QI_EVENT_${EVENT}'.
+ *
+ * See also: qemu-instr/events-list.h
+ */
+
+/**
+ * qi_ctrl_event_id:
+ * @id: Event identifier.
+ *
+ * Get an event by its identifier.
+ *
+ * This routine has a constant cost, as opposed to qi_ctrl_event_name() and
+ * qi_ctrl_event_pattern().
+ *
+ * Pre-conditions: @id is valid.
+ *
+ * Returns: Pointer to selected #QIEvent.
+ *
+ */
+QI_IDECL QIEvent* qi_ctrl_event_id(QIEventID id);
+
+/**
+ * qi_ctrl_event_name:
+ * @id: Event name.
+ *
+ * Search an event by its name.
+ *
+ * Returns: Pointer to #QIEvent or #NULL if not found.
+ */
+QI_IDECL QIEvent* qi_ctrl_event_name(const char *name);
+
+/**
+ * qi_ctrl_event_pattern:
+ * @pat: Event name pattern.
+ * @ev: Event to start searching from (not included).
+ *
+ * Iteratively get all events with a given name pattern.
+ *
+ * Returns: pointer to #TraceEvent or #NULL if not found.
+ */
+QI_IDECL QIEvent* qi_ctrl_event_pattern(const char *pat, QIEvent *ev);
+
+/**
+ * qi_ctrl_event_is_pattern:
+ *
+ * Whether the given string is an event name pattern.
+ */
+QI_IDECL bool qi_ctrl_event_is_pattern(const char *str);
+
+/**
+ * qi_ctrl_event_count:
+ *
+ * Return the number of events.
+ */
+QI_IDECL QIEventID qi_ctrl_event_count(void);
+
+
+
+/**
+ * qi_ctrl_event_get_id:
+ *
+ * Get the identifier of an event.
+ */
+QI_IDECL QIEventID qi_ctrl_event_get_id(QIEvent *ev);
+
+/**
+ * qi_ctrl_event_get_name:
+ *
+ * Get the name of an event.
+ */
+QI_IDECL const char * qi_ctrl_event_get_name(QIEvent *ev);
+
+
+#if !defined(QI_TYPE_DYNAMIC)
+#include "instrument/qemu-instr/control-internal.h"
+#endif
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* QI__CONTROL_H */
new file mode 100644
@@ -0,0 +1,94 @@
+/*
+ * Macros for symbol visibility.
+ *
+ * Copyright (C) 2012-2013 Lluís Vilanova <vilanova@ac.upc.edu>
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
+ * See the COPYING file in the top-level directory of QEMU.
+ */
+
+#ifndef QI__VISIBILITY_INTERNAL_H
+#define QI__VISIBILITY_INTERNAL_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <qemu-instr/config.h>
+
+
+/**
+ * SECTION:visibility
+ * @section_id: qi-visibility
+ * @title: Symbol visibility
+ *
+ * This code is taken from http://gcc.gnu.org/wiki/Visibility.
+ */
+
+/**
+ * QI_VPUBLIC:
+ *
+ * Make an element public to third-party code.
+ */
+
+/**
+ * QI_VLOCAL:
+ *
+ * Make an element not visible to third-party code.
+ */
+
+#if defined _WIN32 || defined __CYGWIN__
+ #ifdef BUILDING_QEMU
+ #ifdef __GNUC__
+ #define QI_VPUBLIC __attribute__ ((dllexport))
+ #else
+ #define QI_VPUBLIC __declspec(dllexport)
+ #endif
+ #else
+ #ifdef __GNUC__
+ #define QI_VPUBLIC __attribute__ ((dllimport))
+ #else
+ #define QI_VPUBLIC __declspec(dllimport)
+ #endif
+ #endif
+ #define QI_VLOCAL
+#else
+ #if __GNUC__ >= 4
+ #define QI_VPUBLIC __attribute__ ((visibility ("default")))
+ #define QI_VLOCAL __attribute__ ((visibility ("hidden")))
+ #else
+ #define QI_VPUBLIC
+ #define QI_VLOCAL
+ #endif
+#endif
+
+/**
+ * QI_IDECL:
+ *
+ * Instrumentation-type dependant declaration attribute for inlined routines.
+ */
+
+#if defined(QI_TYPE_DYNAMIC)
+#define QI_IDECL QI_VPUBLIC
+#else
+#define QI_IDECL static
+#endif
+
+/**
+ * QI_IDEF:
+ *
+ * Instrumentation-type dependant definition attribute for inlined routines.
+ */
+
+#if defined(QI_TYPE_DYNAMIC)
+#define QI_IDEF
+#else
+#define QI_IDEF static inline
+#endif
+
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* QI__VISIBILITY_INTERNAL_H */
@@ -88,3 +88,6 @@ def api_c(events):
args = e.args,
argnames = ", ".join(e.args.names()),
)
+
+def api_events_h(events):
+ pass
@@ -39,3 +39,6 @@ def api_h(events):
qemu_backend = e.api(e.QEMU_TRACE_BACKEND),
argnames = ", ".join(e.args.names()),
)
+
+def api_events_h(events):
+ pass
@@ -77,3 +77,6 @@ def api_h(events):
argnames = ", ".join(e.args.names()),
upper_name = e.name.upper(),
)
+
+def api_events_h(events):
+ pass
new file mode 100644
@@ -0,0 +1,56 @@
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+
+"""
+Generate .h with event description for trace instrumentation clients.
+"""
+
+__author__ = "Lluís Vilanova <vilanova@ac.upc.edu>"
+__copyright__ = "Copyright 2012-2013, Lluís Vilanova <vilanova@ac.upc.edu>"
+__license__ = "GPL version 2 or (at your option) any later version"
+
+__maintainer__ = "Stefan Hajnoczi"
+__email__ = "stefanha@linux.vnet.ibm.com"
+
+
+from tracetool import out
+
+
+def begin(events):
+ out('/* This file is autogenerated by tracetool, do not edit. */',
+ '',
+ '#ifndef QI__EVENTS_LIST_H',
+ '#define QI__EVENTS_LIST_H',
+ '',
+ '#ifdef __cplusplus',
+ 'extern "C" {',
+ '#endif',
+ '',
+ )
+
+ # event identifiers
+ out('typedef enum {')
+
+ for e in events:
+ out(' QI_EVENT_%s,' % e.name.upper())
+
+ out(' QI_EVENT_COUNT',
+ '} QIEventID;',
+ '',
+ )
+
+ # static state
+ for e in events:
+ if 'disable' in e.properties:
+ enabled = 0
+ else:
+ enabled = 1
+ out('#define QI_EVENT_%s_ENABLED %d' % (e.name.upper(), enabled))
+
+ out('#ifdef __cplusplus',
+ '}',
+ '#endif',
+ '',
+ '#endif /* QI__EVENTS_LIST_H */',
+ '',
+ )
Signed-off-by: Lluís Vilanova <vilanova@ac.upc.edu> --- .gitignore | 1 Makefile | 1 configure | 1 instrument/Makefile.objs | 13 +++ instrument/api-control.c | 14 +++ instrument/qemu-instr/control-internal.h | 53 ++++++++++++ instrument/qemu-instr/control.h | 124 +++++++++++++++++++++++++++ instrument/qemu-instr/visibility-internal.h | 94 ++++++++++++++++++++ scripts/tracetool/backend/instr_dynamic.py | 3 + scripts/tracetool/backend/instr_none.py | 3 + scripts/tracetool/backend/instr_static.py | 3 + scripts/tracetool/format/api_events_h.py | 56 ++++++++++++ 12 files changed, 366 insertions(+) create mode 100644 instrument/api-control.c create mode 100644 instrument/qemu-instr/control-internal.h create mode 100644 instrument/qemu-instr/control.h create mode 100644 instrument/qemu-instr/visibility-internal.h create mode 100644 scripts/tracetool/format/api_events_h.py