基于qemu-riscv从0开始构建嵌入式linux系统ch10. qemu之virtio与fw_cfg

上一节我们已经基本完成了uboot的移植,下一步自然就是移植linux kernel。在真实的嵌入式开发板上,内核往往会存储在文件系统中,当然也不排除一些直接裸存储于在sd卡或flash介质上,因为我们之前的qemu模拟器中没有添加sd卡或硬盘介质,因此本节我们先回过头来丰富一下qemu的资源。在qemu提供了很多虚拟的外设,但是为了使虚拟机性能更好,我们决定使用转为虚拟化打造的virtio技术来提供文件系统块设备的虚拟化,而且virtio在后续还可以直接提供其他设备如网络,GPU,键盘、鼠标等设备虚拟化。另外我们还将添加fw_cfg用于一些参数传递,起到一些辅助作用。

virtio

virtio是一种I/O半虚拟化解决方案,是一套通用I/O设备虚拟化的程序,是对半虚拟化Hypervisor中的一组通用I/O设备的抽象。关于virtio的原理和介绍我这里不做过多介绍,有很多博客都有介绍,如 https://www.cnblogs.com/super-sos/p/9044154.html 。我比较实在,喜欢直接查找阅读相关的源代码去自己感悟理解这些技术。好了,扯远了,我们回到主题,我们这节直接调研qemu相关的API例化virtio-mmio设备到我们的仿真环境中,这是非常简单的。

  • qemu-6.0.0/hw/riscv/quard_star.c添加VIRTIO基地址,这里我们定义在0x10100000开始。
    [QUARD_STAR_VIRTIO] = { 0x10100000,        0x1000 }, //Eight consecutive groups
  • sysbus_create_simple创建virtio-mmio设备,我们这里创建八组virtio-mmio设备,后面会配置为不同的设备,如块设备,网卡等。注意基地址,中断号配置正确。
    for (i = 0; i < QUARD_STAR_COUNT; i++) {sysbus_create_simple("virtio-mmio",memmap[QUARD_STAR_VIRTIO].base + i * memmap[QUARD_STAR_VIRTIO].size,qdev_get_gpio_in(DEVICE(virtio_plic), QUARD_STAR_IRQ + i));}
  • uboot设备树/soc节点添加virtio_mmio
     virtio_mmio@10107000 {interrupts = <0x8>;interrupt-parent = <0x11>;reg = <0x0 0x10107000 0x0 0x1000>;compatible = "virtio,mmio";};virtio_mmio@10106000 {interrupts = <0x7>;interrupt-parent = <0x11>;reg = <0x0 0x10106000 0x0 0x1000>;compatible = "virtio,mmio";};virtio_mmio@10105000 {interrupts = <0x6>;interrupt-parent = <0x11>;reg = <0x0 0x10105000 0x0 0x1000>;compatible = "virtio,mmio";};virtio_mmio@10104000 {interrupts = <0x5>;interrupt-parent = <0x11>;reg = <0x0 0x10104000 0x0 0x1000>;compatible = "virtio,mmio";};virtio_mmio@10103000 {interrupts = <0x4>;interrupt-parent = <0x11>;reg = <0x0 0x10103000 0x0 0x1000>;compatible = "virtio,mmio";};virtio_mmio@10102000 {interrupts = <0x3>;interrupt-parent = <0x11>;reg = <0x0 0x10102000 0x0 0x1000>;compatible = "virtio,mmio";};virtio_mmio@10101000 {interrupts = <0x2>;interrupt-parent = <0x11>;reg = <0x0 0x10101000 0x0 0x1000>;compatible = "virtio,mmio";};virtio_mmio@10100000 {interrupts = <0x1>;interrupt-parent = <0x11>;reg = <0x0 0x10100000 0x0 0x1000>;compatible = "virtio,mmio";};

ok,virtio_mmio设备添加完成。接下来注意打开uboot以及后面linux kernel的virtio相关设备的驱动支持即可。

fw_cfg

