www.pudn.com > czxtsycx1.zip > Mode_t.asm


.MODEL HUGE 
STACK       SEGMENT STACK PARA 'STACK' 
            DB 200 DUP(0) 
STACK       ENDS 
include \tc\g\include\g_def.asm 
CODE        SEGMENT WORD PUBLIC 'CODE' 
            ASSUME CS:CODE,DS:DATA,SS:STACK 
MODE_CHANGE PROC FAR 
START:      MOV AX,DATA 
            MOV DS,AX 
            CLI 
            MOV AX,STACK 
            MOV SS,AX 
            MOV SAVE_SS,AX 
            MOV SP,200 
            MOV SAVE_SP,SP 
            STI 
            MOV DS:FILE_OVER,1 
            ; 
            .386P 
            MOV AH,0DFH 
            CALL OPEN_A20 
            ; save current GDTR & IDTR 
            SGDT FWORD PTR SAVE_GDT 
            SIDT FWORD PTR SAVE_IDT 
            ;set desc for cs 
            MOV DI,OFFSET GDT_CS 
            MOV AX,CS 
            MOV CX,10H 
            MUL CX 
            MOV [DI].BASE_L,AX 
            MOV [DI].BASE_M,DL 
            ;set desc for ds 
            MOV DI,OFFSET GDT_DS 
            MOV DX,0 
            MOV AX,DS 
            MOV CX,10H 
            MUL CX 
            MOV [DI].BASE_L,AX 
            MOV [DI].BASE_M,DL 
            MOV [DI].BASE_H,DH 
            ;set desc for ss 
            MOV DI,OFFSET GDT_SS 
            MOV AX,SS 
            MOV CX,10H 
            MUL CX 
            MOV [DI].BASE_L,AX 
            MOV [DI].BASE_M,DL 
            ;set desc for gdt_buf 
            MOV DI,OFFSET GDT_BUF 
            MOV [DI].BASE_L,0      ;base_addr=2M 
            MOV [DI].BASE_M,020H 
            MOV [DI].GRAN,0FH      ;limit=1M 
            ; 
            CLI 
            MOV AX,DS 
            MOV CX,10H 
            MUL CX 
            ADD AX,OFFSET GDT_DEF  
                         ;DX:AX=32 address for GDT 
            ADC DX,0  
            MOV DTLOAD,AX 
            MOV DTLOAD+2,DX 
            MOV AX,OFFSET GDT_SIZE 
            SUB AX,OFFSET DTSIZE 
            ADD AX,1 
            MOV DTSIZE,AX 
            ;*********************************************** 
                                      ; mov file to c_buffer 
            MOV DS:G_BUF_SUM,0 
            MOV AX,3D02H              ;for read 
            LEA DX,FILE_NAME 
            INT 21H 
            JNC READ_FILE0 
            LEA DX,ERR_FILE 
            MOV AH,9 
            INT 21H 
            MOV AH,4CH 
            INT 21H 
 
READ_FILE0: MOV DS:FILE_HANDLE,AX 
READ_FILE:   
            MOV DS:SAVE_SS,SS 
            MOV DS:SAVE_SP,SP 
            SGDT FWORD PTR SAVE_GDT 
            SIDT FWORD PTR SAVE_IDT 
 
            MOV BX,DS:FILE_HANDLE  ;file_handle to BX 
            MOV CX,1024            ;to read byte_count 
            MOV DX,OFFSET C_BUFFER 
            MOV AH,3FH             ;read file 
            INT 21H 
            JNC READ_FILE1 
            MOV AX,0 
            MOV DS:C_BUF_SIZE,AX 
            MOV DS:FILE_OVER,AX 
            MOV AH,3EH            ;close file 
            INT 21H 
            JMP PROTECT_MODE 
READ_FILE1: MOV DS:C_BUF_SIZE,AX  ;read really byte_count 
            CMP AX,1024 
            JNL PROTECT_MODE 
            MOV DS:FILE_OVER,0 
            MOV BX,DS:FILE_HANDLE   
            MOV AH,3EH            ;close file 
            INT 21H 
            ;********************************************* 
PROTECT_MODE: 
            cli 
            LGDT FWORD PTR DTSIZE 
             
            MOV AX,GDT_DS_SEL 
            MOV DS,AX 
            MOV ES,AX 
            MOV FS,AX 
            MOV GS,AX 
            sti 
            ; 
            MOV EAX,00000001H 
            MOV CR0,EAX 
            JMP EDS_FLUSH         ;clear instructors 
EDS_FLUSH:  DB 0EAH 
            DW OFFSET MOVE_BUF 
            DW GDT_CS_SEL 
            ;**************************************** 
