accel/tcg/plugin-gen.c | 30 +++ gdbstub/gdbstub.c | 2 +- include/exec/gdbstub.h | 14 ++ include/hw/core/cpu.h | 1 + include/qemu/plugin.h | 15 ++ include/qemu/qemu-plugin.h | 176 ++++++++++++++-- plugins/api.c | 135 +++++++++++- plugins/core.c | 33 +++ tests/tcg/Makefile.target | 1 + tests/tcg/plugins/meson.build | 2 +- tests/tcg/plugins/patch.c | 241 ++++++++++++++++++++++ tests/tcg/x86_64/Makefile.softmmu-target | 32 ++- tests/tcg/x86_64/system/patch-target.c | 27 +++ tests/tcg/x86_64/system/validate-patch.py | 39 ++++ 14 files changed, 725 insertions(+), 23 deletions(-) create mode 100644 tests/tcg/plugins/patch.c create mode 100644 tests/tcg/x86_64/system/patch-target.c create mode 100755 tests/tcg/x86_64/system/validate-patch.py
This patch series adds several new API functions focused on enabling use
cases around reading and writing guest memory from QEMU plugins. To support
these new APIs, some utility functionality around retrieving information about
address spaces is added as well.
The new qemu_plugin_write_register utilizes gdb_write_register, which is now
declared in gdbstub.h for this purpose instead of being static.
qemu_plugin_write_memory_vaddr utilizes cpu_memory_rw_debug much the same as
the existing read_memory_vaddr function does.
The read and write_hwaddr functions are the most different. These functions
use address_space_rw, which works well in most cases. There is an important
caveat that for writes, the page being written will be set dirty by the
write operation. This dirty setting requires locking the page range,
which can contend with an already held lock in page_collection_lock
when called in a tb translate callback with a write to the instruction
memory in the tb. The doc comments warn against doing this, and it's unlikely
anyone would want to do this.
I've also added two test plugins: one that implements a simple hypercall
interface that guest code can use to communicate with the plugin in a
structured way with a test to ensure that this hypercall works and writing
virtual memory works. And one that implements a simple patch utility to patch
memory at runtime. The test for the second plugin ensures the patch applies
successfully to instruction memory, and can use both hw and vaddr methods.
For v3, I've had a few comments from the last submission that I've addressed,
and some that I haven't for one reason or another:
- Enforce QEMU_PLUGIN_CB_ flags in register read/write operations: done!
- Fix my commit messages and add long messages describing commits: done!
- Un-expose AS internals: done! Functions operate on current vCPU, current AS.
- Clean up use of current_cpu: done!
- Make functions take a vcpu_idx: not done. May revisit but it allows footguns.
Even for translation, seems best to not do this now. We can easily add _vcpu
versions of these functions in the future if we change our minds!
For v5, I've just updated the enforcement of the QEMU_PLUGIN_CB_ flags to just
use immediate stores, which simplifies the implementation quite a lot and
should be more efficient too. Thanks Pierrick for the suggestion!
v6 is a formatting pass, I left some whitespace that needed removal, some
license text was wrong, and so forth.
v8 reverts a mistake I made extending the size of arrays of TCGHelperInfo
structs, as I misunderstood their sizes. It preserves adding an explicit
zero as the last entry for clarity, however.
v9 fixes qemu_plugin_read_register to return -1 on parameter or flag state
error instead of 0.
In v10, I relaxed the restriction on when the register r/w functions can be
called, allowing all them to be used from any callback where the CPU is not
currently executing, with additional notes in the documentation for exceptions
(atexit and flush, which do not operate on a specific CPU and in which
current_cpu is not set).
v11 makes the cb flags functions inline and fixes a typo where cpu was asserted
but current_cpu was actually accessed.
v12 removes the hypercalls plugin because the functions it tested are also
tested by the patcher plugin, making it redundant. We'll circle back on a
hypercalls API in the future as a part of the plugin API, not as a plugin
itself.
Rowan Hart (1):
plugins: Add enforcement of QEMU_PLUGIN_CB flags in register R/W
callbacks
novafacing (6):
gdbstub: Expose gdb_write_register function to consumers of gdbstub
plugins: Add register write API
plugins: Add memory virtual address write API
plugins: Add memory hardware address read/write API
plugins: Add patcher plugin and test
plugins: Update plugin version and add notes
accel/tcg/plugin-gen.c | 30 +++
gdbstub/gdbstub.c | 2 +-
include/exec/gdbstub.h | 14 ++
include/hw/core/cpu.h | 1 +
include/qemu/plugin.h | 15 ++
include/qemu/qemu-plugin.h | 176 ++++++++++++++--
plugins/api.c | 135 +++++++++++-
plugins/core.c | 33 +++
tests/tcg/Makefile.target | 1 +
tests/tcg/plugins/meson.build | 2 +-
tests/tcg/plugins/patch.c | 241 ++++++++++++++++++++++
tests/tcg/x86_64/Makefile.softmmu-target | 32 ++-
tests/tcg/x86_64/system/patch-target.c | 27 +++
tests/tcg/x86_64/system/validate-patch.py | 39 ++++
14 files changed, 725 insertions(+), 23 deletions(-)
create mode 100644 tests/tcg/plugins/patch.c
create mode 100644 tests/tcg/x86_64/system/patch-target.c
create mode 100755 tests/tcg/x86_64/system/validate-patch.py
--
2.49.0
I've updated this patch to address some notes about the build/test configuration for the patch plugin. Please check https://lore.kernel.org/qemu-devel/20250619161547.1401448-1-rowanbhart@gmail.com/T/#t instead. On 6/11/25 4:24 PM, Rowan Hart wrote: > This patch series adds several new API functions focused on enabling use > cases around reading and writing guest memory from QEMU plugins. To support > these new APIs, some utility functionality around retrieving information about > address spaces is added as well. > > The new qemu_plugin_write_register utilizes gdb_write_register, which is now > declared in gdbstub.h for this purpose instead of being static. > > qemu_plugin_write_memory_vaddr utilizes cpu_memory_rw_debug much the same as > the existing read_memory_vaddr function does. > > The read and write_hwaddr functions are the most different. These functions > use address_space_rw, which works well in most cases. There is an important > caveat that for writes, the page being written will be set dirty by the > write operation. This dirty setting requires locking the page range, > which can contend with an already held lock in page_collection_lock > when called in a tb translate callback with a write to the instruction > memory in the tb. The doc comments warn against doing this, and it's unlikely > anyone would want to do this. > > I've also added two test plugins: one that implements a simple hypercall > interface that guest code can use to communicate with the plugin in a > structured way with a test to ensure that this hypercall works and writing > virtual memory works. And one that implements a simple patch utility to patch > memory at runtime. The test for the second plugin ensures the patch applies > successfully to instruction memory, and can use both hw and vaddr methods. > > For v3, I've had a few comments from the last submission that I've addressed, > and some that I haven't for one reason or another: > > - Enforce QEMU_PLUGIN_CB_ flags in register read/write operations: done! > - Fix my commit messages and add long messages describing commits: done! > - Un-expose AS internals: done! Functions operate on current vCPU, current AS. > - Clean up use of current_cpu: done! > - Make functions take a vcpu_idx: not done. May revisit but it allows footguns. > Even for translation, seems best to not do this now. We can easily add _vcpu > versions of these functions in the future if we change our minds! > > For v5, I've just updated the enforcement of the QEMU_PLUGIN_CB_ flags to just > use immediate stores, which simplifies the implementation quite a lot and > should be more efficient too. Thanks Pierrick for the suggestion! > > v6 is a formatting pass, I left some whitespace that needed removal, some > license text was wrong, and so forth. > > v8 reverts a mistake I made extending the size of arrays of TCGHelperInfo > structs, as I misunderstood their sizes. It preserves adding an explicit > zero as the last entry for clarity, however. > > v9 fixes qemu_plugin_read_register to return -1 on parameter or flag state > error instead of 0. > > In v10, I relaxed the restriction on when the register r/w functions can be > called, allowing all them to be used from any callback where the CPU is not > currently executing, with additional notes in the documentation for exceptions > (atexit and flush, which do not operate on a specific CPU and in which > current_cpu is not set). > > v11 makes the cb flags functions inline and fixes a typo where cpu was asserted > but current_cpu was actually accessed. > > v12 removes the hypercalls plugin because the functions it tested are also > tested by the patcher plugin, making it redundant. We'll circle back on a > hypercalls API in the future as a part of the plugin API, not as a plugin > itself. > > Rowan Hart (1): > plugins: Add enforcement of QEMU_PLUGIN_CB flags in register R/W > callbacks > > novafacing (6): > gdbstub: Expose gdb_write_register function to consumers of gdbstub > plugins: Add register write API > plugins: Add memory virtual address write API > plugins: Add memory hardware address read/write API > plugins: Add patcher plugin and test > plugins: Update plugin version and add notes > > accel/tcg/plugin-gen.c | 30 +++ > gdbstub/gdbstub.c | 2 +- > include/exec/gdbstub.h | 14 ++ > include/hw/core/cpu.h | 1 + > include/qemu/plugin.h | 15 ++ > include/qemu/qemu-plugin.h | 176 ++++++++++++++-- > plugins/api.c | 135 +++++++++++- > plugins/core.c | 33 +++ > tests/tcg/Makefile.target | 1 + > tests/tcg/plugins/meson.build | 2 +- > tests/tcg/plugins/patch.c | 241 ++++++++++++++++++++++ > tests/tcg/x86_64/Makefile.softmmu-target | 32 ++- > tests/tcg/x86_64/system/patch-target.c | 27 +++ > tests/tcg/x86_64/system/validate-patch.py | 39 ++++ > 14 files changed, 725 insertions(+), 23 deletions(-) > create mode 100644 tests/tcg/plugins/patch.c > create mode 100644 tests/tcg/x86_64/system/patch-target.c > create mode 100755 tests/tcg/x86_64/system/validate-patch.py >
On 6/11/25 4:24 PM, Rowan Hart wrote: > This patch series adds several new API functions focused on enabling use > cases around reading and writing guest memory from QEMU plugins. To support > these new APIs, some utility functionality around retrieving information about > address spaces is added as well. > > The new qemu_plugin_write_register utilizes gdb_write_register, which is now > declared in gdbstub.h for this purpose instead of being static. > > qemu_plugin_write_memory_vaddr utilizes cpu_memory_rw_debug much the same as > the existing read_memory_vaddr function does. > > The read and write_hwaddr functions are the most different. These functions > use address_space_rw, which works well in most cases. There is an important > caveat that for writes, the page being written will be set dirty by the > write operation. This dirty setting requires locking the page range, > which can contend with an already held lock in page_collection_lock > when called in a tb translate callback with a write to the instruction > memory in the tb. The doc comments warn against doing this, and it's unlikely > anyone would want to do this. > > I've also added two test plugins: one that implements a simple hypercall > interface that guest code can use to communicate with the plugin in a > structured way with a test to ensure that this hypercall works and writing > virtual memory works. And one that implements a simple patch utility to patch > memory at runtime. The test for the second plugin ensures the patch applies > successfully to instruction memory, and can use both hw and vaddr methods. > > For v3, I've had a few comments from the last submission that I've addressed, > and some that I haven't for one reason or another: > > - Enforce QEMU_PLUGIN_CB_ flags in register read/write operations: done! > - Fix my commit messages and add long messages describing commits: done! > - Un-expose AS internals: done! Functions operate on current vCPU, current AS. > - Clean up use of current_cpu: done! > - Make functions take a vcpu_idx: not done. May revisit but it allows footguns. > Even for translation, seems best to not do this now. We can easily add _vcpu > versions of these functions in the future if we change our minds! > > For v5, I've just updated the enforcement of the QEMU_PLUGIN_CB_ flags to just > use immediate stores, which simplifies the implementation quite a lot and > should be more efficient too. Thanks Pierrick for the suggestion! > > v6 is a formatting pass, I left some whitespace that needed removal, some > license text was wrong, and so forth. > > v8 reverts a mistake I made extending the size of arrays of TCGHelperInfo > structs, as I misunderstood their sizes. It preserves adding an explicit > zero as the last entry for clarity, however. > > v9 fixes qemu_plugin_read_register to return -1 on parameter or flag state > error instead of 0. > > In v10, I relaxed the restriction on when the register r/w functions can be > called, allowing all them to be used from any callback where the CPU is not > currently executing, with additional notes in the documentation for exceptions > (atexit and flush, which do not operate on a specific CPU and in which > current_cpu is not set). > > v11 makes the cb flags functions inline and fixes a typo where cpu was asserted > but current_cpu was actually accessed. > > v12 removes the hypercalls plugin because the functions it tested are also > tested by the patcher plugin, making it redundant. We'll circle back on a > hypercalls API in the future as a part of the plugin API, not as a plugin > itself. > > Rowan Hart (1): > plugins: Add enforcement of QEMU_PLUGIN_CB flags in register R/W > callbacks > > novafacing (6): > gdbstub: Expose gdb_write_register function to consumers of gdbstub > plugins: Add register write API > plugins: Add memory virtual address write API > plugins: Add memory hardware address read/write API > plugins: Add patcher plugin and test > plugins: Update plugin version and add notes > > accel/tcg/plugin-gen.c | 30 +++ > gdbstub/gdbstub.c | 2 +- > include/exec/gdbstub.h | 14 ++ > include/hw/core/cpu.h | 1 + > include/qemu/plugin.h | 15 ++ > include/qemu/qemu-plugin.h | 176 ++++++++++++++-- > plugins/api.c | 135 +++++++++++- > plugins/core.c | 33 +++ > tests/tcg/Makefile.target | 1 + > tests/tcg/plugins/meson.build | 2 +- > tests/tcg/plugins/patch.c | 241 ++++++++++++++++++++++ > tests/tcg/x86_64/Makefile.softmmu-target | 32 ++- > tests/tcg/x86_64/system/patch-target.c | 27 +++ > tests/tcg/x86_64/system/validate-patch.py | 39 ++++ > 14 files changed, 725 insertions(+), 23 deletions(-) > create mode 100644 tests/tcg/plugins/patch.c > create mode 100644 tests/tcg/x86_64/system/patch-target.c > create mode 100755 tests/tcg/x86_64/system/validate-patch.py > @Alex, series looks good to me now. Would you like to add comments, or is it good for you also? Thanks, Pierrick
Pierrick Bouvier <pierrick.bouvier@linaro.org> writes: > On 6/11/25 4:24 PM, Rowan Hart wrote: >> This patch series adds several new API functions focused on enabling use >> cases around reading and writing guest memory from QEMU plugins. To support >> these new APIs, some utility functionality around retrieving information about >> address spaces is added as well. >> The new qemu_plugin_write_register utilizes gdb_write_register, >> which is now >> declared in gdbstub.h for this purpose instead of being static. >> qemu_plugin_write_memory_vaddr utilizes cpu_memory_rw_debug much the >> same as >> the existing read_memory_vaddr function does. >> The read and write_hwaddr functions are the most different. These >> functions >> use address_space_rw, which works well in most cases. There is an important >> caveat that for writes, the page being written will be set dirty by the >> write operation. This dirty setting requires locking the page range, >> which can contend with an already held lock in page_collection_lock >> when called in a tb translate callback with a write to the instruction >> memory in the tb. The doc comments warn against doing this, and it's unlikely >> anyone would want to do this. >> I've also added two test plugins: one that implements a simple >> hypercall >> interface that guest code can use to communicate with the plugin in a >> structured way with a test to ensure that this hypercall works and writing >> virtual memory works. And one that implements a simple patch utility to patch >> memory at runtime. The test for the second plugin ensures the patch applies >> successfully to instruction memory, and can use both hw and vaddr methods. >> For v3, I've had a few comments from the last submission that I've >> addressed, >> and some that I haven't for one reason or another: >> - Enforce QEMU_PLUGIN_CB_ flags in register read/write operations: >> done! >> - Fix my commit messages and add long messages describing commits: done! >> - Un-expose AS internals: done! Functions operate on current vCPU, current AS. >> - Clean up use of current_cpu: done! >> - Make functions take a vcpu_idx: not done. May revisit but it allows footguns. >> Even for translation, seems best to not do this now. We can easily add _vcpu >> versions of these functions in the future if we change our minds! >> For v5, I've just updated the enforcement of the QEMU_PLUGIN_CB_ >> flags to just >> use immediate stores, which simplifies the implementation quite a lot and >> should be more efficient too. Thanks Pierrick for the suggestion! >> v6 is a formatting pass, I left some whitespace that needed removal, >> some >> license text was wrong, and so forth. >> v8 reverts a mistake I made extending the size of arrays of >> TCGHelperInfo >> structs, as I misunderstood their sizes. It preserves adding an explicit >> zero as the last entry for clarity, however. >> v9 fixes qemu_plugin_read_register to return -1 on parameter or flag >> state >> error instead of 0. >> In v10, I relaxed the restriction on when the register r/w functions >> can be >> called, allowing all them to be used from any callback where the CPU is not >> currently executing, with additional notes in the documentation for exceptions >> (atexit and flush, which do not operate on a specific CPU and in which >> current_cpu is not set). >> v11 makes the cb flags functions inline and fixes a typo where cpu >> was asserted >> but current_cpu was actually accessed. >> v12 removes the hypercalls plugin because the functions it tested >> are also >> tested by the patcher plugin, making it redundant. We'll circle back on a >> hypercalls API in the future as a part of the plugin API, not as a plugin >> itself. >> Rowan Hart (1): >> plugins: Add enforcement of QEMU_PLUGIN_CB flags in register R/W >> callbacks >> novafacing (6): >> gdbstub: Expose gdb_write_register function to consumers of gdbstub >> plugins: Add register write API >> plugins: Add memory virtual address write API >> plugins: Add memory hardware address read/write API >> plugins: Add patcher plugin and test >> plugins: Update plugin version and add notes >> accel/tcg/plugin-gen.c | 30 +++ >> gdbstub/gdbstub.c | 2 +- >> include/exec/gdbstub.h | 14 ++ >> include/hw/core/cpu.h | 1 + >> include/qemu/plugin.h | 15 ++ >> include/qemu/qemu-plugin.h | 176 ++++++++++++++-- >> plugins/api.c | 135 +++++++++++- >> plugins/core.c | 33 +++ >> tests/tcg/Makefile.target | 1 + >> tests/tcg/plugins/meson.build | 2 +- >> tests/tcg/plugins/patch.c | 241 ++++++++++++++++++++++ >> tests/tcg/x86_64/Makefile.softmmu-target | 32 ++- >> tests/tcg/x86_64/system/patch-target.c | 27 +++ >> tests/tcg/x86_64/system/validate-patch.py | 39 ++++ >> 14 files changed, 725 insertions(+), 23 deletions(-) >> create mode 100644 tests/tcg/plugins/patch.c >> create mode 100644 tests/tcg/x86_64/system/patch-target.c >> create mode 100755 tests/tcg/x86_64/system/validate-patch.py >> > > @Alex, > series looks good to me now. > > Would you like to add comments, or is it good for you also? I'll do a pass through next week but I think we are in good shape. > > Thanks, > Pierrick -- Alex Bennée Virtualisation Tech Lead @ Linaro
© 2016 - 2026 Red Hat, Inc.