fw_cfg是qemu提供的传递参数给内核的虚拟ip,这里我们也添加下这个ip,后面我们如果想通过qemu启动传递一些参数给虚拟机就会非常方便。

  • qemu-6.0.0/hw/riscv/quard_star.c添加基地址,这里我们定义在0x10108000开始,fw_cfg的寄存器个数非常少。
    [QUARD_STAR_FW_CFG] = { 0x10108000,          0x18 },
  • fw_cfg_init_mem_wide创建fw_cfg设备,使用类似fw_cfg_add_*接口可以内置一些参数到fw_cfg,这里我们吧core的数量内置到fw_cfg中。
    s->fw_cfg = fw_cfg_init_mem_wide(memmap[QUARD_STAR_FW_CFG].base + 8, memmap[QUARD_STAR_FW_CFG].base,  8, memmap[QUARD_STAR_FW_CFG].base + 16,&address_space_memory);fw_cfg_add_i16(s->fw_cfg, FW_CFG_NB_CPUS, (uint16_t)machine->smp.cpus);rom_set_fw(s->fw_cfg);
  • uboot设备树/节点添加fw-cfg
 fw-cfg@10108000 {dma-coherent;reg = <0x0 0x10108000 0x0 0x18>;compatible = "qemu,fw-cfg-mmio";};

ok,fw-cfg设备添加完成。同样注意打开uboot、kernel的fw-cfg设备的驱动支持,uboot需要打开CMD_QFW功能。

测试使用

修改run.sh的启动脚本

$SHELL_FOLDER/output/qemu/bin/qemu-system-riscv64 \
-M quard-star \
-m 1G \
-smp 8 \
-drive if=pflash,bus=0,unit=0,format=raw,file=$SHELL_FOLDER/output/fw/fw.bin \
-drive file=$SHELL_FOLDER/output/rootfs/rootfs.img,format=raw,id=hd0 \
-device virtio-blk-device,drive=hd0 \
-fw_cfg name="opt/qemu_cmdline",string="qemu_vc="$DEFAULT_V"" \
--serial vc:$DEFAULT_VC --serial vc:$DEFAULT_VC --serial vc:$DEFAULT_VC --monitor vc:$DEFAULT_VC --parallel none

这里我们添加了一个virtio-blk-device设备,并加载了rootfs.img文件系统文件,当然我们现在还没有制做根文件系统,这个文件是用dd命令生成的空文件img。-fw_cfg选项可以添加参数,如果想添加多个参数可以多次使用该选项,注意自定义参数必须添加在opt路径下。启动程序看看效果:

如图所示,使用qfw list/qfw cpus/virtio scan/virtio info命令均可以输出正确的信息,可见功能已经正常,后面就可以开始移植内核构建根文件系统加载启动内核了。

到这里本篇内容讲述完成。本节内容比较简单,为内核启动添加虚拟化的硬件基础,万事俱备,下一节我们将向着linux Kernel出发!。

本教程的
github仓库:https://github.com/QQxiaoming/quard_star_tutorial
gitee仓库:https://gitee.com/QQxiaoming/quard_star_tutorial
本节所在tag:ch10

