gem5模拟器入门(二)——创建一个简单的配置脚本

        本章教程将引导您设置一个简单的 gem5 仿真脚本,并首次运行 gem5。假设您已经完成了gem5模拟器入门(一)——环境配置-CSDN博客,并成功构建了带有可执行文件 build/X86/gem5.opt 的 gem5。

        配置脚本将模拟一个非常简单的系统,只有一个简单的 CPU 核心,这个 CPU 核心将连接到系统范围的内存总线。我们还将有一个连接到内存总线的单一DDR3内存通道。

gem5 配置脚本

        gem5 二进制文件接受一个 Python 脚本作为参数,该脚本设置并执行仿真。在这个脚本中,您将创建一个要模拟的系统,创建系统的所有组件,并指定系统组件的所有参数。然后,您可以从脚本中开始仿真。

        这个脚本完全由用户定义。您可以在配置脚本中选择使用任何有效的 Python 代码。本书提供了一种风格示例,该示例在很大程度上依赖于 Python 中的类和继承。作为 gem5 用户,您可以决定将配置脚本做得多么简单或复杂。

        在 gem5 中的 configs/examples 目录中,有许多示例配置脚本。这些脚本大多数都是包罗万象的,允许用户在命令行上指定几乎所有选项。与其从这些复杂的脚本开始,本书将从一个可以运行 gem5 的最简单脚本开始,然后逐步构建。希望到本节结束时,您会对仿真脚本的工作原理有一个很好的了解。

SimObjects

gem5 的模块化设计是围绕 SimObject 类型构建的。模拟系统中的大多数组件都是 SimObjects:CPU、缓存、内存控制器、总线等。gem5 将所有这些对象从其 C++ 实现导出到 Python。因此,从 Python 配置脚本中,您可以创建任何 SimObject,设置其参数,并指定 SimObjects 之间的交互。

1.创建配置文件

mkdir configs/tutorial
mkdir configs/tutorial/part1/
touch configs/tutorial/part1/simple.py

这只是一个普通的 Python 文件,将由 gem5 可执行文件中的嵌入式 Python 执行。因此,您可以使用 Python 中的任何功能和库。

在这个文件中我们要做的第一件事是导入 m5 库和我们编译的所有 SimObjects。

import m5
from m5.objects import *

接下来,我们将创建第一个 SimObject:我们要模拟的系统。System 对象将是我们模拟系统中所有其他对象的父对象。System 对象包含了许多功能性(非时序级)信息,比如物理内存范围、根时钟域、根电压域、内核(在全系统仿真中)等。要创建系统 SimObject,我们只需像实例化普通的 Python 类一样实例化它:

system = System()

现在我们有了要模拟的系统的参考,让我们来设置系统的时钟。首先,我们需要创建一个时钟域。然后我们可以在该域上设置时钟频率。在SimObject上设置参数与在Python对象上设置成员完全相同,因此我们可以简单地将时钟设置为1 GHz。最后,我们必须为这个时钟域指定一个电压域。由于我们现在不关心系统功率,所以我们将使用电压域的默认选项。

system.clk_domain = SrcClockDomain()
system.clk_domain.clock = '1GHz'
system.clk_domain.voltage_domain = VoltageDomain()

 一旦我们有了一个系统,让我们来设置如何模拟内存。我们将使用时序模式进行内存模拟。除了像快进和从检查点恢复这样的特殊情况外,您几乎总是会使用时序模式进行内存模拟。我们还将设置一个大小为512 MB的单个内存范围,这是一个非常小的系统。请注意,在Python配置脚本中,每当需要大小时,您可以使用通用的口头用语和单位来指定大小,比如“512MB”。类似地,对于时间,您可以使用时间单位(例如,“5ns”)。这些将自动转换为一个通用的表示形式。

system.mem_mode = 'timing'
system.mem_ranges = [AddrRange('512MB')]

现在,我们可以创建一个CPU。我们将从gem5中最简单的基于时序的X86 ISA CPU开始,即X86TimingSimpleCPU。这个CPU模型在一个时钟周期内执行每条指令,除了流经内存系统的内存请求。要创建CPU,您只需实例化对象:

