小编tha*_*mes的帖子

Qemu 裸机仿真 - 如何查看 UART 输出?

问题:

如何从使用 Qemu 运行的裸机程序获取 UART 输出?

背景

这是我一直在使用的命令行调用:

qemu-system-arm -M xilinx-zynq-a9 -cpu cortex-a9 -nographic -kernel $BUILD_DIR/mm.elf -m 512M -s -S
Run Code Online (Sandbox Code Playgroud)
  • 使用机器xilinx-zynq-a9
  • 处理器cortex-a9
  • 由于这是裸机,因此可执行文件是一个自包含的 ELF 文件
  • -m 512M表示平台有 512 MiB RAM
  • -s是一个快捷方式-gdb tcp::1234
  • -S意味着启动时冻结CPU

我使用的ELF文件(mm.elf)执行一个简单的矩阵乘法运算,然后打印它是成功还是失败,以及运行了多长时间。ELF 是使用 Xilinx ARM 工具链编译的。我用它来进行软件故障注入。目前我使用 GDB 来询问应该打印的变量的值。然而,由于在故障注入的情况下打印可能会出现很多问题,因此最好看看通过 UART 实际发送的内容。

相关回答:

将 QEMU 窗口输出重定向到运行 qemu 的终端

这有一些我尝试过的建议,但它不适用,因为问题是关于在主机终端窗口中获​​取 Linux 启动消息。

如何在没有操作系统的情况下运行程序?

这是一个不太相关的问题,因为它仍然假设用户拥有某种引导加载程序。虽然从技术上讲必须有一个引导加载程序才能运行应用程序,但 Xilinx 在boot.S等文件中提供了此系统代码,然后将其编译到 ELF 文件中,作为之前运行的代码main

我尝试过的事情:

我尝试将这些添加到当前 Qemu 命令的末尾。结果遵循尝试的参数。

  • -serial mon:stdio
    • 没有什么
  • -serial null …

arm qemu reliability bare-metal uart

10
推荐指数
1
解决办法
1万
查看次数

Qemu 插件函数 - 如何访问客户内存和寄存器

背景

Qemu版本 4.2.0于 2019 年 12 月发布,包含一项称为TCG 插件的新功能。他们在test/plugins目录中有一些示例,并且 API 或多或少在qemu-plugin.h中定义。

该文件定义了两个枚举类型qemu_plugin_cb_flagsqemu_plugin_mem_rw,它们被传递到注册回调的函数中。这些枚举似乎表明回调是否会读取或写入 CPU 寄存器或内存。但是,所有示例插件都使用QEMU_PLUGIN_CB_NO_REGS,并且只有 2 个插件使用内存访问枚举。 hotpages.cmem.c用作QEMU_PLUGIN_MEM_RW注册内存回调的默认值 ( qemu_plugin_register_vcpu_mem_cb)。 mem.c当插件加载时有一个参数来选择是读还是写,但是,它似乎在回调函数中没有任何区别。

问题

我的问题是,如何从插件回调函数访问来宾内存和寄存器?API 似乎表明这是可能的,因为回调注册要求您说明是否要访问它们,以及它是 RW 还是只是读取。

有没有使用这部分 API 的示例?我意识到这是 Qemu 功能的一个非常新的部分。

代码

当您在指令上注册回调时(例如insn.c中),您可以获得指令的虚拟地址。

uint64_t insn_vaddr = qemu_plugin_insn_vaddr(insn);
Run Code Online (Sandbox Code Playgroud)

我正在运行一个裸机ARM程序,这个虚拟地址似乎与ELF文件中指令的地址相关。

在内存回调函数内部,您可以调用qemu_plugin_get_hwaddr来获取内存访问的硬件地址,但我不确定该结构到底代表什么。

有关的

这个答案已有 7 年历史了,建议使用 GDB 接口。我的问题与使用 TCG 插件功能特别相关。

c arm qemu bare-metal

5
推荐指数
1
解决办法
2764
查看次数

标签 统计

arm ×2

bare-metal ×2

qemu ×2

c ×1

reliability ×1

uart ×1