trace: [qmp] Add commands to query and control event tracing state
Signed-off-by: Lluís Vilanova <vilanova@ac.upc.edu> Message-id: 20140825111957.31112.31733.stgit@fimbulvetr.bsc.es Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
This commit is contained in:
parent
60e17d2822
commit
1dde0f48d5
@ -11,6 +11,9 @@
|
|||||||
# QAPI event definitions
|
# QAPI event definitions
|
||||||
{ 'include': 'qapi/event.json' }
|
{ 'include': 'qapi/event.json' }
|
||||||
|
|
||||||
|
# Tracing commands
|
||||||
|
{ 'include': 'qapi/trace.json' }
|
||||||
|
|
||||||
##
|
##
|
||||||
# LostTickPolicy:
|
# LostTickPolicy:
|
||||||
#
|
#
|
||||||
|
65
qapi/trace.json
Normal file
65
qapi/trace.json
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
# -*- mode: python -*-
|
||||||
|
#
|
||||||
|
# Copyright (C) 2011-2014 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.
|
||||||
|
|
||||||
|
|
||||||
|
##
|
||||||
|
# @TraceEventState:
|
||||||
|
#
|
||||||
|
# State of a tracing event.
|
||||||
|
#
|
||||||
|
# @unavailable: The event is statically disabled.
|
||||||
|
#
|
||||||
|
# @disabled: The event is dynamically disabled.
|
||||||
|
#
|
||||||
|
# @enabled: The event is dynamically enabled.
|
||||||
|
#
|
||||||
|
# Since 2.2
|
||||||
|
##
|
||||||
|
{ 'enum': 'TraceEventState',
|
||||||
|
'data': ['unavailable', 'disabled', 'enabled'] }
|
||||||
|
|
||||||
|
##
|
||||||
|
# @TraceEventInfo:
|
||||||
|
#
|
||||||
|
# Information of a tracing event.
|
||||||
|
#
|
||||||
|
# @name: Event name.
|
||||||
|
# @state: Tracing state.
|
||||||
|
#
|
||||||
|
# Since 2.2
|
||||||
|
##
|
||||||
|
{ 'type': 'TraceEventInfo',
|
||||||
|
'data': {'name': 'str', 'state': 'TraceEventState'} }
|
||||||
|
|
||||||
|
##
|
||||||
|
# @trace-event-get-state:
|
||||||
|
#
|
||||||
|
# Query the state of events.
|
||||||
|
#
|
||||||
|
# @name: Event name pattern (case-sensitive glob).
|
||||||
|
#
|
||||||
|
# Returns: a list of @TraceEventInfo for the matching events
|
||||||
|
#
|
||||||
|
# Since 2.2
|
||||||
|
##
|
||||||
|
{ 'command': 'trace-event-get-state',
|
||||||
|
'data': {'name': 'str'},
|
||||||
|
'returns': ['TraceEventInfo'] }
|
||||||
|
|
||||||
|
##
|
||||||
|
# @trace-event-set-state:
|
||||||
|
#
|
||||||
|
# Set the dynamic tracing state of events.
|
||||||
|
#
|
||||||
|
# @name: Event name pattern (case-sensitive glob).
|
||||||
|
# @enable: Whether to enable tracing.
|
||||||
|
# @ignore-unavailable: #optional Do not match unavailable events with @name.
|
||||||
|
#
|
||||||
|
# Since 2.2
|
||||||
|
##
|
||||||
|
{ 'command': 'trace-event-set-state',
|
||||||
|
'data': {'name': 'str', 'enable': 'bool', '*ignore-unavailable': 'bool'} }
|
@ -3752,5 +3752,40 @@ Example:
|
|||||||
|
|
||||||
-> { "execute": "rtc-reset-reinjection" }
|
-> { "execute": "rtc-reset-reinjection" }
|
||||||
<- { "return": {} }
|
<- { "return": {} }
|
||||||
|
EQMP
|
||||||
|
|
||||||
|
{
|
||||||
|
.name = "trace-event-get-state",
|
||||||
|
.args_type = "name:s",
|
||||||
|
.mhandler.cmd_new = qmp_marshal_input_trace_event_get_state,
|
||||||
|
},
|
||||||
|
|
||||||
|
SQMP
|
||||||
|
trace-event-get-state
|
||||||
|
---------------------
|
||||||
|
|
||||||
|
Query the state of events.
|
||||||
|
|
||||||
|
Example:
|
||||||
|
|
||||||
|
-> { "execute": "trace-event-get-state", "arguments": { "name": "qemu_memalign" } }
|
||||||
|
<- { "return": [ { "name": "qemu_memalign", "state": "disabled" } ] }
|
||||||
|
EQMP
|
||||||
|
|
||||||
|
{
|
||||||
|
.name = "trace-event-set-state",
|
||||||
|
.args_type = "name:s,enable:b,ignore-unavailable:b?",
|
||||||
|
.mhandler.cmd_new = qmp_marshal_input_trace_event_set_state,
|
||||||
|
},
|
||||||
|
|
||||||
|
SQMP
|
||||||
|
trace-event-set-state
|
||||||
|
---------------------
|
||||||
|
|
||||||
|
Set the state of events.
|
||||||
|
|
||||||
|
Example:
|
||||||
|
|
||||||
|
-> { "execute": "trace-event-set-state", "arguments": { "name": "qemu_memalign", "enable": "true" } }
|
||||||
|
<- { "return": {} }
|
||||||
EQMP
|
EQMP
|
||||||
|
@ -144,3 +144,4 @@ util-obj-$(CONFIG_TRACE_SIMPLE) += simple.o generated-tracers.o
|
|||||||
util-obj-$(CONFIG_TRACE_FTRACE) += ftrace.o
|
util-obj-$(CONFIG_TRACE_FTRACE) += ftrace.o
|
||||||
util-obj-$(CONFIG_TRACE_UST) += generated-ust.o
|
util-obj-$(CONFIG_TRACE_UST) += generated-ust.o
|
||||||
util-obj-y += control.o
|
util-obj-y += control.o
|
||||||
|
util-obj-y += qmp.o
|
||||||
|
75
trace/qmp.c
Normal file
75
trace/qmp.c
Normal file
@ -0,0 +1,75 @@
|
|||||||
|
/*
|
||||||
|
* QMP commands for tracing events.
|
||||||
|
*
|
||||||
|
* Copyright (C) 2014 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 "qemu/typedefs.h"
|
||||||
|
#include "qmp-commands.h"
|
||||||
|
#include "trace/control.h"
|
||||||
|
|
||||||
|
|
||||||
|
TraceEventInfoList *qmp_trace_event_get_state(const char *name, Error **errp)
|
||||||
|
{
|
||||||
|
TraceEventInfoList *events = NULL;
|
||||||
|
bool found = false;
|
||||||
|
TraceEvent *ev;
|
||||||
|
|
||||||
|
ev = NULL;
|
||||||
|
while ((ev = trace_event_pattern(name, ev)) != NULL) {
|
||||||
|
TraceEventInfoList *elem = g_new(TraceEventInfoList, 1);
|
||||||
|
elem->value = g_new(TraceEventInfo, 1);
|
||||||
|
elem->value->name = g_strdup(trace_event_get_name(ev));
|
||||||
|
if (!trace_event_get_state_static(ev)) {
|
||||||
|
elem->value->state = TRACE_EVENT_STATE_UNAVAILABLE;
|
||||||
|
} else if (!trace_event_get_state_dynamic(ev)) {
|
||||||
|
elem->value->state = TRACE_EVENT_STATE_DISABLED;
|
||||||
|
} else {
|
||||||
|
elem->value->state = TRACE_EVENT_STATE_ENABLED;
|
||||||
|
}
|
||||||
|
elem->next = events;
|
||||||
|
events = elem;
|
||||||
|
found = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!found && !trace_event_is_pattern(name)) {
|
||||||
|
error_setg(errp, "unknown event \"%s\"", name);
|
||||||
|
}
|
||||||
|
|
||||||
|
return events;
|
||||||
|
}
|
||||||
|
|
||||||
|
void qmp_trace_event_set_state(const char *name, bool enable,
|
||||||
|
bool has_ignore_unavailable,
|
||||||
|
bool ignore_unavailable, Error **errp)
|
||||||
|
{
|
||||||
|
bool found = false;
|
||||||
|
TraceEvent *ev;
|
||||||
|
|
||||||
|
/* Check all selected events are dynamic */
|
||||||
|
ev = NULL;
|
||||||
|
while ((ev = trace_event_pattern(name, ev)) != NULL) {
|
||||||
|
found = true;
|
||||||
|
if (!(has_ignore_unavailable && ignore_unavailable) &&
|
||||||
|
!trace_event_get_state_static(ev)) {
|
||||||
|
error_setg(errp, "cannot set dynamic tracing state for \"%s\"",
|
||||||
|
trace_event_get_name(ev));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!found && !trace_event_is_pattern(name)) {
|
||||||
|
error_setg(errp, "unknown event \"%s\"", name);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Apply changes */
|
||||||
|
ev = NULL;
|
||||||
|
while ((ev = trace_event_pattern(name, ev)) != NULL) {
|
||||||
|
if (trace_event_get_state_static(ev)) {
|
||||||
|
trace_event_set_state_dynamic(ev, enable);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user