system.cpu = X86TimingSimpleCPU()

如果我们想要使用RISCV ISA,我们可以使用RiscvTimingSimpleCPU,如果我们想要使用ARM ISA,我们可以使用ArmTimingSimpleCPU。然而,在这个练习中,我们将继续使用X86 ISA。

接下来,我们将创建系统范围的内存总线:

system.membus = SystemXBar()

现在我们有了内存总线,让我们将CPU上的缓存端口连接到它上面。在这种情况下,由于我们要模拟的系统没有任何缓存,我们将直接将I-cache和D-cache端口连接到内存总线上。在这个示例系统中,我们没有缓存。

system.cpu.icache_port = system.membus.cpu_side_ports
system.cpu.dcache_port = system.membus.cpu_side_ports

关于gem5端口的一点说明

为了将内存系统组件连接在一起,gem5使用了一个端口抽象。每个内存对象可以有两种类型的端口,请求端口和响应端口。请求从请求端口发送到响应端口,响应从响应端口发送到请求端口。在连接端口时,您必须将一个请求端口连接到一个响应端口。

从Python配置文件中连接端口非常容易。您只需将请求端口设置为等于响应端口,它们就会被连接起来。例如:

system.cpu.icache_port = system.l1_cache.cpu_side

在这个例子中,CPU的icache_port是一个请求端口,缓存的cpu_side是一个响应端口。请求端口和响应端口可以在=的任一侧,并且将建立相同的连接。在建立连接之后,请求者可以向响应者发送请求。在幕后有很多魔法来建立连接,其中的细节对大多数用户来说并不重要。

gem5 Python配置中两个端口之间的=的另一个显着的魔法是,允许一个端口在一侧,另一侧是一个端口数组。例如:

system.cpu.icache_port = system.membus.cpu_side_ports

在这个例子中,CPU的icache_port是一个请求端口,membus的cpu_side_ports是一个响应端口数组。在这种情况下,在cpu_side_ports上生成一个新的响应端口,并且这个新创建的端口将连接到请求端口。

接下来,我们需要连接一些其他的端口,以确保我们的系统能够正常运行。我们需要在CPU上创建一个I/O控制器,并将其连接到内存总线。此外,我们需要将系统中的一个特殊端口连接到内存总线。这个端口是一个仅用于功能的端口,允许系统读写内存。

将PIO和中断端口连接到内存总线是x86特有的要求。其他ISA(例如ARM)不需要这3行额外的连接。

system.cpu.createInterruptController()
system.cpu.interrupts[0].pio = system.membus.mem_side_ports
system.cpu.interrupts[0].int_requestor = system.membus.cpu_side_ports
system.cpu.interrupts[0].int_responder = system.membus.mem_side_portssystem.system_port = system.membus.cpu_side_ports

接下来,我们需要创建一个内存控制器并将其连接到内存总线。对于这个系统,我们将使用一个简单的DDR3控制器,它将负责整个系统的内存范围。

system.mem_ctrl = MemCtrl()
system.mem_ctrl.dram = DDR3_1600_8x8()
system.mem_ctrl.dram.range = system.mem_ranges[0]
system.mem_ctrl.port = system.membus.mem_side_ports

完成了这些最后的连接之后,我们已经完成了对我们模拟系统的实例化!我们的系统应该如下图所示。

 接下来,我们需要设置CPU要执行的进程。由于我们是在系统调用模拟模式(SE模式)下执行,我们只需将CPU指向已编译的可执行文件即可。我们将执行一个简单的“Hello world”程序。gem5已经内置了一个已编译的程序,所以我们将使用它。您可以指定任何为x86构建且已静态编译的应用程序。

 Full system vs syscall emulation

gem5可以在两种不同的模式下运行,称为“系统调用模拟”和“全系统”或SE和FS模式。在全系统模式下(稍后详细介绍全系统部分),gem5模拟整个硬件系统并运行未经修改的内核。全系统模式类似于运行虚拟机。

