* [Qemu-devel] [PATCH v2 1/2] trace: include CPU index in trace_memory_region_*()
@ 2016-03-02 20:12 Hollis Blanchard
2016-03-02 20:12 ` [Qemu-devel] [PATCH v2 2/2] trace: separate MMIO tracepoints from TB-access tracepoints Hollis Blanchard
2016-03-04 15:12 ` [Qemu-devel] [PATCH v2 1/2] trace: include CPU index in trace_memory_region_*() Stefan Hajnoczi
0 siblings, 2 replies; 4+ messages in thread
From: Hollis Blanchard @ 2016-03-02 20:12 UTC (permalink / raw)
To: stefanha; +Cc: Hollis Blanchard, qemu-devel
Knowing which CPU performed an action is essential for understanding SMP guest
behavior.
However, cpu_physical_memory_rw() may be executed by a machine init function,
before any VCPUs are running, when there is no CPU running ('current_cpu' is
NULL). In this case, store -1 in the trace record as the CPU index. Trace
analysis tools may need to be aware of this special case.
Signed-off-by: Hollis Blanchard <hollis_blanchard@mentor.com>
---
v2: use get_cpu_index() helper function
---
memory.c | 32 ++++++++++++++++++++------------
trace-events | 8 ++++----
2 files changed, 24 insertions(+), 16 deletions(-)
diff --git a/memory.c b/memory.c
index 013c2ed..89395e6 100644
--- a/memory.c
+++ b/memory.c
@@ -386,6 +386,14 @@ static hwaddr memory_region_to_absolute_addr(MemoryRegion *mr, hwaddr offset)
return abs_addr;
}
+static int get_cpu_index(void)
+{
+ if (current_cpu) {
+ return current_cpu->cpu_index;
+ }
+ return -1;
+}
+
static MemTxResult memory_region_oldmmio_read_accessor(MemoryRegion *mr,
hwaddr addr,
uint64_t *value,
@@ -398,10 +406,10 @@ static MemTxResult memory_region_oldmmio_read_accessor(MemoryRegion *mr,
tmp = mr->ops->old_mmio.read[ctz32(size)](mr->opaque, addr);
if (mr->subpage) {
- trace_memory_region_subpage_read(mr, addr, tmp, size);
+ trace_memory_region_subpage_read(get_cpu_index(), mr, addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_READ_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
- trace_memory_region_ops_read(mr, abs_addr, tmp, size);
+ trace_memory_region_ops_read(get_cpu_index(), mr, abs_addr, tmp, size);
}
*value |= (tmp & mask) << shift;
return MEMTX_OK;
@@ -419,10 +427,10 @@ static MemTxResult memory_region_read_accessor(MemoryRegion *mr,
tmp = mr->ops->read(mr->opaque, addr, size);
if (mr->subpage) {
- trace_memory_region_subpage_read(mr, addr, tmp, size);
+ trace_memory_region_subpage_read(get_cpu_index(), mr, addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_READ_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
- trace_memory_region_ops_read(mr, abs_addr, tmp, size);
+ trace_memory_region_ops_read(get_cpu_index(), mr, abs_addr, tmp, size);
}
*value |= (tmp & mask) << shift;
return MEMTX_OK;
@@ -441,10 +449,10 @@ static MemTxResult memory_region_read_with_attrs_accessor(MemoryRegion *mr,
r = mr->ops->read_with_attrs(mr->opaque, addr, &tmp, size, attrs);
if (mr->subpage) {
- trace_memory_region_subpage_read(mr, addr, tmp, size);
+ trace_memory_region_subpage_read(get_cpu_index(), mr, addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_READ_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
- trace_memory_region_ops_read(mr, abs_addr, tmp, size);
+ trace_memory_region_ops_read(get_cpu_index(), mr, abs_addr, tmp, size);
}
*value |= (tmp & mask) << shift;
return r;
@@ -462,10 +470,10 @@ static MemTxResult memory_region_oldmmio_write_accessor(MemoryRegion *mr,
tmp = (*value >> shift) & mask;
if (mr->subpage) {
- trace_memory_region_subpage_write(mr, addr, tmp, size);
+ trace_memory_region_subpage_write(get_cpu_index(), mr, addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_WRITE_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
- trace_memory_region_ops_write(mr, abs_addr, tmp, size);
+ trace_memory_region_ops_write(get_cpu_index(), mr, abs_addr, tmp, size);
}
mr->ops->old_mmio.write[ctz32(size)](mr->opaque, addr, tmp);
return MEMTX_OK;
@@ -483,10 +491,10 @@ static MemTxResult memory_region_write_accessor(MemoryRegion *mr,
tmp = (*value >> shift) & mask;
if (mr->subpage) {
- trace_memory_region_subpage_write(mr, addr, tmp, size);
+ trace_memory_region_subpage_write(get_cpu_index(), mr, addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_WRITE_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
- trace_memory_region_ops_write(mr, abs_addr, tmp, size);
+ trace_memory_region_ops_write(get_cpu_index(), mr, abs_addr, tmp, size);
}
mr->ops->write(mr->opaque, addr, tmp, size);
return MEMTX_OK;
@@ -504,10 +512,10 @@ static MemTxResult memory_region_write_with_attrs_accessor(MemoryRegion *mr,
tmp = (*value >> shift) & mask;
if (mr->subpage) {
- trace_memory_region_subpage_write(mr, addr, tmp, size);
+ trace_memory_region_subpage_write(get_cpu_index(), mr, addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_WRITE_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
- trace_memory_region_ops_write(mr, abs_addr, tmp, size);
+ trace_memory_region_ops_write(get_cpu_index(), mr, abs_addr, tmp, size);
}
return mr->ops->write_with_attrs(mr->opaque, addr, tmp, size, attrs);
}
diff --git a/trace-events b/trace-events
index 6fba6cc..a9f33fb 100644
--- a/trace-events
+++ b/trace-events
@@ -1620,10 +1620,10 @@ disable exec_tb_exit(void *next_tb, unsigned int flags) "tb:%p flags=%x"
translate_block(void *tb, uintptr_t pc, uint8_t *tb_code) "tb:%p, pc:0x%"PRIxPTR", tb_code:%p"
# memory.c
-memory_region_ops_read(void *mr, uint64_t addr, uint64_t value, unsigned size) "mr %p addr %#"PRIx64" value %#"PRIx64" size %u"
-memory_region_ops_write(void *mr, uint64_t addr, uint64_t value, unsigned size) "mr %p addr %#"PRIx64" value %#"PRIx64" size %u"
-memory_region_subpage_read(void *mr, uint64_t offset, uint64_t value, unsigned size) "mr %p offset %#"PRIx64" value %#"PRIx64" size %u"
-memory_region_subpage_write(void *mr, uint64_t offset, uint64_t value, unsigned size) "mr %p offset %#"PRIx64" value %#"PRIx64" size %u"
+memory_region_ops_read(int cpu_index, void *mr, uint64_t addr, uint64_t value, unsigned size) "cpu %d mr %p addr %#"PRIx64" value %#"PRIx64" size %u"
+memory_region_ops_write(int cpu_index, void *mr, uint64_t addr, uint64_t value, unsigned size) "cpu %d mr %p addr %#"PRIx64" value %#"PRIx64" size %u"
+memory_region_subpage_read(int cpu_index, void *mr, uint64_t offset, uint64_t value, unsigned size) "cpu %d mr %p offset %#"PRIx64" value %#"PRIx64" size %u"
+memory_region_subpage_write(int cpu_index, void *mr, uint64_t offset, uint64_t value, unsigned size) "cpu %d mr %p offset %#"PRIx64" value %#"PRIx64" size %u"
# qom/object.c
object_dynamic_cast_assert(const char *type, const char *target, const char *file, int line, const char *func) "%s->%s (%s:%d:%s)"
--
1.9.1
^ permalink raw reply related [flat|nested] 4+ messages in thread
* [Qemu-devel] [PATCH v2 2/2] trace: separate MMIO tracepoints from TB-access tracepoints
2016-03-02 20:12 [Qemu-devel] [PATCH v2 1/2] trace: include CPU index in trace_memory_region_*() Hollis Blanchard
@ 2016-03-02 20:12 ` Hollis Blanchard
2016-03-07 21:32 ` Hollis Blanchard
2016-03-04 15:12 ` [Qemu-devel] [PATCH v2 1/2] trace: include CPU index in trace_memory_region_*() Stefan Hajnoczi
1 sibling, 1 reply; 4+ messages in thread
From: Hollis Blanchard @ 2016-03-02 20:12 UTC (permalink / raw)
To: stefanha; +Cc: Hollis Blanchard, qemu-devel
Memory accesses to code which has previously been translated into a TB show up
in the MMIO path, so that they may invalidate the TB. It's extremely confusing
to mix those in with device MMIOs, so split them into their own tracepoint.
Signed-off-by: Hollis Blanchard <hollis_blanchard@mentor.com>
Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
---
It took many hours to figure out why some RAM accesses were coming through the
MMIO path instead of being handled inline in the TBs.
On IRC, Paolo expressed some concern about performance, but ultimately agreed
that adding one conditional to an already heavy codepath wouldn't have much
impact.
v2: rename trace_memory_region_ops_tb_read/write to
trace_memory_region_tb_read/write
---
memory.c | 30 ++++++++++++++++++++++++++++++
trace-events | 2 ++
2 files changed, 32 insertions(+)
diff --git a/memory.c b/memory.c
index 89395e6..84347fa 100644
--- a/memory.c
+++ b/memory.c
@@ -407,6 +407,11 @@ static MemTxResult memory_region_oldmmio_read_accessor(MemoryRegion *mr,
tmp = mr->ops->old_mmio.read[ctz32(size)](mr->opaque, addr);
if (mr->subpage) {
trace_memory_region_subpage_read(get_cpu_index(), mr, addr, tmp, size);
+ } else if (mr == &io_mem_notdirty) {
+ /* Accesses to code which has previously been translated into a TB show
+ * up in the MMIO path, as accesses to the io_mem_notdirty
+ * MemoryRegion. */
+ trace_memory_region_tb_read(get_cpu_index(), addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_READ_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
trace_memory_region_ops_read(get_cpu_index(), mr, abs_addr, tmp, size);
@@ -428,6 +433,11 @@ static MemTxResult memory_region_read_accessor(MemoryRegion *mr,
tmp = mr->ops->read(mr->opaque, addr, size);
if (mr->subpage) {
trace_memory_region_subpage_read(get_cpu_index(), mr, addr, tmp, size);
+ } else if (mr == &io_mem_notdirty) {
+ /* Accesses to code which has previously been translated into a TB show
+ * up in the MMIO path, as accesses to the io_mem_notdirty
+ * MemoryRegion. */
+ trace_memory_region_tb_read(get_cpu_index(), addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_READ_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
trace_memory_region_ops_read(get_cpu_index(), mr, abs_addr, tmp, size);
@@ -450,6 +460,11 @@ static MemTxResult memory_region_read_with_attrs_accessor(MemoryRegion *mr,
r = mr->ops->read_with_attrs(mr->opaque, addr, &tmp, size, attrs);
if (mr->subpage) {
trace_memory_region_subpage_read(get_cpu_index(), mr, addr, tmp, size);
+ } else if (mr == &io_mem_notdirty) {
+ /* Accesses to code which has previously been translated into a TB show
+ * up in the MMIO path, as accesses to the io_mem_notdirty
+ * MemoryRegion. */
+ trace_memory_region_tb_read(get_cpu_index(), addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_READ_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
trace_memory_region_ops_read(get_cpu_index(), mr, abs_addr, tmp, size);
@@ -471,6 +486,11 @@ static MemTxResult memory_region_oldmmio_write_accessor(MemoryRegion *mr,
tmp = (*value >> shift) & mask;
if (mr->subpage) {
trace_memory_region_subpage_write(get_cpu_index(), mr, addr, tmp, size);
+ } else if (mr == &io_mem_notdirty) {
+ /* Accesses to code which has previously been translated into a TB show
+ * up in the MMIO path, as accesses to the io_mem_notdirty
+ * MemoryRegion. */
+ trace_memory_region_tb_write(get_cpu_index(), addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_WRITE_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
trace_memory_region_ops_write(get_cpu_index(), mr, abs_addr, tmp, size);
@@ -492,6 +512,11 @@ static MemTxResult memory_region_write_accessor(MemoryRegion *mr,
tmp = (*value >> shift) & mask;
if (mr->subpage) {
trace_memory_region_subpage_write(get_cpu_index(), mr, addr, tmp, size);
+ } else if (mr == &io_mem_notdirty) {
+ /* Accesses to code which has previously been translated into a TB show
+ * up in the MMIO path, as accesses to the io_mem_notdirty
+ * MemoryRegion. */
+ trace_memory_region_tb_write(get_cpu_index(), addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_WRITE_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
trace_memory_region_ops_write(get_cpu_index(), mr, abs_addr, tmp, size);
@@ -513,6 +538,11 @@ static MemTxResult memory_region_write_with_attrs_accessor(MemoryRegion *mr,
tmp = (*value >> shift) & mask;
if (mr->subpage) {
trace_memory_region_subpage_write(get_cpu_index(), mr, addr, tmp, size);
+ } else if (mr == &io_mem_notdirty) {
+ /* Accesses to code which has previously been translated into a TB show
+ * up in the MMIO path, as accesses to the io_mem_notdirty
+ * MemoryRegion. */
+ trace_memory_region_tb_write(get_cpu_index(), addr, tmp, size);
} else if (TRACE_MEMORY_REGION_OPS_WRITE_ENABLED) {
hwaddr abs_addr = memory_region_to_absolute_addr(mr, addr);
trace_memory_region_ops_write(get_cpu_index(), mr, abs_addr, tmp, size);
diff --git a/trace-events b/trace-events
index a9f33fb..5d0d483 100644
--- a/trace-events
+++ b/trace-events
@@ -1624,6 +1624,8 @@ memory_region_ops_read(int cpu_index, void *mr, uint64_t addr, uint64_t value, u
memory_region_ops_write(int cpu_index, void *mr, uint64_t addr, uint64_t value, unsigned size) "cpu %d mr %p addr %#"PRIx64" value %#"PRIx64" size %u"
memory_region_subpage_read(int cpu_index, void *mr, uint64_t offset, uint64_t value, unsigned size) "cpu %d mr %p offset %#"PRIx64" value %#"PRIx64" size %u"
memory_region_subpage_write(int cpu_index, void *mr, uint64_t offset, uint64_t value, unsigned size) "cpu %d mr %p offset %#"PRIx64" value %#"PRIx64" size %u"
+memory_region_tb_read(int cpu_index, uint64_t addr, uint64_t value, unsigned size) "cpu %d addr %#"PRIx64" value %#"PRIx64" size %u"
+memory_region_tb_write(int cpu_index, uint64_t addr, uint64_t value, unsigned size) "cpu %d addr %#"PRIx64" value %#"PRIx64" size %u"
# qom/object.c
object_dynamic_cast_assert(const char *type, const char *target, const char *file, int line, const char *func) "%s->%s (%s:%d:%s)"
--
1.9.1
^ permalink raw reply related [flat|nested] 4+ messages in thread
* Re: [Qemu-devel] [PATCH v2 1/2] trace: include CPU index in trace_memory_region_*()
2016-03-02 20:12 [Qemu-devel] [PATCH v2 1/2] trace: include CPU index in trace_memory_region_*() Hollis Blanchard
2016-03-02 20:12 ` [Qemu-devel] [PATCH v2 2/2] trace: separate MMIO tracepoints from TB-access tracepoints Hollis Blanchard
@ 2016-03-04 15:12 ` Stefan Hajnoczi
1 sibling, 0 replies; 4+ messages in thread
From: Stefan Hajnoczi @ 2016-03-04 15:12 UTC (permalink / raw)
To: Hollis Blanchard; +Cc: qemu-devel
[-- Attachment #1: Type: text/plain, Size: 831 bytes --]
On Wed, Mar 02, 2016 at 12:12:54PM -0800, Hollis Blanchard wrote:
> Knowing which CPU performed an action is essential for understanding SMP guest
> behavior.
>
> However, cpu_physical_memory_rw() may be executed by a machine init function,
> before any VCPUs are running, when there is no CPU running ('current_cpu' is
> NULL). In this case, store -1 in the trace record as the CPU index. Trace
> analysis tools may need to be aware of this special case.
>
> Signed-off-by: Hollis Blanchard <hollis_blanchard@mentor.com>
> ---
> v2: use get_cpu_index() helper function
> ---
> memory.c | 32 ++++++++++++++++++++------------
> trace-events | 8 ++++----
> 2 files changed, 24 insertions(+), 16 deletions(-)
Thanks, applied to my tracing tree:
https://github.com/stefanha/qemu/commits/tracing
Stefan
[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 473 bytes --]
^ permalink raw reply [flat|nested] 4+ messages in thread
* Re: [Qemu-devel] [PATCH v2 2/2] trace: separate MMIO tracepoints from TB-access tracepoints
2016-03-02 20:12 ` [Qemu-devel] [PATCH v2 2/2] trace: separate MMIO tracepoints from TB-access tracepoints Hollis Blanchard
@ 2016-03-07 21:32 ` Hollis Blanchard
0 siblings, 0 replies; 4+ messages in thread
From: Hollis Blanchard @ 2016-03-07 21:32 UTC (permalink / raw)
To: stefanha; +Cc: qemu-devel
[-- Attachment #1: Type: text/plain, Size: 1133 bytes --]
On Wed, 2016-03-02 at 12:12 -0800, Hollis Blanchard wrote:
> Memory accesses to code which has previously been translated into a
> TB show up
> in the MMIO path, so that they may invalidate the TB. It's extremely
> confusing
> to mix those in with device MMIOs, so split them into their own
> tracepoint.
>
> Signed-off-by: Hollis Blanchard <hollis_blanchard@mentor.com>
> Reviewed-by: Stefan Hajnoczi <stefanha@redhat.com>
> ---
> It took many hours to figure out why some RAM accesses were coming
> through the
> MMIO path instead of being handled inline in the TBs.
>
> On IRC, Paolo expressed some concern about performance, but
> ultimately agreed
> that adding one conditional to an already heavy codepath wouldn't
> have much
> impact.
>
> v2: rename trace_memory_region_ops_tb_read/write to
> trace_memory_region_tb_read/write
>
Stefan, any further comment here? You sent a Reviewed-by on the
original, but unlike the "include CPU index" patch, you didn't mention
adding this one to https://github.com/stefanha/qemu/commits/tracing.
--
Hollis Blanchard <hollis_blanchard@mentor.com>
Mentor Graphics Emulation Division
[-- Attachment #2: Type: text/html, Size: 1610 bytes --]
^ permalink raw reply [flat|nested] 4+ messages in thread
end of thread, other threads:[~2016-03-07 21:32 UTC | newest]
Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2016-03-02 20:12 [Qemu-devel] [PATCH v2 1/2] trace: include CPU index in trace_memory_region_*() Hollis Blanchard
2016-03-02 20:12 ` [Qemu-devel] [PATCH v2 2/2] trace: separate MMIO tracepoints from TB-access tracepoints Hollis Blanchard
2016-03-07 21:32 ` Hollis Blanchard
2016-03-04 15:12 ` [Qemu-devel] [PATCH v2 1/2] trace: include CPU index in trace_memory_region_*() Stefan Hajnoczi
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).