版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報或認(rèn)領(lǐng)
文檔簡介
1、實(shí)驗(yàn)三一、實(shí)驗(yàn)?zāi)康?. 掌握TASM匯編語言與TURBO C語言匯合編程的方法。2. 實(shí)現(xiàn)內(nèi)核與引導(dǎo)程序分離,掌握軟盤上引導(dǎo)操作系統(tǒng)方法。3. 設(shè)計并實(shí)現(xiàn)一種簡單的作業(yè)控制語言,建立具有較友好的控制命令的批處理原型操作系統(tǒng),掌握操作系統(tǒng)提供用戶界面和內(nèi)部功能的實(shí)現(xiàn)方法。二、實(shí)驗(yàn)內(nèi)容在實(shí)驗(yàn)二的基礎(chǔ)上,進(jìn)化你的原型操作系統(tǒng),增加下列操作系統(tǒng)功能:(1)將原型操作系統(tǒng)分離為引導(dǎo)程序和MYOS內(nèi)核,由引導(dǎo)程序加載內(nèi)核;(2)內(nèi)核由匯編語言kernal.asm和c語言kernal.c二個模塊生成;(3)利用C語言實(shí)現(xiàn)作業(yè)控制語言mJCB,原型操作系統(tǒng)在當(dāng)前行顯示一個指示符(可以是簡單的一個字符或你的學(xué)號
2、之類),允許用戶輸入一行命令(回車結(jié)束,語法由你設(shè)計),操作系統(tǒng)解釋命令并完成相應(yīng)的功能(3個以上的內(nèi)置功能,如time、date、asc等,而且能執(zhí)行軟盤上的某個用戶程序),并在你的實(shí)驗(yàn)報告中詳細(xì)介紹你的mJCB語言的語法格式和功能。三、實(shí)驗(yàn)報告1、涉及的基礎(chǔ)知識和實(shí)驗(yàn)環(huán)境工具綜述、你的解決方案包括程序算法原理或流程圖、程序模塊說明、變量定義與作用說明、數(shù)據(jù)結(jié)構(gòu)組織等A 實(shí)驗(yàn)環(huán)境工具綜述:本次試驗(yàn)環(huán)境為VMware9平臺上搭建的8086虛擬機(jī),編譯器為tasm,tcc,鏈接器為tlink,通過Winhex剪輯2進(jìn)制文件,并用DiskWriter工具將主程序?qū)懭胩摂M軟盤,通過虛擬機(jī)加載軟盤實(shí)現(xiàn)
3、裸機(jī)運(yùn)行。B 算法原理:a) 計算機(jī)啟動后,通過引導(dǎo)扇區(qū)加載軟盤上余下的有效扇區(qū)。b) 引導(dǎo)扇區(qū)安裝必要的中斷,如8號中斷用以動態(tài)顯示時間,21號中斷用以用戶程序的返回,設(shè)置棧指針,數(shù)據(jù)段指針,建立c語言運(yùn)行環(huán)境,設(shè)置計數(shù)器,用以動態(tài)顯示時間。配置完成后,轉(zhuǎn)入基于c語言的控制程序的運(yùn)行。c) 基于c語言的控制程序無限重復(fù)向輸入端請求命令,解析命令,跳轉(zhuǎn)調(diào)用對應(yīng)程序,但接收到重啟命令時重啟,接到關(guān)機(jī)命令時進(jìn)行關(guān)機(jī)。d) 系統(tǒng)總的實(shí)現(xiàn)為引導(dǎo)程序(osa.asm),匯編實(shí)現(xiàn)的c語言函數(shù)庫(clib.asm),匯編實(shí)現(xiàn)的中斷程序庫(oslib.asm),c語言實(shí)現(xiàn)的控制臺程序(osc.c)。e) 由于
4、系統(tǒng)已搭建c語言運(yùn)行環(huán)境,并提供了相應(yīng)的庫,再提供一個供用戶用于鏈接c語言程序的啟動程序,用戶程序即可完全由c語言實(shí)現(xiàn)。啟動程序指定用戶程序的偏移(如c9000.asm指定了用戶的c程序偏移為9000h,可更改啟動程序中的org來更改目標(biāo)程序的偏移),并能夠返回控制臺(通過調(diào)用自己安裝的int 21H返回)。C 程序模塊說明:a) clib.asm中匯編實(shí)現(xiàn)的c函數(shù)庫extern char cls();功能:清屏,清空第0頁的顯存輸入:無返回:無extern int puts(const char * str);功能:向當(dāng)前光標(biāo)位置輸出字符串輸入:字符串首地址返回:輸出字符個數(shù)extern c
5、har* gets(char* str);功能:讀取字符串輸入:字符串首地址返回:字符串首地址extern int strlen(const char *str);功能:求以0結(jié)束的字符串的長度輸入:字符串首地址返回:字符從長度extern int getchar(void);功能:讀取字符輸入:無返回:字符的ascii碼extern int putchar(int c);功能:輸出字符輸入:字符c返回:字符cextern unsigned int port_in8(unsigned int port);功能:從port端口讀入8位數(shù)據(jù)輸入:端口號返回:讀取的數(shù)據(jù)extern unsigned
6、 int port_in16(unsigned int port); 功能:從port端口讀入16位數(shù)據(jù)輸入:端口號返回:讀取的數(shù)據(jù)extern void port_out8(unsigned int port, unsigned int value); 功能:向port端口輸出8位數(shù)據(jù)value輸入:端口號和數(shù)據(jù)返回:無 extern void port_out16(unsigned int port, unsigned int value); 功能:從port端口輸出16位數(shù)據(jù)value輸入:端口號和數(shù)據(jù)返回:無extern void setp_cursor(unsigned int bh
7、, unsigned int dh, unsigned int dl); 功能:將第bh頁的指針置于dh行dl列 輸入:頁號bh,行號dh,列號dl 返回:無extern void run_pro(int ord); 功能:運(yùn)行程序地址表中第ord號程序輸入:程序序號返回:無b) 主控制程序:osc.cextern char cls(); extern int puts(const char * str);extern char* gets(char* str);extern int strlen(const char *str);extern int getchar(void);extern
8、 int putchar(int c);extern unsigned int port_in8(unsigned int port);extern unsigned int port_in16(unsigned int port);extern void port_out8(unsigned int port, unsigned int value);extern void port_out16(unsigned int port, unsigned int value);extern void setp_cursor(unsigned int bh, unsigned int dh, un
9、signed int dl);extern void run_pro(int ord);void inttostr(int x, char *str);int strtoint(char *str);unsigned int bcdtodex(unsigned int x);void get_date(char* buf);/*yy-mm-dd*/void set_date(char *buf);void get_time(char* buf);/*hh:mm:ss*/void set_time(char *buf);void pre_time();void interface();int s
10、trcmp(char str1, char str2);void atoA(char *buf);int deal(char *buf);int inside(int min, int max, int x);int change_time(int paras);int islegal(int y, int m, int d);int change_date(int paras);int shutdown(int paras);int reboot(int paras);int jc(int paras, char *buf);char buffer80;int control = 1;cha
11、r Exit_Message30 = nPress any key to exit.;unsigned int add_Table30 = 0x9000, 0, 0xa000, 0, 0xb000, 0;cmain()int paras;control = 0;while (1)cls();interface();gets(buffer);setp_cursor(0, 6, 0);paras = deal(buffer);if (paras != 0) jc(paras, buffer);puts(Exit_Message);getchar();c) 用戶程序:cx0.c cx1.c2、實(shí)驗(yàn)步
12、驟、操作的主要過程、運(yùn)行結(jié)果、屏幕畫面截圖等A 實(shí)驗(yàn)步驟a) 編寫代碼b) 在dosbox上執(zhí)行批處理文件0.bat,得到,執(zhí)行9000.bat得到用戶程序1,執(zhí)行a000.bat得到用戶程序2c) 使用WinHex將中7e00h到結(jié)束的所有數(shù)據(jù)寫到虛擬軟盤文件Tinix.img偏移為0的位置處,將用戶程序1和用戶程序2對應(yīng)的代碼寫到1400h和2400h處。d) 從軟盤啟動虛擬機(jī)B 屏幕截圖a) 開機(jī)界面b) 時間設(shè)置c) 日期設(shè)置 d) 運(yùn)行程序地址表中的用戶程序e) 指令參數(shù)錯誤檢查f) 執(zhí)行重啟命令,由于重啟時無法截圖,只提供命令輸入界面g) 關(guān)機(jī)指令C 指令總
13、結(jié)a) Time 修改cmos時間,不需要參數(shù)b) Date 修改cmos日期,不需要參數(shù)c) Run x執(zhí)行第x號用戶程序,1=x=2,安裝新程序x需擴(kuò)展。d) Reboot 重啟,不需要參數(shù)e) Shutdown 關(guān)機(jī),不需要參數(shù)四、實(shí)驗(yàn)心得體會A. 程序c語言環(huán)境的配置和實(shí)現(xiàn),應(yīng)基于編譯器tcc默認(rèn)的調(diào)用規(guī)范cdecl。a) cdecl在8086上對c語言參數(shù)的入棧順序?yàn)閺挠蚁蜃笕霔#瑢5幕謴?fù)由程序調(diào)用者caller實(shí)現(xiàn),匯編實(shí)現(xiàn)c語言函數(shù)庫時,不需要在函數(shù)中對棧進(jìn)行恢復(fù)。在匯編程序中調(diào)用c實(shí)現(xiàn)的函數(shù),對參數(shù)壓棧和對函數(shù)返回后要注意恢復(fù)。b) cdecl對函數(shù)的返回值,8位,16位和3
14、2位分別存放于al、ax、dx和ax中,匯編中調(diào)用c實(shí)現(xiàn)的函數(shù)時返回值的獲取為以上寄存器。c) cdecl只對ds,ss,bp,si,di等寄存器進(jìn)行保護(hù)。當(dāng)在匯編中調(diào)用c實(shí)現(xiàn)的函數(shù)時,若通用寄存器ax,bx,cx,dx中存在有意義的值,要自行進(jìn)行壓棧保護(hù)。B. 實(shí)現(xiàn)tcc的過程中,發(fā)現(xiàn)tcc在棧的處理上存在bug。tcc編譯tcc_bug文件得到的二進(jìn)制文件,通過debug反匯編解析,發(fā)現(xiàn),tcc對函數(shù)中的臨時字符串buf的取值從bx + offset中?。óa(chǎn)生錯誤的位置在tcc_bug.c文件中有標(biāo)注),而bx默認(rèn)的段地址為ds而不是ss。當(dāng)ds不等于ss時,會取出錯誤的值,產(chǎn)生亂碼。解決
15、方法:通過在引導(dǎo)程序中配置c語言環(huán)境時ds和ss設(shè)置相同的值,成功解決產(chǎn)生亂碼的問題。C. 由于8086程序在dos上運(yùn)行是使用int 21h的4ch號功能返回控制臺,本次實(shí)驗(yàn)對安裝了僅有單個iret指令的21h中斷,來實(shí)現(xiàn)初步對dos程序的小的兼容,用于與用戶的c語言鏈接的啟動程序使用int 21h調(diào)用安裝的iret進(jìn)行返回控制臺。Osc.cextern char cls(); extern int puts(const char * str);extern char* gets(char* str);extern int strlen(const char *str);extern int
16、 getchar(void);extern int putchar(int c);extern unsigned int port_in8(unsigned int port);extern unsigned int port_in16(unsigned int port);extern void port_out8(unsigned int port, unsigned int value);extern void port_out16(unsigned int port, unsigned int value);extern void setp_cursor(unsigned int bh
17、, unsigned int dh, unsigned int dl);extern void run_pro(int ord);void inttostr(int x, char *str);int strtoint(char *str);unsigned int bcdtodex(unsigned int x);void get_date(char* buf);/*yy-mm-dd*/void set_date(char *buf);void get_time(char* buf);/*hh:mm:ss*/void set_time(char *buf);void pre_time();v
18、oid interface();int strcmp(char str1, char str2);void atoA(char *buf);int deal(char *buf);int inside(int min, int max, int x);int change_time(int paras);int islegal(int y, int m, int d);int change_date(int paras);int shutdown(int paras);int reboot(int paras);int jc(int paras, char *buf);char buffer8
19、0;int control = 1;char Exit_Message30 = nPress any key to exit.;unsigned int add_Table30 = 0x9000, 0, 0xa000, 0, 0xb000, 0;cmain()int paras;control = 0;while (1)cls();interface();gets(buffer);setp_cursor(0, 6, 0);paras = deal(buffer);if (paras != 0) jc(paras, buffer);puts(Exit_Message);getchar();/*c
20、ontrol = 1;*/void inttostr(int x, char *str)int l = 0;int i, offset;char buf10;if (x = 0) str0 = 0;str1 = 0;return;if (x 0)bufl = x % 10 + 0;x = x / 10;l+;for (i = 0; i l; +i)strl - i - 1 + offset = bufi;strl + offset = 0;int strtoint(char *str)int len = strlen(str);int i;int sou;int p;int ans; if (
21、str0 = -)sou = 1;p = -1;elsesou = 0;p = 1;ans = 0;for (i = sou; i 4) * 10 + (x & 0xf);void get_date(char* buf)/*yy-mm-dd*/unsigned int y, m, d;port_out8(0x70, 9); /*獲取年*/y = port_in8(0x71) & 0xff;buf0 = (y 4) + 0;buf1 = (y & 0xf) + 0;buf2 = -;port_out8(0x70, 8);/*獲取月*/m = port_in8(0x71) & 0xff;buf3
22、= (m 4) + 0;buf4 = (m & 0xf) + 0;buf5 = -;port_out8(0x70, 7);/*獲取日*/d = port_in8(0x71) & 0xff;buf6 = (d 4) + 0;buf7 = (d & 0xf) + 0;buf8 = 0;void set_date(char *buf)unsigned int y, m, d;y = (buf0 - 0) 4) + buf1 - 0;port_out8(0x70, 9); port_out8(0x71, y);m = (buf3 - 0) 4) + buf4 - 0;port_out8(0x70, 8
23、);port_out8(0x71, m);d = (buf6 - 0) 4) + 0;buf1 = (h & 0xf) + 0;buf2 = :;port_out8(0x70, 2);/*獲取分*/m = port_in8(0x71) & 0xff;buf3 = (m 4) + 0;buf4 = (m & 0xf) + 0;buf5 = :;port_out8(0x70, 0);/*獲取秒*/s = port_in8(0x71) & 0xff;buf6 = (s 4) + 0;buf7 = (s & 0xf) + 0;buf8 = 0;void set_time(char *buf)unsig
24、ned int h, m, s;h = (buf0 - 0) 4) + buf1 - 0;port_out8(0x70, 4); port_out8(0x71, h);m = (buf3 - 0) 4) + buf4 - 0;port_out8(0x70, 2);port_out8(0x71, m);s = (buf6 - 0) 4) + buf7 - 0;port_out8(0x70, 0);port_out8(0x71, s);void pre_time()char buf20;/*setp_cursor(0, 1, 62);*/*puts(Time:);*/setp_cursor(0,
25、1, 70);get_time(buf);puts(buf);/*setp_cursor(0, 2, 62);*/*puts(Date:);*/setp_cursor(0, 2, 70);get_date(buf);puts(buf);void interface()int i;int pos4;pos0 = 0;pos1 = 8;pos2 = 60;pos3 = 79;cls();setp_cursor(0, 0, 0);for (i = 0; i 80; +i)putchar(=);for (i = 0; i 4; +i)setp_cursor(0, 1, posi);putchar(|)
26、;for (i = 0; i 4; +i)setp_cursor(0, 2, posi);putchar(|);setp_cursor(0, 3, 0);for (i = 0; i 80; +i)putchar(=);setp_cursor(0, 1, 2);puts(Lab03);setp_cursor(0, 1, 62);/*把以下部分放到pre_time,亂碼,尋址問題?*/puts(Time:);setp_cursor(0, 2, 62);puts(Date:);pre_time();setp_cursor(0, 2, 30);puts(MYOS 3.0);setp_cursor(0,
27、 4, 0);puts(Input command:);setp_cursor(0, 5, 0);for (i = 0; i 80; +i)putchar(-);setp_cursor(0, 4, 14);int strcmp(char str1, char str2)int len1 = strlen(str1);int len2 = strlen(str2);int i = 0, j = 0;while (i len1 & j len2 & str1i = str2j)i+;j+;return (str2j - str1i);void atoA(char *buf)int len = st
28、rlen(buf);int i;for (i = 0; i len; +i)if (a = bufi & bufi = z) bufi -= a - A;int deal(char *buf)int len = strlen(buf);int pos = 0;int pos0 = 0;int paras;paras = 0;atoA(buf);while (pos len)while (bufpos = ) pos+;if (pos len) paras+;while (pos len & bufpos != )bufpos0 = bufpos;pos0+;pos+;bufpos0 = 0;p
29、os0+;pos+;return paras;int inside(int min, int max, int x)return (min = x & x = max);int change_time(int paras)char t10;int h, m, s;int tx6;int x, i;tx0 = 0; tx1 = 1; tx2 = 3; tx3 = 4; tx4 = 6; tx5 = 7;if (paras != 1) puts(-2: Parameter is wrong!);return -2;puts(Input time hh:mm:ss: );gets(t);x = 0;
30、for (i = 0; i 6; +i)if (!inside(0, 9, ttxi) x = 1; if (x = 0 & strlen(t) = 8 & t2 = : & t5 = :)t2 = 0; t5 = 0;h = strtoint(t + 0);m = strtoint(t + 3);s = strtoint(t + 6);if (inside(0, 23, h) & inside(0, 59, m) & inside(0, 59, s)set_time(t);elsex = 1;if (x = 1)puts(-3: The time you inputed is wrong!)
31、;return -3;puts(0: Success!);return 0;int islegal(int y, int m, int d)if (m = 1 | m = 3 | m = 5 | m = 7 | m = 8 | m = 10 | m = 12) & (1 = d & d = 31) return 1;if (m = 4 | m = 6 | m = 9 | m = 11) & (1 = d & d = 30)return 1;if (m = 2 & ( (y % 4 = 0) & (y % 100 != 0) | (y % 400 = 0) & (1 = d & d = 29)
32、) | (1 = d & d = 28) return 1;return 0;int change_date(int paras)char t10;int y, m, d;int tx6;int x, i;tx0 = 0; tx1 = 1; tx2 = 3; tx3 = 4; tx4 = 6; tx5 = 7;if (paras != 1) puts(-2: Parameter is wrong!);return -2;puts(Input date YY-MM-DD: );gets(t);x = 0;for (i = 0; i 結(jié)束cmp al, 08je _gets_2;是否為Backsp
33、ace;yes刪除字符2cmp al, 32jb _gets_1;是否為可視字符cmp al, 126ja _gets_1;是否為可視字符mov ah, 0call near ptr charstack;入棧處理jmp _gets_3;顯示字符串3_gets_2:;刪除字符2mov ah, 1call near ptr charstack;出棧處理_gets_3:;顯示字符串mov ah, 2call near ptr charstackjmp _gets_1;繼續(xù)讀取字符_gets_return:mov ah, 0mov al, 0call near ptr charstackmov ax,
34、 10push axcall near ptr _putcharpop cxmov ax, si;返回字符串地址pop sipop bpret_gets endp;函數(shù)名稱:charstack;功能:存放最多topmax個字符;函數(shù)輸入:ah=功能號,0表示入棧,1表示出棧,2表示顯示,3返回棧當(dāng)前大小;4表示清空棧;ds:si指向字符棧空間起始地址;上升型空棧;對于0號功能:al=入棧字符;對于1號功能:al=返回字符;對于2號功能:dh、dl分別表示行和列號,bh為頁號,bl為屬性;對于3號功能:ax返回top值;對于4號功能:清空棧top、len = 0; bug 由于int 10H 在
35、窗口右下角,輸出字符串長于有限位數(shù)時,; 會自動將顯存中內(nèi)容向上挪動一行,并且不會回退,跟dos一樣,; 所有不太好看,沒了topmax equ 65charstack procjmp short charstack_startptabledw charstack_push, charstack_popdw charstack_show, charstack_sizedw charstack_cleartopdw 0lendw 0charstack_start:push bxpush cxpush dxpush bppush escmp ah, 4ja charstack_returnmov
36、cl, ahmov ch, 0add cx, cxmov bp, cxjmp word ptr cs:bp + ptablecharstack_push:cmp word ptr cs:top, topmaxjne charstack_push_1sub word ptr cs:top, 1charstack_push_1:mov bx, cs:topmov si + bx, aladd word ptr cs:top, 1jmp short charstack_returncharstack_pop:cmp word ptr cs:top, 0je charstack_returndec w
37、ord ptr cs:topmov bx, cs:topmov al, si + bxjmp short charstack_returncharstack_show:push axmov cx, cs:lenmov ah, 20Hcall near ptr printcmov cx, dsmov es, cxmov cx, cs:topmov cs:len, cxmov bp, simov ax, 1301Hint 10Hmov ah, 01mov cx, 0607hint 10Hpop axjmp short charstack_returncharstack_size:mov ax, cs:topjmp short charstack_returncharstack_clear:mov word ptr cs:top, 0mov word ptr cs:len, 0charstack_return:pop espop bppop dxpop cxpop bxretcharstack endp;函數(shù)名:printc;功能:重復(fù)輸出同一字符;函數(shù)輸入:dh:行號,dl:列號,bh:頁號,bl屬性,ah:字符,cx:次數(shù);函數(shù)輸
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 高中地理 第二單元 第2節(jié)《氣壓帶和風(fēng)帶》教學(xué)設(shè)計 新人教版必修1
- 八年級生物上冊 第六單元 生物的多樣性及其保護(hù) 第二章 認(rèn)識生物的多樣性教案 (新版)新人教版
- 2024-2025學(xué)年新教材高中歷史 第一單元 第1課 中華文明的起源與早期國家教案3 新人教版必修《中外歷史綱要(上)》
- 2024城市軌道交通建設(shè)合同標(biāo)的
- 2024年農(nóng)田林網(wǎng)建設(shè)及果樹種植承包合同
- 2024年大額個人借款正式合同
- 2024企業(yè)信息化建設(shè)合同屬性規(guī)定
- 2024年基因檢測與藥物研發(fā)合同
- 2024年工程保險與擔(dān)保協(xié)議
- 2024年品牌授權(quán)使用合同包含知識產(chǎn)權(quán)保護(hù)
- 喬丹體育侵權(quán)案例
- 廣告學(xué)專業(yè)大學(xué)生職業(yè)規(guī)劃
- 第一講人民幣匯率與人民幣國際化
- 《世界的聚落》知識點(diǎn)解析
- 通達(dá)信系統(tǒng)指標(biāo)公式
- 2024中國罕見病行業(yè)趨勢觀察報告
- 創(chuàng)作屬于自己的戲劇舞臺美術(shù)設(shè)計
- 蘇教版2022-2023五年級數(shù)學(xué)上冊全冊教材分析
- 埋地鋼質(zhì)管道腐蝕與防護(hù)
- 人工智能對教育考試的改革與應(yīng)用
- 會議宴會接待通知單
評論
0/150
提交評論