Import QEMU upstream snapshot d2e570c
Upstream: https://gitlab.com/qemu-project/qemu.git Upstream-Commit: d2e570cc0f97b936902a5b1b86b73c0f5998b475
This commit is contained in:
@@ -0,0 +1,84 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
"""
|
||||
Format management.
|
||||
|
||||
|
||||
Creating new formats
|
||||
--------------------
|
||||
|
||||
A new format named 'foo-bar' corresponds to Python module
|
||||
'tracetool/format/foo_bar.py'.
|
||||
|
||||
A format module should provide a docstring, whose first non-empty line will be
|
||||
considered its short description.
|
||||
|
||||
All formats must generate their contents through the 'tracetool.out' routine.
|
||||
|
||||
|
||||
Format functions
|
||||
----------------
|
||||
|
||||
======== ==================================================================
|
||||
Function Description
|
||||
======== ==================================================================
|
||||
generate Called to generate a format-specific file.
|
||||
======== ==================================================================
|
||||
|
||||
"""
|
||||
|
||||
__author__ = "Lluís Vilanova <[email protected]>"
|
||||
__copyright__ = "Copyright 2012-2014, Lluís Vilanova <[email protected]>"
|
||||
__license__ = "GPL version 2 or (at your option) any later version"
|
||||
|
||||
__maintainer__ = "Stefan Hajnoczi"
|
||||
__email__ = "[email protected]"
|
||||
|
||||
|
||||
import os
|
||||
|
||||
import tracetool
|
||||
|
||||
|
||||
def get_list():
|
||||
"""Get a list of (name, description) pairs."""
|
||||
res = []
|
||||
modnames = []
|
||||
for filename in os.listdir(tracetool.format.__path__[0]):
|
||||
if filename.endswith('.py') and filename != '__init__.py':
|
||||
modnames.append(filename.rsplit('.', 1)[0])
|
||||
for modname in sorted(modnames):
|
||||
module = tracetool.try_import("tracetool.format." + modname)
|
||||
|
||||
# just in case; should never fail unless non-module files are put there
|
||||
if not module[0]:
|
||||
continue
|
||||
module = module[1]
|
||||
|
||||
doc = module.__doc__
|
||||
if doc is None:
|
||||
doc = ""
|
||||
doc = doc.strip().split("\n")[0]
|
||||
|
||||
name = modname.replace("_", "-")
|
||||
res.append((name, doc))
|
||||
return res
|
||||
|
||||
|
||||
def exists(name):
|
||||
"""Return whether the given format exists."""
|
||||
if len(name) == 0:
|
||||
return False
|
||||
name = name.replace("-", "_")
|
||||
return tracetool.try_import("tracetool.format." + name)[0]
|
||||
|
||||
|
||||
def generate(events, format, backend, group):
|
||||
if not exists(format):
|
||||
raise ValueError("unknown format: %s" % format)
|
||||
format = format.replace("-", "_")
|
||||
func = tracetool.try_import("tracetool.format." + format,
|
||||
"generate")[1]
|
||||
if func is None:
|
||||
raise AttributeError("format has no 'generate': %s" % format)
|
||||
func(events, backend, group)
|
||||
@@ -0,0 +1,67 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
"""
|
||||
trace/generated-tracers.c
|
||||
"""
|
||||
|
||||
__author__ = "Lluís Vilanova <[email protected]>"
|
||||
__copyright__ = "Copyright 2012-2014, Lluís Vilanova <[email protected]>"
|
||||
__license__ = "GPL version 2 or (at your option) any later version"
|
||||
|
||||
__maintainer__ = "Stefan Hajnoczi"
|
||||
__email__ = "[email protected]"
|
||||
|
||||
|
||||
from tracetool import out
|
||||
|
||||
|
||||
def generate(events, backend, group):
|
||||
active_events = [e for e in events
|
||||
if "disable" not in e.properties]
|
||||
|
||||
header = "trace-" + group + ".h"
|
||||
|
||||
out('/* This file is autogenerated by tracetool, do not edit. */',
|
||||
'/* SPDX-License-Identifier: GPL-2.0-or-later */',
|
||||
'',
|
||||
'#include "qemu/osdep.h"',
|
||||
'#include "qemu/module.h"',
|
||||
'#include "%s"' % header,
|
||||
'')
|
||||
|
||||
for e in events:
|
||||
out('uint16_t %s;' % e.api(e.QEMU_DSTATE))
|
||||
|
||||
for e in events:
|
||||
out('TraceEvent %(event)s = {',
|
||||
' .id = 0,',
|
||||
' .name = \"%(name)s\",',
|
||||
' .sstate = %(sstate)s,',
|
||||
' .dstate = &%(dstate)s',
|
||||
'};',
|
||||
event = e.api(e.QEMU_EVENT),
|
||||
name = e.name,
|
||||
sstate = "TRACE_%s_ENABLED" % e.name.upper(),
|
||||
dstate = e.api(e.QEMU_DSTATE))
|
||||
|
||||
out('TraceEvent *%(group)s_trace_events[] = {',
|
||||
group = group.lower())
|
||||
|
||||
for e in events:
|
||||
out(' &%(event)s,', event = e.api(e.QEMU_EVENT))
|
||||
|
||||
out(' NULL,',
|
||||
'};',
|
||||
'')
|
||||
|
||||
out('static void trace_%(group)s_register_events(void)',
|
||||
'{',
|
||||
' trace_event_register_group(%(group)s_trace_events);',
|
||||
'}',
|
||||
'trace_init(trace_%(group)s_register_events)',
|
||||
group = group.lower())
|
||||
|
||||
backend.generate_begin(active_events, group)
|
||||
for event in active_events:
|
||||
backend.generate(event, group)
|
||||
backend.generate_end(active_events, group)
|
||||
@@ -0,0 +1,78 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
"""
|
||||
trace/generated-tracers.dtrace (DTrace only).
|
||||
"""
|
||||
|
||||
__author__ = "Lluís Vilanova <[email protected]>"
|
||||
__copyright__ = "Copyright 2012-2014, Lluís Vilanova <[email protected]>"
|
||||
__license__ = "GPL version 2 or (at your option) any later version"
|
||||
|
||||
__maintainer__ = "Stefan Hajnoczi"
|
||||
__email__ = "[email protected]"
|
||||
|
||||
|
||||
from tracetool import out
|
||||
from sys import platform
|
||||
|
||||
|
||||
# Reserved keywords from
|
||||
# https://wikis.oracle.com/display/DTrace/Types,+Operators+and+Expressions
|
||||
RESERVED_WORDS = (
|
||||
'auto', 'goto', 'sizeof', 'break', 'if', 'static', 'case', 'import',
|
||||
'string', 'char', 'inline', 'stringof', 'const', 'int', 'struct',
|
||||
'continue', 'long', 'switch', 'counter', 'offsetof', 'this',
|
||||
'default', 'probe', 'translator', 'do', 'provider', 'typedef',
|
||||
'double', 'register', 'union', 'else', 'restrict', 'unsigned',
|
||||
'enum', 'return', 'void', 'extern', 'self', 'volatile', 'float',
|
||||
'short', 'while', 'for', 'signed', 'xlate',
|
||||
)
|
||||
|
||||
|
||||
def generate(events, backend, group):
|
||||
events = [e for e in events
|
||||
if "disable" not in e.properties]
|
||||
|
||||
# SystemTap's dtrace(1) warns about empty "provider qemu {}" but is happy
|
||||
# with an empty file. Avoid the warning.
|
||||
# But dtrace on macOS can't deal with empty files.
|
||||
if not events and platform != "darwin":
|
||||
return
|
||||
|
||||
out('/* This file is autogenerated by tracetool, do not edit. */',
|
||||
'/* SPDX-License-Identifier: GPL-2.0-or-later */',
|
||||
'',
|
||||
'provider qemu {')
|
||||
|
||||
for e in events:
|
||||
args = []
|
||||
for type_, name in e.args:
|
||||
if platform == "darwin":
|
||||
# macOS dtrace accepts only C99 _Bool
|
||||
if type_ == 'bool':
|
||||
type_ = '_Bool'
|
||||
if type_ == 'bool *':
|
||||
type_ = '_Bool *'
|
||||
# It converts int8_t * in probe points to char * in header
|
||||
# files and introduces [-Wpointer-sign] warning.
|
||||
# Avoid it by changing probe type to signed char * beforehand.
|
||||
if type_ == 'int8_t *':
|
||||
type_ = 'signed char *'
|
||||
|
||||
# SystemTap dtrace(1) emits a warning when long long is used
|
||||
type_ = type_.replace('unsigned long long', 'uint64_t')
|
||||
type_ = type_.replace('signed long long', 'int64_t')
|
||||
type_ = type_.replace('long long', 'int64_t')
|
||||
|
||||
if name in RESERVED_WORDS:
|
||||
name += '_'
|
||||
args.append(type_ + ' ' + name)
|
||||
|
||||
# Define prototype for probe arguments
|
||||
out('',
|
||||
'probe %(name)s(%(args)s);',
|
||||
name=e.name,
|
||||
args=','.join(args))
|
||||
|
||||
out('',
|
||||
'};')
|
||||
@@ -0,0 +1,78 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
"""
|
||||
trace/generated-tracers.h
|
||||
"""
|
||||
|
||||
__author__ = "Lluís Vilanova <[email protected]>"
|
||||
__copyright__ = "Copyright 2012-2017, Lluís Vilanova <[email protected]>"
|
||||
__license__ = "GPL version 2 or (at your option) any later version"
|
||||
|
||||
__maintainer__ = "Stefan Hajnoczi"
|
||||
__email__ = "[email protected]"
|
||||
|
||||
|
||||
from tracetool import out
|
||||
|
||||
|
||||
def generate(events, backend, group):
|
||||
header = "trace/control.h"
|
||||
|
||||
out('/* This file is autogenerated by tracetool, do not edit. */',
|
||||
'/* SPDX-License-Identifier: GPL-2.0-or-later */',
|
||||
'',
|
||||
'#ifndef TRACE_%s_GENERATED_TRACERS_H' % group.upper(),
|
||||
'#define TRACE_%s_GENERATED_TRACERS_H' % group.upper(),
|
||||
'',
|
||||
'#include "%s"' % header,
|
||||
'')
|
||||
|
||||
for e in events:
|
||||
out('extern TraceEvent %(event)s;',
|
||||
event = e.api(e.QEMU_EVENT))
|
||||
|
||||
for e in events:
|
||||
out('extern uint16_t %s;' % e.api(e.QEMU_DSTATE))
|
||||
|
||||
# static state
|
||||
for e in events:
|
||||
if 'disable' in e.properties:
|
||||
enabled = 0
|
||||
else:
|
||||
enabled = 1
|
||||
out('#define TRACE_%s_ENABLED %d' % (e.name.upper(), enabled))
|
||||
|
||||
backend.generate_begin(events, group)
|
||||
|
||||
for e in events:
|
||||
# tracer-specific dstate
|
||||
out('',
|
||||
'#define %(api)s() ( \\',
|
||||
api=e.api(e.QEMU_BACKEND_DSTATE))
|
||||
|
||||
if "disable" not in e.properties:
|
||||
backend.generate_backend_dstate(e, group)
|
||||
|
||||
out(' false)')
|
||||
|
||||
out('',
|
||||
'static inline void %(api)s(%(args)s)',
|
||||
'{',
|
||||
api=e.api(),
|
||||
args=e.args)
|
||||
|
||||
if "disable" not in e.properties:
|
||||
backend.generate(e, group, check_trace_event_get_state=False)
|
||||
|
||||
if backend.check_trace_event_get_state:
|
||||
event_id = 'TRACE_' + e.name.upper()
|
||||
cond = "trace_event_get_state(%s)" % event_id
|
||||
out(' if (%(cond)s) {',
|
||||
cond=cond)
|
||||
backend.generate(e, group, check_trace_event_get_state=True)
|
||||
out(' }')
|
||||
out('}')
|
||||
|
||||
backend.generate_end(events, group)
|
||||
|
||||
out('#endif /* TRACE_%s_GENERATED_TRACERS_H */' % group.upper())
|
||||
@@ -0,0 +1,128 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
"""
|
||||
Generate .stp file that printfs log messages (DTrace with SystemTAP only).
|
||||
"""
|
||||
|
||||
__author__ = "Daniel P. Berrange <[email protected]>"
|
||||
__copyright__ = "Copyright (C) 2014-2019, Red Hat, Inc."
|
||||
__license__ = "GPL version 2 or (at your option) any later version"
|
||||
|
||||
__maintainer__ = "Daniel Berrange"
|
||||
__email__ = "[email protected]"
|
||||
|
||||
import re
|
||||
|
||||
from tracetool import out
|
||||
from tracetool.backend.dtrace import binary, probeprefix
|
||||
from tracetool.backend.simple import is_string
|
||||
from tracetool.format.stap import stap_escape
|
||||
|
||||
|
||||
STATE_SKIP = 0
|
||||
STATE_LITERAL = 1
|
||||
STATE_MACRO = 2
|
||||
|
||||
def c_macro_to_format(macro):
|
||||
if macro.startswith("PRI"):
|
||||
return macro[3]
|
||||
|
||||
raise Exception("Unhandled macro '%s'" % macro)
|
||||
|
||||
def c_fmt_to_stap(fmt):
|
||||
state = 0
|
||||
bits = []
|
||||
literal = ""
|
||||
macro = ""
|
||||
escape = 0;
|
||||
for i in range(len(fmt)):
|
||||
if fmt[i] == '\\':
|
||||
if escape:
|
||||
escape = 0
|
||||
else:
|
||||
escape = 1
|
||||
if state != STATE_LITERAL:
|
||||
raise Exception("Unexpected escape outside string literal")
|
||||
literal = literal + fmt[i]
|
||||
elif fmt[i] == '"' and not escape:
|
||||
if state == STATE_LITERAL:
|
||||
state = STATE_SKIP
|
||||
bits.append(literal)
|
||||
literal = ""
|
||||
else:
|
||||
if state == STATE_MACRO:
|
||||
bits.append(c_macro_to_format(macro))
|
||||
macro = ""
|
||||
state = STATE_LITERAL
|
||||
elif fmt[i] == ' ' or fmt[i] == '\t':
|
||||
if state == STATE_MACRO:
|
||||
bits.append(c_macro_to_format(macro))
|
||||
macro = ""
|
||||
state = STATE_SKIP
|
||||
elif state == STATE_LITERAL:
|
||||
literal = literal + fmt[i]
|
||||
else:
|
||||
escape = 0
|
||||
if state == STATE_SKIP:
|
||||
state = STATE_MACRO
|
||||
|
||||
if state == STATE_LITERAL:
|
||||
literal = literal + fmt[i]
|
||||
else:
|
||||
macro = macro + fmt[i]
|
||||
|
||||
if state == STATE_MACRO:
|
||||
bits.append(c_macro_to_format(macro))
|
||||
elif state == STATE_LITERAL:
|
||||
bits.append(literal)
|
||||
|
||||
# All variables in systemtap are 64-bit in size
|
||||
# The "%l" integer size qualifier is thus redundant
|
||||
# and "%ll" is not valid at all. Similarly the size_t
|
||||
# based "%z" size qualifier is not valid. We just
|
||||
# strip all size qualifiers for sanity.
|
||||
fmt = re.sub(r"%(\d*)(l+|z)(x|u|d)", r"%\1\3", "".join(bits))
|
||||
return fmt
|
||||
|
||||
def generate(events, backend, group):
|
||||
out('/* This file is autogenerated by tracetool, do not edit. */',
|
||||
'/* SPDX-License-Identifier: GPL-2.0-or-later */',
|
||||
'')
|
||||
|
||||
for event_id, e in enumerate(events):
|
||||
if 'disable' in e.properties:
|
||||
continue
|
||||
|
||||
out('probe %(probeprefix)s.log.%(name)s = %(probeprefix)s.%(name)s ?',
|
||||
'{',
|
||||
probeprefix=probeprefix(),
|
||||
name=e.name)
|
||||
|
||||
# Get references to userspace strings
|
||||
for type_, name in e.args:
|
||||
name = stap_escape(name)
|
||||
if is_string(type_):
|
||||
out(' try {',
|
||||
' arg%(name)s_str = %(name)s ? ' +
|
||||
'user_string_n(%(name)s, 512) : "<null>"',
|
||||
' } catch {}',
|
||||
name=name)
|
||||
|
||||
# Determine systemtap's view of variable names
|
||||
fields = ["pid()", "gettimeofday_ns()"]
|
||||
for type_, name in e.args:
|
||||
name = stap_escape(name)
|
||||
if is_string(type_):
|
||||
fields.append("arg" + name + "_str")
|
||||
else:
|
||||
fields.append(name)
|
||||
|
||||
# Emit the entire record in a single SystemTap printf()
|
||||
arg_str = ', '.join(arg for arg in fields)
|
||||
fmt_str = "%d@%d " + e.name + " " + c_fmt_to_stap(e.fmt) + "\\n"
|
||||
out(' printf("%(fmt_str)s", %(arg_str)s)',
|
||||
fmt_str=fmt_str, arg_str=arg_str)
|
||||
|
||||
out('}')
|
||||
|
||||
out()
|
||||
@@ -0,0 +1,83 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
"""
|
||||
trace-DIR.rs
|
||||
"""
|
||||
|
||||
__author__ = "Tanish Desai <[email protected]>"
|
||||
__copyright__ = "Copyright 2025, Tanish Desai <[email protected]>"
|
||||
__license__ = "GPL version 2 or (at your option) any later version"
|
||||
|
||||
__maintainer__ = "Stefan Hajnoczi"
|
||||
__email__ = "[email protected]"
|
||||
|
||||
|
||||
from tracetool import out
|
||||
|
||||
|
||||
def generate(events, backend, group):
|
||||
out('// SPDX-License-Identifier: GPL-2.0-or-later',
|
||||
'// This file is @generated by tracetool, do not edit.',
|
||||
'',
|
||||
'#[allow(unused_imports)]',
|
||||
'use std::ffi::c_char;',
|
||||
'#[allow(unused_imports)]',
|
||||
'use util::bindings;',
|
||||
'',
|
||||
'#[allow(dead_code)]',
|
||||
'#[inline(always)]',
|
||||
'fn trace_event_state_is_enabled(dstate: u16) -> bool {',
|
||||
' (unsafe { trace_events_enabled_count }) != 0 && dstate != 0',
|
||||
'}',
|
||||
'',
|
||||
'extern "C" {',
|
||||
' #[allow(dead_code)]',
|
||||
' static mut trace_events_enabled_count: u32;',
|
||||
'}',)
|
||||
|
||||
out('extern "C" {')
|
||||
|
||||
for e in events:
|
||||
out(' #[allow(dead_code)]',
|
||||
' static mut %s: u16;' % e.api(e.QEMU_DSTATE))
|
||||
out('}',
|
||||
'')
|
||||
|
||||
backend.generate_begin(events, group)
|
||||
|
||||
for e in events:
|
||||
out('#[inline(always)]',
|
||||
'#[allow(dead_code)]',
|
||||
'pub fn %(api)s() -> bool',
|
||||
'{',
|
||||
api=e.api(e.QEMU_RUST_DSTATE))
|
||||
|
||||
if "disable" not in e.properties:
|
||||
backend.generate_backend_dstate(e, group)
|
||||
if backend.check_trace_event_get_state:
|
||||
out(' trace_event_state_is_enabled(unsafe { _%(event_id)s_DSTATE}) ||',
|
||||
event_id = 'TRACE_' + e.name.upper())
|
||||
|
||||
out(' false',
|
||||
'}',
|
||||
'',
|
||||
'#[inline(always)]',
|
||||
'#[allow(dead_code)]',
|
||||
'pub fn %(api)s(%(args)s)',
|
||||
'{',
|
||||
api=e.api(e.QEMU_TRACE),
|
||||
args=e.args.rust_decl())
|
||||
|
||||
if "disable" not in e.properties:
|
||||
backend.generate(e, group, check_trace_event_get_state=False)
|
||||
if backend.check_trace_event_get_state:
|
||||
event_id = 'TRACE_' + e.name.upper()
|
||||
out(' if trace_event_state_is_enabled(unsafe { _%(event_id)s_DSTATE}) {',
|
||||
event_id = event_id,
|
||||
api=e.api())
|
||||
backend.generate(e, group, check_trace_event_get_state=True)
|
||||
out(' }')
|
||||
out('}',
|
||||
'')
|
||||
|
||||
backend.generate_end(events, group)
|
||||
@@ -0,0 +1,71 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
"""
|
||||
Generate .stp file that outputs simpletrace binary traces (DTrace with SystemTAP only).
|
||||
"""
|
||||
|
||||
__author__ = "Stefan Hajnoczi <redhat.com>"
|
||||
__copyright__ = "Copyright (C) 2014, Red Hat, Inc."
|
||||
__license__ = "GPL version 2 or (at your option) any later version"
|
||||
|
||||
__maintainer__ = "Stefan Hajnoczi"
|
||||
__email__ = "[email protected]"
|
||||
|
||||
|
||||
from tracetool import out
|
||||
from tracetool.backend.dtrace import probeprefix
|
||||
from tracetool.backend.simple import is_string
|
||||
from tracetool.format.stap import stap_escape
|
||||
|
||||
|
||||
def generate(events, backend, group):
|
||||
out('/* This file is autogenerated by tracetool, do not edit. */',
|
||||
'/* SPDX-License-Identifier: GPL-2.0-or-later */',
|
||||
'')
|
||||
|
||||
for event_id, e in enumerate(events):
|
||||
if 'disable' in e.properties:
|
||||
continue
|
||||
|
||||
out('probe %(probeprefix)s.simpletrace.%(name)s = %(probeprefix)s.%(name)s ?',
|
||||
'{',
|
||||
probeprefix=probeprefix(),
|
||||
name=e.name)
|
||||
|
||||
# Calculate record size
|
||||
sizes = ['24'] # sizeof(TraceRecord)
|
||||
for type_, name in e.args:
|
||||
name = stap_escape(name)
|
||||
if is_string(type_):
|
||||
out(' try {',
|
||||
' arg%(name)s_str = %(name)s ? user_string_n(%(name)s, 512) : "<null>"',
|
||||
' } catch {}',
|
||||
' arg%(name)s_len = strlen(arg%(name)s_str)',
|
||||
name=name)
|
||||
sizes.append('4 + arg%s_len' % name)
|
||||
else:
|
||||
sizes.append('8')
|
||||
sizestr = ' + '.join(sizes)
|
||||
|
||||
# Generate format string and value pairs for record header and arguments
|
||||
fields = [('8b', str(event_id)),
|
||||
('8b', 'gettimeofday_ns()'),
|
||||
('4b', sizestr),
|
||||
('4b', 'pid()')]
|
||||
for type_, name in e.args:
|
||||
name = stap_escape(name)
|
||||
if is_string(type_):
|
||||
fields.extend([('4b', 'arg%s_len' % name),
|
||||
('.*s', 'arg%s_len, arg%s_str' % (name, name))])
|
||||
else:
|
||||
fields.append(('8b', name))
|
||||
|
||||
# Emit the entire record in a single SystemTap printf()
|
||||
fmt_str = '%'.join(fmt for fmt, _ in fields)
|
||||
arg_str = ', '.join(arg for _, arg in fields)
|
||||
out(' printf("%%8b%%%(fmt_str)s", 1, %(arg_str)s)',
|
||||
fmt_str=fmt_str, arg_str=arg_str)
|
||||
|
||||
out('}')
|
||||
|
||||
out()
|
||||
@@ -0,0 +1,61 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
"""
|
||||
Generate .stp file (DTrace with SystemTAP only).
|
||||
"""
|
||||
|
||||
__author__ = "Lluís Vilanova <[email protected]>"
|
||||
__copyright__ = "Copyright 2012-2014, Lluís Vilanova <[email protected]>"
|
||||
__license__ = "GPL version 2 or (at your option) any later version"
|
||||
|
||||
__maintainer__ = "Stefan Hajnoczi"
|
||||
__email__ = "[email protected]"
|
||||
|
||||
|
||||
from tracetool import out
|
||||
from tracetool.backend.dtrace import binary, probeprefix
|
||||
|
||||
|
||||
# Technically 'self' is not used by systemtap yet, but
|
||||
# they recommended we keep it in the reserved list anyway
|
||||
RESERVED_WORDS = (
|
||||
'break', 'catch', 'continue', 'delete', 'else', 'for',
|
||||
'foreach', 'function', 'global', 'if', 'in', 'limit',
|
||||
'long', 'next', 'probe', 'return', 'self', 'string',
|
||||
'try', 'while'
|
||||
)
|
||||
|
||||
|
||||
def stap_escape(identifier):
|
||||
# Append underscore to reserved keywords
|
||||
if identifier in RESERVED_WORDS:
|
||||
return identifier + '_'
|
||||
return identifier
|
||||
|
||||
|
||||
def generate(events, backend, group):
|
||||
events = [e for e in events
|
||||
if "disable" not in e.properties]
|
||||
|
||||
out('/* This file is autogenerated by tracetool, do not edit. */',
|
||||
'/* SPDX-License-Identifier: GPL-2.0-or-later */',
|
||||
'')
|
||||
|
||||
for e in events:
|
||||
# Define prototype for probe arguments
|
||||
out('probe %(probeprefix)s.%(name)s = process("%(binary)s").mark("%(name)s")',
|
||||
'{',
|
||||
probeprefix=probeprefix(),
|
||||
name=e.name,
|
||||
binary=binary())
|
||||
|
||||
i = 1
|
||||
if len(e.args) > 0:
|
||||
for name in e.args.names():
|
||||
name = stap_escape(name)
|
||||
out(' %s = $arg%d;' % (name, i))
|
||||
i += 1
|
||||
|
||||
out('}')
|
||||
|
||||
out()
|
||||
@@ -0,0 +1,35 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
"""
|
||||
trace/generated-ust.c
|
||||
"""
|
||||
|
||||
__author__ = "Mohamad Gebai <[email protected]>"
|
||||
__copyright__ = "Copyright 2012, Mohamad Gebai <[email protected]>"
|
||||
__license__ = "GPL version 2 or (at your option) any later version"
|
||||
|
||||
__maintainer__ = "Stefan Hajnoczi"
|
||||
__email__ = "[email protected]"
|
||||
|
||||
|
||||
from tracetool import out
|
||||
|
||||
|
||||
def generate(events, backend, group):
|
||||
events = [e for e in events
|
||||
if "disabled" not in e.properties]
|
||||
|
||||
out('/* This file is autogenerated by tracetool, do not edit. */',
|
||||
'/* SPDX-License-Identifier: GPL-2.0-or-later */',
|
||||
'',
|
||||
'#include "qemu/osdep.h"',
|
||||
'',
|
||||
'#define TRACEPOINT_DEFINE',
|
||||
'#define TRACEPOINT_CREATE_PROBES',
|
||||
'',
|
||||
'/* If gcc version 4.7 or older is used, LTTng ust gives a warning when compiling with',
|
||||
' -Wredundant-decls.',
|
||||
' */',
|
||||
'#pragma GCC diagnostic ignored "-Wredundant-decls"',
|
||||
'',
|
||||
'#include "trace-ust-all.h"')
|
||||
@@ -0,0 +1,106 @@
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
"""
|
||||
trace/generated-ust-provider.h
|
||||
"""
|
||||
|
||||
__author__ = "Mohamad Gebai <[email protected]>"
|
||||
__copyright__ = "Copyright 2012, Mohamad Gebai <[email protected]>"
|
||||
__license__ = "GPL version 2 or (at your option) any later version"
|
||||
|
||||
__maintainer__ = "Stefan Hajnoczi"
|
||||
__email__ = "[email protected]"
|
||||
|
||||
|
||||
from tracetool import out
|
||||
|
||||
|
||||
def generate(events, backend, group):
|
||||
events = [e for e in events
|
||||
if "disabled" not in e.properties]
|
||||
|
||||
if group == "all":
|
||||
include = "trace-ust-all.h"
|
||||
else:
|
||||
include = "trace-ust.h"
|
||||
|
||||
out('/* This file is autogenerated by tracetool, do not edit. */',
|
||||
'/* SPDX-License-Identifier: GPL-2.0-or-later */',
|
||||
'',
|
||||
'#undef TRACEPOINT_PROVIDER',
|
||||
'#define TRACEPOINT_PROVIDER qemu',
|
||||
'',
|
||||
'#undef TRACEPOINT_INCLUDE',
|
||||
'#define TRACEPOINT_INCLUDE "./%s"' % include,
|
||||
'',
|
||||
'#if !defined (TRACE_%s_GENERATED_UST_H) || \\' % group.upper(),
|
||||
' defined(TRACEPOINT_HEADER_MULTI_READ)',
|
||||
'#define TRACE_%s_GENERATED_UST_H' % group.upper(),
|
||||
'',
|
||||
'#include <lttng/tracepoint.h>',
|
||||
'',
|
||||
'/*',
|
||||
' * LTTng ust 2.0 does not allow you to use TP_ARGS(void) for tracepoints',
|
||||
' * requiring no arguments. We define these macros introduced in more recent'
|
||||
' * versions of LTTng ust as a workaround',
|
||||
' */',
|
||||
'#ifndef _TP_EXPROTO1',
|
||||
'#define _TP_EXPROTO1(a) void',
|
||||
'#endif',
|
||||
'#ifndef _TP_EXDATA_PROTO1',
|
||||
'#define _TP_EXDATA_PROTO1(a) void *__tp_data',
|
||||
'#endif',
|
||||
'#ifndef _TP_EXDATA_VAR1',
|
||||
'#define _TP_EXDATA_VAR1(a) __tp_data',
|
||||
'#endif',
|
||||
'#ifndef _TP_EXVAR1',
|
||||
'#define _TP_EXVAR1(a)',
|
||||
'#endif',
|
||||
'')
|
||||
|
||||
for e in events:
|
||||
if len(e.args) > 0:
|
||||
out('TRACEPOINT_EVENT(',
|
||||
' qemu,',
|
||||
' %(name)s,',
|
||||
' TP_ARGS(%(args)s),',
|
||||
' TP_FIELDS(',
|
||||
name=e.name,
|
||||
args=", ".join(", ".join(i) for i in e.args))
|
||||
|
||||
types = e.args.types()
|
||||
names = e.args.names()
|
||||
fmts = e.formats()
|
||||
for t,n,f in zip(types, names, fmts):
|
||||
if ('char *' in t) or ('char*' in t):
|
||||
out(' ctf_string(' + n + ', ' + n + ')')
|
||||
elif ("%p" in f) or ("x" in f) or ("PRIx" in f):
|
||||
out(' ctf_integer_hex('+ t + ', ' + n + ', ' + n + ')')
|
||||
elif ("ptr" in t) or ("*" in t):
|
||||
out(' ctf_integer_hex('+ t + ', ' + n + ', ' + n + ')')
|
||||
elif ('int' in t) or ('long' in t) or ('unsigned' in t) \
|
||||
or ('size_t' in t) or ('bool' in t):
|
||||
out(' ctf_integer(' + t + ', ' + n + ', ' + n + ')')
|
||||
elif ('double' in t) or ('float' in t):
|
||||
out(' ctf_float(' + t + ', ' + n + ', ' + n + ')')
|
||||
elif ('void *' in t) or ('void*' in t):
|
||||
out(' ctf_integer_hex(unsigned long, ' + n + ', ' + n + ')')
|
||||
|
||||
out(' )',
|
||||
')',
|
||||
'')
|
||||
|
||||
else:
|
||||
out('TRACEPOINT_EVENT(',
|
||||
' qemu,',
|
||||
' %(name)s,',
|
||||
' TP_ARGS(void),',
|
||||
' TP_FIELDS()',
|
||||
')',
|
||||
'',
|
||||
name=e.name)
|
||||
|
||||
out('#endif /* TRACE_%s_GENERATED_UST_H */' % group.upper(),
|
||||
'',
|
||||
'/* This part must be outside ifdef protection */',
|
||||
'#include <lttng/tracepoint-event.h>')
|
||||
Reference in New Issue
Block a user