另一方面,系统调用模拟模式并没有模拟系统中的所有设备,而是专注于模拟CPU和内存系统。系统调用模拟配置要简单得多,因为您不需要实例化实际系统中需要的所有硬件设备。然而,系统调用模拟只模拟Linux系统调用,因此只模拟用户模式代码。

如果您的研究问题不需要模拟操作系统,并且需要额外的性能,那么您应该使用SE模式。然而,如果您需要对系统进行高保真建模,或者像页表遍历这样的操作系统交互很重要,那么您应该使用FS模式。

首先,我们必须创建进程(另一个SimObject)。然后,我们将进程的命令设置为我们要运行的命令。这是一个类似于argv的列表,其中可执行文件位于第一个位置,其余列表中是可执行文件的参数。然后,我们将CPU设置为使用该进程作为其工作负载,并最终在CPU中创建功能执行上下文。

binary = 'tests/test-progs/hello/bin/x86/linux/hello'# for gem5 V21 and beyond
system.workload = SEWorkload.init_compatible(binary)process = Process()
process.cmd = [binary]
system.cpu.workload = process
system.cpu.createThreads()

我们需要做的最后一件事是实例化系统并开始执行。首先,我们创建Root对象。然后,我们实例化模拟。实例化过程会遍历我们在Python中创建的所有SimObjects,并创建它们的C++等效对象。

需要注意的是,您不必实例化Python类,然后将参数显式地指定为成员变量。您还可以将参数作为命名参数传递,就像下面的Root对象一样。

root = Root(full_system = False, system = system)
m5.instantiate()

最后,我们可以启动实际的模拟了!顺便说一下,gem5现在使用Python 3风格的打印函数,因此print不再是一个语句,而必须作为一个函数调用。

print("Beginning simulation!")
exit_event = m5.simulate()

一旦模拟结束,我们就可以检查系统的状态。

print('Exiting @ tick {} because {}'.format(m5.curTick(), exit_event.getCause()))

2.运行gem5

现在我们已经创建了一个简单的模拟脚本(完整版本可以在gem5代码库中的configs/learning_gem5/part1/simple.py 找到),我们准备好运行gem5了。gem5可以接受许多参数,但只需要一个位置参数,即模拟脚本。因此,我们可以从gem5的根目录直接运行gem5:

build/X86/gem5.opt configs/tutorial/part1/simple.py

输出如下:

gem5 Simulator System.  https://www.gem5.org
gem5 is copyrighted software; use the --copyright option for details.gem5 version 23.1.0.0
gem5 compiled May 28 2024 11:47:30
gem5 started May 28 2024 13:06:09
gem5 executing on Aquarius, pid 168573
command line: build/X86/gem5.opt configs/learning_gem5/part1/simple.pyGlobal frequency set at 1000000000000 ticks per second
warn: No dot file generated. Please install pydot to generate the dot file and pdf.
src/mem/dram_interface.cc:692: warn: DRAM device capacity (8192 Mbytes) does not match the address range assigned (512 Mbytes)
src/base/statistics.hh:279: warn: One of the stats is a legacy stat. Legacy stat is a stat that does not belong to any statistics::Group. Legacy stat is deprecated.
system.remote_gdb: Listening for connections on port 7000
Beginning simulation!
src/sim/simulate.cc:199: info: Entering event queue @ 0.  Starting simulation...
Hello world!
Exiting @ tick 503912000 because exiting with last active thread context

在配置文件中更改参数应该会产生不同的结果。例如,如果你将系统时钟加倍,模拟应该会更快完成。或者,如果你将DDR控制器改为DDR4,性能应该会更好。

此外,您还可以将CPU模型更改为X86MinorCPU以模拟顺序CPU,或者将其更改为X86O3CPU以模拟乱序CPU。然而,请注意,X86O3CPU当前无法与simple.py一起使用,因为X86O3CPU需要具有单独的指令和数据缓存的系统(X86O3CPU可以与下一节中的配置一起使用)。

