彙編語言裸機實現時鐘程序-BCD轉ASCII,修改中斷向量表

爲了熟悉BIOS的各種中斷功能,所以寫來練練手。

注:以下所有中斷均爲BIOS中斷,無DOS中斷。

先說一下實現思路:

一、先能取得當前系統時間,查BIOS中斷知道

7、時鐘服務(Clock Service——INT 1AH)
00H —讀取時鐘滴答計數

01H —設置時鐘滴答計數

02H —讀取時間

03H —設置時間

04H —讀取日期

05H —設置日期

06H —設置鬧鐘
07H —鬧鐘復位
0AH —讀取天數計數
0BH —設置天數計數
80H —設置聲音源信息

其中

(3)、功能02H
功能描述:讀取時間

入口參數:AH02H
出口參數:CHBCD碼格式的小時

CL
BCD碼格式的分鐘
DH
BCD碼格式的秒
DL
00H——標準時間,否則,夏令時
CF
0——時鐘在走,否則,時鐘停止

調用1AH號中斷的02H功能就可以得到當前系統的時間。

二、顯示當前系統時間

查表

1、顯示服務(Video Service——INT 10H)
00H —設置顯示器模式
01H —
設置光標形狀
02H —
設置光標位置
03H —
讀取光標信息式
04H —
讀取光標位置
05H —
設置顯示頁
06H
07H —初始化或滾屏
08H —
讀光標處的字符及其屬性
09H —
在光標處按指定屬性顯示字符
0AH —
在當前光標處顯示字符
0BH —
設置調色板、背景色或邊框
0CH —
寫圖形象素
0DH —
讀圖形象素
0EH —
Teletype模式下顯示字符
0FH —
讀取顯示器模
10H —
顏色
11H —
字體
12H —
顯示器的配置
13H —
Teletype模式下顯示字符串
1AH —
讀取/設置顯示組合編碼
1BH —
讀取功能/狀態信息
1CH —
保存/恢復顯示器狀態

其中
(19)、功能13H
功能描述:在Teletype模式下顯示字符串
入口參數:AH
=13H
BH
=頁碼
BL=屬性(AL=00H
或01H)
CX
=顯示字符串長度
(DH、DL)=座標(
行、列)
ES:BP=顯示字符串的地址 AL
=顯示輸出方式
0——字符串中只含顯示字符,其顯示屬性在BL
中。顯示後,光標位置不變
1——字符串中只含顯示字符,其顯示屬性在BL
中。顯示後,光標位置改變
2——字符串中含顯示字符和顯示屬性。顯示後,光標位置不變

3——
字符串中含顯示字符和顯示屬性。顯示後,光標位置改變
出口參數:無

調用10H號中斷的13H功能可以顯示字符串,但是該功能入口參數是ASCII碼,可是第一步中得到的是BCD碼,所以必須有一個轉碼的過程。

一組BCD碼4個位,可以直接轉換爲二進制數然後加上數字0的ASCII碼即爲該BCD對應數值的ASCII碼。

 

三、動態顯示當前時間

這是這程序的關鍵地方,實現方式,可以用程序查詢當前時間若改變就重新顯示當前時間,這只是最初的想法,並沒有編碼實現。理論上應該是可行的。

後來BIOS中斷向量表,發現

8H號中斷,是系統自動觸發的中斷,每隔1/18.2秒觸發一次,這個時間遠小於1秒,所以我們可以讓這個中斷的服務程序來刷新時鐘的顯示,

這個中斷的的服務程序入口在

70H

1CH

28

指向每1/18.2秒時可執行的服務程序的入口。初始化時該向量指向一條IRET指令。用戶可修改該向量,用戶可修改該向量,使它指向自己的程序。

只要修改這個向量的值爲我們的顯示當前時間的函數地址,就可以每隔1/18.2秒顯示一次當前時間,就可以以秒爲單位動態顯示時間。
修改中斷服務程序入口地址的方法有兩個
1).調用DOS中斷21H的25H功能
2).直接修改內存內容值
因爲是裸機,所以當然用第二種方法。
下面給出程序源碼:
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章