MOVE_BUF:    
            MOV AX,GDT_DS_SEL 
            MOV FS,AX 
            MOV AX,GDT_BUF_SEL 
            MOV GS,AX 
            CMP FS:C_BUF_SIZE,1 
            JL VRAM_DISP           ;file have be read over 
 
            MOV ECX,0 
            MOV CX,FS:C_BUF_SIZE 
            MOV EAX,OFFSET C_BUFFER 
            MOV ESI,EAX 
            MOV EDI,FS:G_BUF_SUM 
MOVE_BUF1:  MOV AL,FS:[ESI]        ;move to 2M 
            MOV GS:[EDI],AL 
            INC EDI 
            INC ESI 
            LOOP MOVE_BUF1 
 
            MOV FS:G_BUF_SUM,EDI 
            CMP FS:FILE_OVER,1 
            JL VRAM_DISP 
            ;***************** ;read again->start real_mode 
            CLI        
            MOV EAX,CR0 
            AND AX,NOT PE_ON 
            MOV CR0,EAX 
            ; 
            DB 0EAH 
            DW OFFSET REAL_MODE0 
            DW CODE 
REAL_MODE0: MOV AH,0DDH 
            CALL CLOSE_A20 
            ; 
            MOV AX,DATA 
            MOV DS,AX 
            LGDT FWORD PTR SAVE_GDT 
            LIDT FWORD PTR SAVE_IDT 
            cli 
            MOV SS,SAVE_SS 
            MOV SP,SAVE_SP 
            sti 
            JMP READ_FILE                 ;read again 
            ;*************************************** 
            ; all of file are moved to g_buf 
 
VRAM_DISP:   
            MOV AX,GDT_DS_SEL 
            MOV FS,AX 
            MOV AX,GDT_BUF_SEL 
            MOV GS,AX 
            MOV AX,VRAM_SEL 
            MOV ES,AX 
            MOV CX,08D0H 
            MOV BX,0 
L1:         MOV ES:[BX],0720H 
            ADD BX,2 
            LOOP L1 
 
            MOV ECX,FS:G_BUF_SUM 
            CMP ECX,2048 
            JL  LL 
            MOV ECX,2048 
LL:         MOV ESI,0 
            MOV EBX,480 
L2:         MOV AL,GS:[ESI] 
            MOV AH,22 
            MOV ES:[EBX],AX 
            ADD EBX,2 
            INC ESI 
            LOOP L2 
;turn to real_mode 
            CLI 
            MOV EAX,CR0 
            AND AX,NOT PE_ON 
            MOV CR0,EAX 
            ; 
            DB 0EAH 
            DW OFFSET REAL_MODE 
            DW CODE 
REAL_MODE:  MOV AH,0DDH 
            TO_DOS 
            .8086 
MODE_CHANGE ENDP 
include \tc\g\include\a20.asm 
 
CODE        ENDS 
DATA        SEGMENT WORD PUBLIC 'DATA' 
FILE_NAME   DB '\TC\G\MODE.TXT',0 
FILE_HANDLE DW 0 
FILE_OVER   DW 0 
ERR_FILE    DB 0DH,0AH,'Open file error$' 
OK_MSG      DB 0DH,0AH,'Have a nice day,Bye!   $' 
SAVE_GDT    DW 4 DUP(0) 
SAVE_IDT    DW 4 DUP(0) 
SAVE_SS     DW 0 
SAVE_SP     DW 0 
DTSIZE      DW 0 
DTLOAD      DW 0,0 
GDT_DEF     EQU $ 
            GDT_DESC <0,0,0,0,0,0> 
GDT_CS      GDT_DESC <0FFFFH,0,0,9AH,0,0> 
                           ;9AH=exec/read ,DPL=0 
GDT_DS      GDT_DESC <0FFFFH,0,0,92H,0,0> 
                           ;92H=P ,DPL=0,TYPE=2 
GDT_SS      GDT_DESC <0,0,0,96H,0,0>    
                           ;96H=R/W ,DOWN 
GDT_VRM     GDT_DESC <0FFFFH,08000H,0BH,92H,0,0> 
                           ;92H=P ,DPL=0,TYPE=2 
GDT_BUF     GDT_DESC <0FFFFH,0,0,92H,0,0> 
                           ;92H=P ,DPL=0,TYPE=2 ,length=1M 
GDT_SIZE    DW 0 
 
C_BUF_SIZE  DW 0 
G_BUF_SUM   DD 0 
C_BUFFER    DB 1024 DUP(?) 
DATA        ENDS 
            END START