所有gem5的BaseCPU都采用格式{ISA}{Type}CPU的命名格式。因此,如果我们想要一个RISCV Minor CPU,我们将使用RiscvMinorCPU。

有效的ISA有:

  • Riscv
  • Arm
  • X86
  • Sparc
  • Power
  • Mips

CPU类型有:

  • AtomicSimpleCPU
  • O3CPU
  • TimingSimpleCPu
  • KvmCPU
  • MinorCPU

接下来,我们将在配置文件中添加缓存,以模拟一个更复杂的系统。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/842912.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

LangChain实战 | 3分钟学会SequentialChain怎么传多个参数

SequentialChain参数传递,总结了以下四种类型 参数传递入参出参一 对 一11一 对 多1n多 对 一n1多 对 多nn 0.连接大模型 先选一个llm,参考这篇博客选择一个国内大模型 LangChain连接国内大模型测试|智谱ai、讯飞星火、通义千问 from langchain_comm…

网络侦察技术

网络侦察技术 收集的信息网络侦察步骤搜索引擎检索命令bing搜索引擎Baidu搜索引擎Shodan钟馗之眼(zoomeye) whois数据库:信息宝库查询注册资料 域名系统网络拓扑社交网络跨域拓展攻击 其它侦察手段社会工程学社会工程学常见形式Web网站查询 其它非技术侦察手段总结网…

巅峰对决:OpenAI与Google如何用大模型开创未来

2024年,人工智能领域正引领着一场波澜壮阔的全球技术革命。 5月14日,OpenAI揭开了其新一代多模态人工智能大模型GPT4系列的神秘面纱,其中GPT-4o不仅拥有流畅迷人的嗓音,还展现出幽默、机智和深刻的洞察力……紧接着,在…

linux下cp和mv命令显示进度条

1.查看当前系统下coreutils工具包的版本号: [rootk8s-master ~]# rpm -qa | grep -w coreutils coreutils-8.22-24.el7_9.2.x86_64当前版本为8.22。 因为cp 和 mv 命令由 coreutils 软件包提供,所以需要重新下载 coreutils 软件包配置补丁 2.下载core…

数据结构——顺序表基本操作的实现(初始化、取值、查找、插入)

一、线性表与顺序表的概述 线性表的数据元素的逻辑特征是线性的,是一种典型的线性结构。这样的结构可以借鉴数组,如数组a[10]中,a[1]前一定是a[0],a[1]后一定是a[2],首结点(a[0])前面无元素&am…

java医院管理系统源码(springboot+vue+mysql)

风定落花生,歌声逐流水,大家好我是风歌,混迹在java圈的辛苦码农。今天要和大家聊的是一款基于springboot的医院管理系统。项目源码以及部署相关请联系风歌,文末附上联系信息 。 项目简介: 医院管理系统的主要使用者分…

VR法治教育展厅互动体验突破了地域限制

VR全景互动展厅搭建编辑器以其卓越的特点、强大的功能及实际应用中的显著优势,成为企业级VR应用的得力助手。这款软件不仅能够制作逼真的虚拟场景,更能让用户沉浸其中,体验前所未有的真实感。 它拥有高度逼真的视觉效果,采用先进的…

智能单款计划助力品牌利润增长

零售品牌若要在激烈的市场竞争中胜出,季中单款的管理无疑是商品生命周期管理的核心环节之一。而单款计划的制定,首先依赖于对爆款、平销及滞销产品的敏锐洞察。一个利润现象不得不引起我们的关注:爆款产品的销售,往往成为拉动品牌…

svix - webhooks

文章目录 一、关于 SvixClient Library Overview与 Svix 托管服务的区别 二、运行服务器1、部署1.1 Docker1) 使用 Docker Compose2) 独立容器 1.2 预编译的二进制文件1.3 从源代码构建 2、运行时依赖项3、Redis/Valkey 注意事项持久性 Eviction 政策4、服务器配置4.1 配置文件…

express.js--生成token(二)

