mirror of
https://github.com/Motorhead1991/qemu.git
synced 2025-07-26 20:03:54 -06:00
plugins: Add memory hardware address read/write API
This patch adds functions to the plugins API to allow plugins to read and write memory via hardware addresses. The functions use the current address space of the current CPU in order to avoid exposing address space information to users. A later patch may want to add a function to permit a specified address space, for example to facilitate architecture-specific plugins that want to operate on them, for example reading ARM secure memory. Reviewed-by: Pierrick Bouvier <pierrick.bouvier@linaro.org> Signed-off-by: Rowan Hart <rowanbhart@gmail.com> Message-ID: <20250624175351.440780-6-rowanbhart@gmail.com> Signed-off-by: Alex Bennée <alex.bennee@linaro.org> Message-ID: <20250627112512.1880708-10-alex.bennee@linaro.org>
This commit is contained in:
parent
f00373b895
commit
30424b8d42
2 changed files with 190 additions and 0 deletions
|
@ -39,6 +39,7 @@
|
|||
#include "qemu/main-loop.h"
|
||||
#include "qemu/plugin.h"
|
||||
#include "qemu/log.h"
|
||||
#include "system/memory.h"
|
||||
#include "tcg/tcg.h"
|
||||
#include "exec/gdbstub.h"
|
||||
#include "exec/target_page.h"
|
||||
|
@ -494,6 +495,102 @@ bool qemu_plugin_write_memory_vaddr(uint64_t addr, GByteArray *data)
|
|||
return true;
|
||||
}
|
||||
|
||||
enum qemu_plugin_hwaddr_operation_result
|
||||
qemu_plugin_read_memory_hwaddr(hwaddr addr, GByteArray *data, size_t len)
|
||||
{
|
||||
#ifdef CONFIG_SOFTMMU
|
||||
if (len == 0) {
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_ERROR;
|
||||
}
|
||||
|
||||
g_assert(current_cpu);
|
||||
|
||||
|
||||
int as_idx = cpu_asidx_from_attrs(current_cpu, MEMTXATTRS_UNSPECIFIED);
|
||||
AddressSpace *as = cpu_get_address_space(current_cpu, as_idx);
|
||||
|
||||
if (as == NULL) {
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_INVALID_ADDRESS_SPACE;
|
||||
}
|
||||
|
||||
g_byte_array_set_size(data, len);
|
||||
MemTxResult res = address_space_rw(as, addr,
|
||||
MEMTXATTRS_UNSPECIFIED, data->data,
|
||||
data->len, false);
|
||||
|
||||
switch (res) {
|
||||
case MEMTX_OK:
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_OK;
|
||||
case MEMTX_ERROR:
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_DEVICE_ERROR;
|
||||
case MEMTX_DECODE_ERROR:
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_INVALID_ADDRESS;
|
||||
case MEMTX_ACCESS_ERROR:
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_ACCESS_DENIED;
|
||||
default:
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_ERROR;
|
||||
}
|
||||
#else
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_ERROR;
|
||||
#endif
|
||||
}
|
||||
|
||||
enum qemu_plugin_hwaddr_operation_result
|
||||
qemu_plugin_write_memory_hwaddr(hwaddr addr, GByteArray *data)
|
||||
{
|
||||
#ifdef CONFIG_SOFTMMU
|
||||
if (data->len == 0) {
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_ERROR;
|
||||
}
|
||||
|
||||
g_assert(current_cpu);
|
||||
|
||||
int as_idx = cpu_asidx_from_attrs(current_cpu, MEMTXATTRS_UNSPECIFIED);
|
||||
AddressSpace *as = cpu_get_address_space(current_cpu, as_idx);
|
||||
|
||||
if (as == NULL) {
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_INVALID_ADDRESS_SPACE;
|
||||
}
|
||||
|
||||
MemTxResult res = address_space_rw(as, addr,
|
||||
MEMTXATTRS_UNSPECIFIED, data->data,
|
||||
data->len, true);
|
||||
switch (res) {
|
||||
case MEMTX_OK:
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_OK;
|
||||
case MEMTX_ERROR:
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_DEVICE_ERROR;
|
||||
case MEMTX_DECODE_ERROR:
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_INVALID_ADDRESS;
|
||||
case MEMTX_ACCESS_ERROR:
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_ACCESS_DENIED;
|
||||
default:
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_ERROR;
|
||||
}
|
||||
#else
|
||||
return QEMU_PLUGIN_HWADDR_OPERATION_ERROR;
|
||||
#endif
|
||||
}
|
||||
|
||||
bool qemu_plugin_translate_vaddr(uint64_t vaddr, uint64_t *hwaddr)
|
||||
{
|
||||
#ifdef CONFIG_SOFTMMU
|
||||
g_assert(current_cpu);
|
||||
|
||||
uint64_t res = cpu_get_phys_page_debug(current_cpu, vaddr);
|
||||
|
||||
if (res == (uint64_t)-1) {
|
||||
return false;
|
||||
}
|
||||
|
||||
*hwaddr = res | (vaddr & ~TARGET_PAGE_MASK);
|
||||
|
||||
return true;
|
||||
#else
|
||||
return false;
|
||||
#endif
|
||||
}
|
||||
|
||||
struct qemu_plugin_scoreboard *qemu_plugin_scoreboard_new(size_t element_size)
|
||||
{
|
||||
return plugin_scoreboard_new(element_size);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue