boot/include/lib_in_real_mode.inc

Code:
  1. ;By Marcus Xing   
  2. ;boot/include/lib_in_real_mode.inc   
  3. ;在boot/loader.asm中在实模式下调用的函数   
  4.   
  5. ;--------------------------------------------------------------------Read_Sector   
  6. Read_Sector:   
  7. ;C函数原型(实模式下调用,短调用):   
  8. ;void Read_Sector(byte16 first_sector_index,byte16 read_sector_number);   
  9. ;注意:   
  10. ;调用前es:bx必须指向缓冲区,ds指向数据区   
  11. ;逻辑扇区号转化为系统调用所需参数的公式如下:   
  12. ;相对扇区号/每磁道扇区号(18)的商Q,余数R   
  13. ;其中:柱面号=Q>>1,磁头号=Q&1,相对起始扇区号=R+1   
  14.   
  15. ;对应的系统调用API如下:   
  16. ;功能号ah=02  
  17. ;hal=要读的扇区数   
  18. ;ch=柱面(磁道)号   
  19. ;cl=起始扇区号   
  20. ;dh=磁头号,dl=驱动器号(0表示A盘)   
  21. ;es:bx缓冲区地址   
  22.   
  23.     push    bp   
  24.     mov bp,sp   
  25.     push    ax   
  26.     push    bx   
  27.     push    cx   
  28.     push    dx   
  29.        
  30.     push    bx                      ;暂存缓冲区偏移   
  31.     mov ax,[bp + 6]                 ;取得要读取的扇区数   
  32.     push    ax                      ;暂时保存之   
  33.     mov ax,[bp + 4]                 ;取得要读的逻辑扇区号   
  34.     mov bl,18      
  35.     div bl                          ;除以每柱面扇区数   
  36.     mov ch,al                                  
  37.     shr ch,1                        ;ch<-柱面号   
  38.     mov dh,al   
  39.     and dh,1                        ;dh<-磁头号   
  40.     mov cl,ah   
  41.     inc cl                          ;cl<-相对扇区号   
  42.     mov dl,0                        ;读A盘   
  43.     pop ax                          ;al<-要读的扇区数   
  44.     pop bx                          ;恢复缓冲区偏移   
  45.        
  46. .Go_On_Reading:   
  47.     mov ah,2                        ;ah<-功能号   
  48.     int 13h   
  49.     jc  .Go_On_Reading              ;如果cf=1,继续读   
  50.        
  51.     pop dx   
  52.     pop cx   
  53.     pop bx   
  54.     pop ax   
  55.        
  56.     pop bp   
  57.     ret   
  58. ;------------------------------------------------------------------Get_FAT_Entry   
  59. Get_FAT_Entry:   
  60. ;C函数原型(实模式下调用,短调用):   
  61. ;u16 Get_FAT_Entry(u16 Sector_No_In_Data_Area);   
  62. ;功能:   
  63. ;入口参数为数据区的相对扇区号,返回值为相应的FAT的值,以表示还有没有下一个扇区   
  64. ;ds指向数据区,在此函数中,es:bx=9000h-100h:0用来作为读FAT的缓冲区   
  65.     push    bp   
  66.     mov bp,sp   
  67.   
  68.     push    bx   
  69.     push    dx   
  70.     push    es   
  71.        
  72.     mov byte [_b_Is_Odd],0      ;作用为局部变量,标记相对FAT的条目索引   
  73.        
  74.     ;es指向9000h-100h   
  75.     mov ax,Base_Of_Loader   
  76.     sub ax,100h   
  77.     mov es,ax   
  78.        
  79.     ;1个FAT条目为12位,条目索引*3/2 = *1.5   
  80.     ;ax为相对FAT字节偏移   
  81.     mov ax,[bp + 4]   
  82.     mov bx,3   
  83.     mul bx   
  84.     mov bx,2   
  85.     div bx   
  86.        
  87.     ;判断余数是否为0,是的话为偶,跳转到   
  88.     ;对应标号,否的话把标记变量置1   
  89.     cmp dx,0   
  90.     je  LABEL_EVEN   
  91.     mov byte [_b_Is_Odd],1   
  92.        
  93. LABEL_EVEN:   
  94.     ;ax=当前条目在FAT的相对逻辑偏移扇区   
  95.     ;dx=当前条目相对当前扇区的字节偏移   
  96.     xor dx,dx   
  97.     mov bx,512   
  98.     div bx   
  99.        
  100.     add ax,1                                ;ax自增1,求得相对整个软盘的逻辑扇区偏移   
  101.        
  102.     ;读2个FAT扇区到缓冲区,一次读2个,   
  103.     ;因为FAT条目可能跨越2个扇区   
  104.     xor bx,bx   
  105.     push    2   
  106.     push    ax   
  107.     call    Read_Sector   
  108.     add sp,4   
  109.   
  110.     mov bx,dx                               ;es:bx指向要求的条目首字节   
  111.     mov ax,[es:bx]                          ;把首字节存到ax   
  112.     cmp byte [_b_Is_Odd],1                  ;判断奇偶,奇偶有不同的处理方式   
  113.     jne LABEL_EVEN2   
  114.     shr ax,4                                ;奇数的处理方式   
  115.        
  116. LABEL_EVEN2:                                ;偶数的处理方式   
  117.     and ax,0fffh                            ;返回值放到ax中   
  118.        
  119. LABEL_DONE:   
  120.     pop es   
  121.     pop dx   
  122.     pop bx   
  123.   
  124.     pop bp   
  125.     ret   
  126. ;----------------------------------------------------------Disp_Str_In_Real_Mode   
  127. Disp_Str_In_Real_Mode:   
  128. ;C函数原型(实模式下调用,短调用):   
  129. ;void Disp_Str_In_Real_Mode(const char *p_sz_Str);   
  130. ;注意:   
  131. ;在变量_w_Disp_Pos处显示字符串,ds指向数据区,es的值在此函数中指向数据区   
  132.     push    bp   
  133.     mov bp,sp   
  134.        
  135.     push    ax   
  136.     push    bx   
  137.     push    cx   
  138.     push    dx   
  139.     push    di   
  140.     push    es   
  141.        
  142. ;此BIOS中断API   
  143. ;功能13H    
  144. ;功能描述:在Teletype模式下显示字符串   
  145. ;入口参数:AH=13H   
  146. ;BH=页码   
  147. ;BL=属性(若AL=00H或01H)   
  148. ;CX=显示字符串长度   
  149. ;(DH、DL)=坐标(行、列)   
  150. ;ES:BP=显示字符串的地址 AL=显示输出方式   
  151. ;0——字符串中只含显示字符,其显示属性在BL中。显示后,光标位置不变   
  152. ;1——字符串中只含显示字符,其显示属性在BL中。显示后,光标位置改变   
  153. ;2——字符串中含显示字符和显示属性。显示后,光标位置不变   
  154. ;3——字符串中含显示字符和显示属性。显示后,光标位置改变   
  155. ;出口参数:无   
  156.   
  157.     mov ax,ds   
  158.     mov es,ax      
  159.     mov bp,[bp + 4]                     ;取得要打印的字符串指针   
  160.        
  161.     mov al,[es:bp]   
  162.     cmp al,0ah   
  163.     jne .3   
  164.     mov ax,[_w_Disp_Pos_In_RM]   
  165.     mov bl,80   
  166.     div bl   
  167.     inc al   
  168.     mul bl   
  169.     mov [_w_Disp_Pos_In_RM],ax   
  170.     jmp .4   
  171.        
  172. .3:    
  173.     mov ax,[_w_Disp_Pos_In_RM];得到显示地址   
  174.     mov bl,80   
  175.     div bl   
  176.     mov dh,al                           ;dh<-行号   
  177.     mov dl,ah                           ;dl<-列号   
  178.        
  179.     xor cx,cx                           ;字符串长度计数器   
  180.     mov di,bp                           ;做临时指针es:di指向字符串   
  181.        
  182. .1:   
  183.     mov al,byte [es:di]   
  184.     cmp al,0                            ;遇到0计数结束   
  185.     je  .2   
  186.     inc cx                              ;计数器自增1   
  187.     inc di                              ;临时指针自增1   
  188.     jmp .1   
  189.   
  190. .2:   
  191.     add word [_w_Disp_Pos_In_RM],cx ;显示地址加上字符串长度   
  192.     mov bx,0007h                        ;bh表示第0页,bl表示字符颜色   
  193.     mov ax,1301h                        ;al为输出方式1   
  194.        
  195.     int 10h   
  196.        
  197. .4:   
  198.     pop es   
  199.     pop di   
  200.     pop dx   
  201.     pop cx   
  202.     pop bx   
  203.     pop ax   
  204.        
  205.     pop bp   
  206.     ret   
  207.        
  208. ;---------------------------------------------------------------------Kill_Motor   
  209. Kill_Motor:   
  210. ;C函数原型(实模式下调用,短调用):   
  211. ;void Kill_Motor();   
  212. ;功能:   
  213. ;如名字所示,以免马达灯长亮   
  214.     push    ax   
  215.     push    dx   
  216.        
  217.     mov dx,03f2h   
  218.     mov al,0   
  219.     out dx,al   
  220.        
  221.     pop dx   
  222.     pop ax   
  223.   
  224.     ret   
  225.       

你可能感兴趣的:(c,api,kill,byte)