查看“Bochs”的源代码
←
Bochs
跳到导航
跳到搜索
因为以下原因,您没有权限编辑本页:
您请求的操作仅限属于该用户组的用户执行:
用户
您可以查看和复制此页面的源代码。
{{Emulators}} '''Bochs'''是一个用于[[Category:x86|x86]]平台的模拟器,至今它还在稳步改进中。 它极大地改善了操作系统开发,因为虚拟机的重启速度比实际硬件快得多,此外,它还提供了详细的调试功能,可以在内核开发过程中提供很大帮助。 强烈建议安装两台Bochs- 除了开箱即用的版本(可以选择二进制程序包下载)之外,您还应该编译第二个启用了内部调试器的实例 - 因此,当您的 “正常” 调试工具无法跟踪的奇怪情况发生时,您可以将其与调试版本进行交叉检查。 您可能还希望启用(并使用)调试IO端口。 ==常见的错误消息== === Running in Bogus Memory 在虚假内存中运行 === 您将代码指针(EIP)发送到某个未初始化的内存区域。 这意味着您要么引用了空(或未初始化)指针,要么损坏了[[Stack#Stack example on the X86 architecture|栈帧Stack Frame]]的返回地址。 你可以尝试清理您的代码,在使用指针之前测试它们,初始化每个指针 (尤其是那些在堆栈上的指针) 并在GCC中启用 *-Wall*。 === 3rd exception with no resolution 未解决的第三异常=== 这是因为CPU没有设法调用异常处理程序,通常是[[Triple Fault|triple fault|三重故障]]。 这可能是由于不良的 [[Interrupt Descriptor Table|中断描述符表IDT]] 寄存器内容,或不良的IDT描述符导致的。 有时(但不太可能),这也可能是由于异常处理程序代码中的严重错误造成的。 检查异常是否与“非法”ASM指令(如<tt>idiv 0</tt>)一起工作,或者 <source lang="asm"> push 0xf001 pop ds ; 0xf001 is no valid segment, mov ax, ~[ds:0x12345678] ; let's see if we get the GPF </source> 在某些情况下,在此之前还有其他错误消息,可以在错误中提供更多详细信息。 可能会显示的一些常见消息: * interrupt(): gate descriptor is not valid sys seg : 您尚未加载IDT,或者IDT已损坏 * interrupt(): SS selector null :* 您没有TSS :* You haven't set SS0 / ESP0 in the TSS * CR0 = 0xe0000001 CR2 = 0xe0000001 :* 您的分页表没有对齐页面 : * 您的页表未指向正确的内存部分 === I/O操作数大小=== Bochs对I/O操作数大小执行一些相当偏执的检查。 从端口0x1234读取一个字节(8位)通常与读取32位值不同。 你需要返回去查芯片data sheet,仔细检查大小是否正确。 === fetch_raw_descriptor: LDTR.valid=0 === 许多人都说 “可是... 我没有LDT,我读到它不是强制性的!?“。 你是对的。 Bochs也没错。 这个消息通常意味着你的程序试图加载一个带有垃圾值的选择器,而这个垃圾值恰好设置了第三位(表指示符Table Indicator )。 CPU会尝试查找LDT中的描述符,但实际没有注册LDT! 在大多数情况下,错误来自堆栈上的push和pop的一些错误配对,这导致非选择器值被加载到段寄存器中。 如果你仍然卡住了,下载Bochs源代码包并搜索你收到的消息。 然后,也许您可以向消息打印代码添加额外的信息(如段错误的错误偏移量、段限制等)。 但是不要修改bochs的操作! 每次我怀疑Bochs中有漏洞,都只是我误解了英特尔手册... ==Bochs和真实硬件之间的差异== ; Bochs启用BIOS中的A20线路 :您的PC不一定会这样做。 有的PC有BIOS选项可以打开,有的没有。 检查启用A20线路的代码,确保其与更快的硬件没有问题。 ;Bochs会抹除它的内存 :在Bochs中,在您(或BIOS)放入其他内容之前,内存始终为零。 在普通PC上,未初始化的内存往往包含垃圾(通常是全1)或以前执行的痕迹。 检查你的指针,初始化它们,必要时在纸上打印你的代码。 ;Bochs无法正确模拟CPU cache缓存/TLB :尽管Bochs确实具有这些构造,但它们的工作方式与常规CPU缓存或TLB不同,并且不会根据正在仿真的CPU进行更改。 如果未正确处理缓存或TLB刷新,Bochs和硬件的行为可能会有所不同(即,它可能在Bochs上工作,但在硬件上不工作,反之亦然)。 ;Bochs软盘没有错误 :在物理PC中,通常在扇区/磁道上发出最多3次读取尝试命令,然后才能进行良好读取。 如果您的引导扇区中没有正确的错误检查/恢复,您很可能会运行一些不是您的内核的东西…… ; Bochs对于返回实模式很灵活 :不管Chris Giese的保护模式教程说明了什么,您不必处于16位保护模式才能清除CR0的PE位。 如果您未能在真实PC上进入16位保护模式,它将挂起,而不会给出任何错误指示-没有三重故障或任何东西! ;Bochs上的计时不是真实耗时 :(除非您将其配置得更接近实时)。 假如在bochs上等待2秒,打算让那些需要2秒才能准备好的虚拟设备准备就绪,但这可能对您来说只有0.02秒...或者可能是200秒。 附加 clock: sync=realtime, time0=local 将导致中断在实际时间间隔,但可能会让OS与PIT中断过载,导致堆栈溢出 (如果它是pre-emptible抢先的) 使用<tt>sync=slook</tt>也会将其设置为实时速度,只是每个虚拟秒之间的虚拟时钟周期是恒定的。 如果需要减速和模拟原始时钟,您需要去设置每秒执行的指令量。 ;CPU始终是Intel/AMD :Bochs模拟CPU,因此CPUID将始终报告为Intel(如果模拟32位系统)或AMD(如果模拟64位系统)报告,而不管系统中到底有什么。 较新版本的Bochs允许您在CPU标记中指定供应商字符串: cpu: vendor_string="test " #必须是12个字符的ASCII字符串! ==Bochs映像文件扼要== 要使用Bochs引导您的自定义内核,请在bochsrc配置文件中搜索 “floppya” 和 “boot” 行。 以下配置允许您使用计算机的“真实”软盘驱动器并从中启动: floppya: 1_44=/dev/fd0, status=inserted boot: floppy 对于Windows用户,应显示为: floppya: 1_44=a:, status=inserted boot: floppy 但是这太慢了,当你处于一个紧凑的修改-构建-启动周期时,会给软盘带来很大的压力。 Bochs提供了映像文件的使用方法,包括创建映像文件的交互式工具 (bximage.exe)。 请注意,即使映像是设备而不是常规文件,Bochs也会模拟软盘的内部结构。。。 ==Bochs调试设施== Bochs具有一些简化调试的功能。其中许多必须通过配置开关启用: === GUI调试器=== Bochs有一个命令行内部调试器,在此基础上还有一个图形界面。 您必须使用配置选项编译Bochs,然后编辑bochsrc文件才能启用GUI调试器。 我在bochsrc文件中使用这一行来启用X中的图形调试: display_library: x, options="gui_debug" 在Windows环境中,将此行添加到您的bochsrc.bxrc display_library: win32, options="gui_debug" 在Windows上,“option”标志(上面一行用来读取的内容)似乎会被接受,但GUI窗口不会出现。 === I/O调试器宏 === 在启用I/O调试端口的情况下编译Bochs时,一些有用的宏(如果是Bochs 2.4或更新版本, <tt>port_e9_hack:enabled=1,如果没有可以试试 <tt>configure --port-e9-hack</tt>): <source lang="c"> //outputs a character to the debug console #define BochsConsolePrintChar(c) outportb(0xe9, c) //stops simulation and breaks into the debug console #define BochsBreak() outportw(0x8A00,0x8A00); outportw(0x8A00,0x08AE0); </source> === Magic Breakpoint === 当您将Bochs与 [http://bochs.sourceforge.net/doc/docbook/user/internal-debugger.html 内部调试器] 一起使用时,您可以通过名为 [http://bochs.sourceforge.net/doc/docbook/user/bochsrc.html#AEN2324 Magic Breakpoint] 的工具触发调试器。 要触发断点,可以在代码中的任意位置插入 <tt>xchg bx, bx</tt>(在GAS语法中是,<tt>xchgw %bx, %bx</tt>),Bochs将在调试器执行它时立即捕获到调试器中。 在实际硬件上,这不起作用,因为它只是用自身替换BX寄存器。 您应该在Bochs配置文件中放入以下行,让它侦听magic breakpoint: magic_break: enabled=1 在旧版本上,仅启用调试器无法在magic breakpoint支持下编译,在这些版本上配置构建时,还需要指定 lt;tt>--enable-magic-breakpoint</tt> 。 ===调试SMP=== 使用内部调试器时,可以使用以下命令切换CPU: set $cpu = <n> 我还发现这在GUI调试器中有时是必要的,即使它为每个CPU都有按钮。 === 内部调试器命令 === 您可以传递一个包含调试命令的文件,以便在使用内部调试器启动bochs时自动运行。 (bochs -rc <file>) Bochs在BIOS加载之前放置了一个自动断点,可以通过将 <tt>continue</tt> 作为所述文件中的第一个命令来自动跳过该断点。 ===调试三重故障=== 使用内部调试器时,您可以在Bochs配置文件中更改此行: reset_on_triple_fault 0 这一行在三重故障时禁用模拟器的重置,使您能够在三重故障发生后调试代码(在实现分页时非常有用)。 ==从源代码编译Bochs== Bochs有许多编译时配置选项,其中一些选项冲突,因此Bochs的二进制版本可能不适合您的目的。 我发现最好是编译自己的Bochs副本,以确保自己定制所需的功能。 此外,如果发布的版本较旧并且不适合您,您应该考虑使用Bochs的CVS快照版本。 例如我直到版本2.4发布都一直觉得这样做很有必要。 在Ubuntu上,你可能需要运行 <source lang="bash"> sudo apt-get install libgtk2.0-dev </source> 并输入您的密码。在其他Linux发行版上,请尝试类型操作。 Bochs配置选项的清单可能会令人困惑,假如您不认为默认值是明智的。这些是我使用的选项,你可以考虑参考: <source lang="bash"> ./configure --enable-smp \ --enable-cpu-level=6 \ --enable-all-optimizations \ --enable-x86-64 \ --enable-pci \ --enable-vmx \ --enable-debugger \ --enable-disasm \ --enable-debugger-gui \ --enable-logging \ --enable-fpu \ --enable-3dnow \ --enable-sb16=dummy \ --enable-cdrom \ --enable-x86-debugger \ --enable-iodebug \ --disable-plugins \ --disable-docbook \ --with-x --with-x11 --with-term --with-sdl2 </source> 几点注意事项 * 如果您使用的是Windows,则最后一行可能应为“--with-Win32”。 * 在Linux上,最好使用SDL作为X11的显示库,因为在某些设置下性能似乎会大大提高 * Bochs支持GDB stub,并有自己的内部调试器。 这些不能编译成相同的Bochs二进制文件。 内部调试器非常有用,它的标志是 --enable-debugger * Bochs中的GDB stub不支持SMP,上次我检查过。 * 如果不启用PCI,则Intel多处理表将不会出现在内存中。 * 如果不指定<tt>--disable-plugins</tt>,就无法成功加载GUI调试器。 否则,就会出现动态加载符号错误。 * 2.4.2版之后的几个特定于CPU的选项已合并到CPU级别规范中,因此已弃用。它们已从上面的示例中删除。 * 默认编译不支持x86-64,-enable-x86-64选项会将其打开 * 在许多Linux发行版上,可以通过软件包管理器安装Bochs。 例如,在使用apt-get的发行版上,我们可以这样做 <source lang="bash"> sudo apt-get install bochs sudo apt-get install bochs-x </source> 要安装Bochs和X11插件(可能会在ubuntu/Linux mint上崩溃:安装SDL插件并使用SDL而不是x作为显示库)。 请注意,在包管理器的二进制文件中未启用图形调试器的可能性很大。 ==另见== ===文章=== *[[Bochs Graphics Adaptor]] *[[Emulator Comparison]] *[[GDB]] *[[:Category:Disk Image Utilities|类别:磁盘映像实用程序]] ===外部链接=== *[http://bochs.sourceforge.net Bochs Homepage] *[http://bochs.sourceforge.net/doc/docbook/user/internal-debugger.html Bochs internal debugger commands documentation] *[http://www.codeproject.com/system/MakingOS_2.asp CodeProject article on using Bochs] [[Category:Emulators]] [[de:Bochs]]
本页使用的模板:
模板:Emulators
(
查看源代码
)
模板:If
(
查看源代码
)
模板:Show1
(
查看源代码
)
模板:SmallNavBox
(
查看源代码
)
返回至“
Bochs
”。
导航菜单
个人工具
登录
命名空间
页面
讨论
变体
已展开
已折叠
查看
阅读
查看源代码
查看历史
更多
已展开
已折叠
搜索
导航
首页
最近更改
随机页面
MediaWiki帮助
工具
链入页面
相关更改
特殊页面
页面信息