基于qemu-riscv从0开始构建嵌入式linux系统ch10. qemu之virtio与fw_cfg相关推荐

  1. 基于qemu-riscv从0开始构建嵌入式linux系统ch3. 添加中断控制器、串口、pflash支持

    基于qemu-riscv从0开始构建嵌入式linux系统ch3. 添加中断控制器.串口.pflash支持 添加串口支持 真实板卡的初期调试中,串口打印可谓神器,几乎所有的SOC都会带有串口这个外设,因 ...

  2. 基于AT91SAM9G20构建嵌入式Linux系统

    本文中使用的目标平台AT91SAM9G20是Atmel公司使用ARM926EJ-S处理器内核开发的一块SoC嵌入式微处理器,主频达到400MHz,具有Atmel 先进的外设DMA 和分布式存储器架构, ...

  3. buildroot:Linux平台构建嵌入式Linux系统的框架

    buildroot是Linux平台上一个构建嵌入式Linux系统的框架.整个Buildroot是由Makefile脚本和Kconfig配置文件构成的.你可以和编译Linux内核一样,通过buildro ...

  4. 嵌入式系统实验 构建嵌入式Linux系统,《嵌入式系统与开发》构建嵌入式Linux系统-实验报告.doc...

    <嵌入式系统与开发>构建嵌入式Linux系统-实验报告 <嵌入式数据库sqlite移植及使用> 实验报告 学生姓名: 陈 彤 学 号: 1座机电话号码 专业班级: 130044 ...

  5. iMX6Ull采用Yocto构建嵌入式Linux系统(三)

    获取Yocto 设置Git用户名和密码 Yocto项目采用repo管理各个git库的方式进行管理.因此,除了使用repo工具外,还需要使用到Git.使用Git前,需要设置Git的用户名和密码: $ g ...

  6. 构建嵌入式linux系统_用于构建嵌入式Linux系统的4种工具

    构建嵌入式linux系统 Linux正在被部署到比Linus Torvalds在他的宿舍里工作的设备更多的设备中. 受支持的各种芯片架构令人震惊,并导致各种大小的设备都使用Linux. 从庞大的IBM ...

  7. 【嵌入式】构建嵌入式Linux系统(uboot、内核、文件系统)

    知识架构及层次 Linux内核由三部分构成: Bootloader:启动引导系统(可执行文件) Kernel:内核(可执行文件) Root File System:根文件系统 嵌入式Linux系统构成 ...

  8. 嵌入式 linux 启动脚本 编写,[9构建嵌入式linux系统项目-启动脚本的编写.ppt

    [9构建嵌入式linux系统项目-启动脚本的编写 启动脚本 教学回顾 shell语法 管道.重定向 变量 结构性语句 教学内容 启动脚本的写法 教学要求 熟悉掌握启动脚本的写法 shell 函数 在s ...

  9. 用QEMU构建嵌入式LINUX系统

    Table of Contents Qemu –从源头建造 ARM工具链 Linux内核 构建文件系统 通过NFS使用根文件系统 配置QEMU Tap网络 创建运行脚本 推荐阅读:<在CentO ...

最新文章

  1. MySQL 数据库大小写的问题
  2. CVPR15 image retrieval reading list
  3. samba安装与配置
  4. 基于角色-功能-资源的权限控制模型的设计与实现-引子
  5. 最大化_怎样保证油压缓冲器工作效率最大化?
  6. 小米9android q测试版,基于Android Q的MIUI来了 小米9尝鲜
  7. 阿里云 Composer 全量镜像
  8. ASP.NET模拟其他用户进行关机
  9. IDEA中Spring智能提示,XML Configuration File中spring config
  10. World Wind Java开发之十——AnalyticSurface栅格渲染(转)
  11. JavaScript.Remove
  12. Oracle和Mysql的区别 转载
  13. mysql重启.....
  14. 辽宁2009对口计算机试题文档之家,中职对口升学计算机网络检测试题一
  15. n 个骰子点数和及各自出现的概率
  16. SSM框架客户管理系统
  17. FreeRTOS死机原因
  18. 用java定义中国象棋的棋子_java大神 求帮忙 我坐的中国象棋怎样移动棋子
  19. 杭电(杭州电子科技大学)操作系统实验二:Linux内核模块编程
  20. 二维码如何制作?快速制作二维码的教程在这里

热门文章

  1. pytorch每日一学1(torch.is_tensor(obj))
  2. 微信公众号开发的测试账号配置
  3. 经典故事---话说河南人
  4. Useful Note
  5. 使用51单片机来实现步进电机的控制
  6. 【微信】微信提现到零钱
  7. solidity 交换变量的两种方法
  8. php 微信检测域名是否被封,检测域名是否已被微信封掉不能访问
  9. matlab脚本终止、暂停的几个函数(pause、error、break、quit、exit、return)
  10. 使用Python进行手机平板移动开发:Kivy与BeeWare框架