设置BIOS的x86模式

3.3.4 设置BIOSx86模式

继续走,下一个函数,set_bios_mode(),跟main来自同一个文件:

 

  94/*

  95 * Tell the BIOS what CPU mode we intend to run in.

  96 */

  97static void set_bios_mode(void)

  98{

  99#ifdef CONFIG_I386

 100        struct biosregs ireg;

 101

 102        initregs(&ireg);

 103        ireg.ax = 0xec00;

 104        ireg.bx = 2;

 105        intcall(0x15, &ireg, NULL);

 106#endif

 107}

 

当然,set_bios_mode函数只针对i386,用于告诉BIOS什么CPU我们将要去运行。对于x86_64来说,是个空函数。这个过程如何处理呢?看到105行,这个intcall是初始化阶段的中断处理函数(牢记,初始化阶段至此,仍然处于实模式阶段,Linux内核的中断系统还没有被初始化,这个函数是内核编译后临时生成的一个bios服务程序,跟前面header.S中的那些int指令效果是一样的),就是将BIOS的寄存器设置成ireg变量。该变量分别针对32位、16位和8位而声明称以下一些联合体:(arch/x86/boot/Boot.h

 

struct biosregs {

       union {

              struct {

                     u32 edi;

                     u32 esi;

                     u32 ebp;

                     u32 _esp;

                     u32 ebx;

                     u32 edx;

                     u32 ecx;

                     u32 eax;

                     u32 _fsgs;

                     u32 _dses;

                     u32 eflags;

              };

              struct {

                     u16 di, hdi;

                     u16 si, hsi;

                     u16 bp, hbp;

                     u16 _sp, _hsp;

                     u16 bx, hbx;

                     u16 dx, hdx;

                     u16 cx, hcx;

                     u16 ax, hax;

                     u16 gs, fs;

                     u16 es, ds;

                     u16 flags, hflags;

              };

              struct {

                     u8 dil, dih, edi2, edi3;

                     u8 sil, sih, esi2, esi3;

                     u8 bpl, bph, ebp2, ebp3;

                     u8 _spl, _sph, _esp2, _esp3;

                     u8 bl, bh, ebx2, ebx3;

                     u8 dl, dh, edx2, edx3;

                     u8 cl, ch, ecx2, ecx3;

                     u8 al, ah, eax2, eax3;

              };

       };

};

 

当然,102行的initregs()函数是用来做一般初始化的:

 

void initregs(struct biosregs *reg)

{

       memset(reg, 0, sizeof *reg);

       reg->eflags |= X86_EFLAGS_CF;

       reg->ds = ds();

       reg->es = ds();

       reg->fs = fs();

       reg->gs = gs();

}

 

我把它贴出来的目的主要是为了说明一下ds()等函数,用来获取段寄存器:

static inline u16 ds(void)

{

       u16 seg;

       asm("movw %%ds,%0" : "=rm" (seg));

       return seg;

}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
x86汇编语言:从实模式到保护模式》主要讲述INTEL x86处理器的16位实模式、32位保护模式,至于虚拟8086模式,则是为了兼容传统的8086程序,现在看来已经完全过时,不再进行讲述。《x86汇编语言:从实模式到保护模式》的特色之一是提供了大量典型的源代码,这些代码以及相配套的工具程序可以到书中指定的网站,或者电子工业出版社华信教育资源网搜索下载。 每一种处理器都有它自己的机器指令集,而汇编语言的发明则是为了方便这些机器指令的记忆和书写。尽管汇编语言已经较少用于大型软件程序的开发,但从学习者的角度来看,要想真正理解计算机的工作原理,掌握它内部的运行机制,学习汇编语言是必不可少的。本书采用开源的NASM汇编语言编译器和VirtualBox虚拟机软件,以个人计算机广泛采用的Intel处理器为基础,详细讲解了Intel处理器的指令系统和工作模式,以大量的代码演示了16/32/64位软件的开发方法,介绍了处理器的16位实模式和32位保护模式,以及基本的指令系统。这是一本有趣的书,它没有把篇幅花在计算一些枯燥的数学题上。相反,它教你如何直接控制硬件,在不借助于BIOS、DOS、Windows、Linux或者任何其他软件支持的情况下来显示字符、读取硬盘数据、控制其他硬件等。本书可作为大专院校相关专业学生和计算机编程爱好者的教程。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值