主要作用是访问路由接口时,生成身份权限信息 下载依赖 npm i express-jwt npm i jsonwebtoken 配置管理 config/index.js module.exports {app: {port: process.PORT || 3000,//jwt密钥jwtSecret: jwtSecret,//token过期时间expiresIn: 60 * 60 * 24,} } con…

从零开始:如何集成美颜SDK和优化美颜接口

今天,小编将从零开始,详细讲解如何集成SDK并优化美颜接口。 一、选择合适的美颜SDK 评估SDK的功能 在评估过程中,可以通过阅读官方文档、查看示例代码以及实际测试来确定SDK是否符合需求。 兼容性和性能 确保其支持你开发的应用平台&…

Android15 Beta更新速览

Android15 Beta更新速览 前台服务变更 前台服务使应用保持活动状态,以便它们可以执行关键且对用户可见的操作,通常以牺牲电池寿命为代价。在 Android 15 Beta 2 中,dataSync 和 mediaProcessing 前台服务类型现在具有约 6 小时的超时时间&a…

内网安全--隧道技术-CS上线本地

免责声明:本文仅做技术交流与学习...请勿非法搞破坏... ---隧道技术:硬刚网络协议,(你不让我走我偏走!) 解决不出网协议上线的问题(利用出网协议进行封装出网) 代理协议: SOCKS4/5 代理软件: SocksCap Proxifier ProxyChains(…

磁盘管理以及文件系统08

1、为什么要对磁盘进行分区? 业务层面:为满足一定的需求所是做的特定操作。 2、硬盘是什么,以及硬盘的作用 硬盘:计算机的存储设备,一个或者多个带磁性的盘组成的,可以在盘片上进行数据的读写。硬盘的最…

LVGL圆弧、线条、图片、色环、按钮矩阵、文本区域、键盘部件

目录 LVGL圆弧部件 LVGL线条部件 LVGL图片部件 LVGL色环部件 LVGL按钮矩阵部件 LVGL文本区域部件 LVGL键盘部件 LVGL圆弧部件 圆弧部件以弧形滑动的形式来调节、显示某个参数的值。 圆弧部件组成部分: 背景弧(LV_PART_MAIN) 前景弧&am…

浏览器提示网站不安全怎么办?有什么解决办法吗?

当你在浏览器中访问一个网站时,如果看到提示说该网站不安全,这通常是由于网站没有使用SSL证书或者SSL证书存在问题。SSL证书在这里扮演着非常关键的角色,下面我会详细解释它的作用以及如何解决这类不安全提示。 SSL证书的作用: 1…

【CTF Web】CTFShow web11 Writeup(RCE+PHP+代码审计)

web11 1 阿呆听完自己菜死了&#xff0c;自己呆了。决定修好漏洞&#xff0c;绝对不能让自己再菜死了。 解法 可知 flag 在 config.php。 <?php # flag in config.php include("config.php"); if(isset($_GET[c])){$c $_GET[c];if(!preg_match("/system…

WorldSpace下的合批策略与ScreenSpace有什么区别

1&#xff09;WorldSpace下的合批策略与ScreenSpace有什么区别 2&#xff09;在iOS上用Metal取代OpenGL的多么 3&#xff09;在动画蓝图中将两个或多个动画同时融合到同一个网格 4&#xff09;Mipmap如何限定层级 这是第387篇UWA技术知识分享的推送&#xff0c;精选了UWA社区的…

java面对对象编程-多态

介绍 方法的多态 多态是在继承&#xff0c;重载&#xff0c;重写的基础上实现的 我们可以看看这个代码 package b;public class main_ {public static void main(String[] args) { // graduate granew graduate(); // gra.cry();//这个时候&#xff0c;子类的cry方法就重写…

结合Django和Vue.js构建现代Web应用

文章目录 1. 创建Django项目2. 配置Django后端3. 创建Vue.js前端4. 连接Django和Vue.js5. 构建和部署 在现代Web开发中&#xff0c;结合后端框架和前端框架是非常常见的&#xff0c;其中Django作为一种流行的Python后端框架&#xff0c;而Vue.js则是一种灵活强大的前端框架。本…