Path: utzoo!utgpu!jarvis.csri.toronto.edu!cs.utexas.edu!tut.cis.ohio-state.edu!mailrus!iuvax!rutgers!umn-d-ub!cs.umn.edu!kemp From: kemp@umn-cs.cs.umn.edu (Stuart R. Kemp) Newsgroups: comp.sys.ibm.pc Subject: 4 gigs in Real Mode Message-ID: <1990Feb5.153408.15670@umn-cs.cs.umn.edu> Date: 5 Feb 90 15:34:08 GMT Sender: kemp@umn-cs.cs.umn.edu (Stuart R. Kemp) Organization: University of Minnesota, Minneapolis - CSCI Dept. Lines: 277 I am posting this on behalf of Evan Koenig. Please direct all replies to him. From koenig@occlusal.rutgers.edu Sat Feb 3 13:14:39 1990 Hello to everyone and thanks for your responses. Since so many people responded to question about the 386, I'm writing this rather generically. In sum here's what has happened since I've posted my original question. Addressing 4gigs in real mode works. I've been using it for over a week now in my C programs. I load multiple images into expanded(extended?) memory and do some edge detection work in the expanded memory. I am therefore absolutely sure that my addressing scheme is good. The problem as I stated was that I couldn't access the 1 to 2 meg range. After some further investigation, I found I couldn't get to the 3 to 4 range. The problem? Address line A20 is gated off by the keyboard controller as so many of you have told me. R. Kirchner@informatik.uni-kl.de says that you have to write d1h to port 64h 00h to port 60h He says that there was a program in a german magazine in regards to this. Can anyone send it to me? I can understand most of the german. Any Way, here is the assembly code needed to access 4 gigs. Clip the assembly portion and save to a file called 4gig.asm. Also included is a small c program written for Turbo C 2.0 that will test the 32 bit addressing. Save that file to peek32.c If anyone gets the A20 addressing line problem solved post it to comp.sys.ibm.pc and send me some mail. Good Luck to all and enjoy!! Evan Koenig koenig@occlusal.rutgers.edu -------------------------Cut here 4gig.asm--------------------------------- ; This program will go into protected mode, return but ; leave fs,gs pointing to a 32 bit descriptor. ; This will result in a 4 gigabyte real mode !!!! ; Just play back what's in memory ; 4 GIG .ASM ;********************************************************* ;Program by Neal Margulis -- Use Masm 5.0, OR TASM V1.0 ; This program was taken the article ; 80386 Protected Mode Initialization ; Dr. Dobb's Journal, October 1988 ;Note: Basically I deleted all the code that dumps some ; test patterns to the screen in protected mode and ; real mode. After returning from protected mode ; CS,DS,ES point to a real mode descriptor (64k segments) ; But, GS,FS are left pointing to the 4gig segment. ; ; #### DONT EVER PLAY WITH GS OR FS, LEAVE THEM ALONE #### ; #### IF YOU MESS WITH THEM, YOU WILL LOSE ACCESS TO #### ; #### THE 4 GIG RANGE. IF YOU WANT TO LEARN MORE #### ; #### ABOUT THE DESCRIPTORS, I SUGGEST YOU PICK UP A #### ; #### FEW BOOKS ON THE 80386!!! NO ONE PARTICULAR #### ; #### BOOK IS GOOD BY ITSELF. I SUGGEST YOU TRY TO #### ; #### FIGURE AS MUCH AS YOU CAN FROM THIS CODE AND #### ; #### THEN BUY A BOOK. #### ; ; THIS PROGRAM SHOULD BE RUN FIRST. I SUGGEST YOU PUT ; IT IN THE AUTOEXECFILE. AFTER THIS PROGRAM RUNS, YOUR ; ASSEMBLY OR C PROGRAM CAN ACCESS ALL 4GIGS ; ; -EVAN KOENIG koenig@occlusal.rutgers.edu ; ;********************************************************* .386p descriptor STRUC limt_0_15 dw 0 base_0_15 dw 0 base_16_23 db 0 access db 0 gran db 0 base_24_31 db 0 descriptor ENDS code_seg_access equ 09ah data_seg_access equ 092h CSEG segment word use16 'code' assume cs:CSEG,ds:CSEG mov ax,CSEG mov ds,ax ; PUT Code Segment in DS mov ax,seg PMODE ; Move PMode segment in ax and eax,0FFFFh ; eax 0000 PMODE Let eax = a040 shl eax,4h ; eax a040 0000 mov ebx,eax ; ebx a040 0000 shr eax,16 ; mov gdt_PM_1.base_0_15,bx mov gdt_PM_2.base_0_15,bx mov gdt_PM_1.base_16_23,al mov gdt_PM_2.base_16_23,al mov ax,seg C3 and eax,0ffffh shl eax,04h mov ebx,eax shr eax,16 mov gdt_c3_5.base_0_15,bx mov gdt_c3_5.base_16_23,al mov ax,cs and eax,0ffffh shl eax,4h add eax,offset gdttbl mov dword ptr gdtaddr+2,eax ; NOW LOAD THE DESCRIPTOR TABLE lgdt gdtaddr A20_ON: cld cli ; Enter Protected Mode mov eax,cr0 or eax,1 mov cr0,eax DB 0eah,0h,0h,08h,0h ; jmp to PMODE use descriptor 1 gdtaddr label qword dw 48 dd ? dw 0 ; global descriptor table gdttbl label dword gdt_null descriptor <,,,,,> ; descrip 0 gdt_PM_1 descriptor <0ffffh,,,code_seg_access,0c0h,0> ; descrip 1 gdt_PM_2 descriptor <0ffffh,,,data_seg_access,08fh,0> ; descrip 2 gtd_3 descriptor <0ffffh,0,0,data_seg_access,08fh,0> ; descrip 3 gdt_rm_4 descriptor <0ffffh,0,0,data_seg_access,08fh,0> ; descrip 4 gdt_c3_5 descriptor <0ffffh,,,code_seg_access,080h,0> ; descrip 5 CSEG ends ;////////////////////////////////////////////////////////////////////////// ; HERE IS OUR PROTECTED MODE PROGRAM ;///////////////////////////////////////////////////////////////////////// PMODE segment para public use32 'code' assume cs:PMODE mov ax,18h ; SELECTOR 3 (18h/8h = 3) IS A 4 GIG DATA SEGMENT mov es,ax ; WITH BASE AT 0 MOV fs,ax ; Let ES and FS point to 4 GiG data segment mov gs,ax mov ax,10h ; Set DS to selector 1, but we don't care mov ds,ax ; ; It isn't my code ; JUMP BACK TO REAL MODE ; LEAVE GS POINTING TO A 32 BIT DESCRIPTOR ; ; MAKE A SHORT JUMP. CLEARS OUT PREFETCH QUEUE. JUMP BACK TO REAL MODE db 0eah ,0h,0h,0h,0h,28h,0h; align 16 pdat db 0ach lastpm label dword PMODE ends c3 segment para public use16 'code' assume cs:c3 mov ax,20h ; Selector #4 real mode mov es,ax ; Set all segment registers back to the real mov ds,ax ; mode descriptor ; Notice!!! Leave Gs and FS pointing to the 4 gig ; address space. NEVER NEVER NEVER CHANGE IN REAL ; MODE, ELSE 4 GIGS GO BYE BYE mov eax,cr0 ; Clear protection mode bit and eax,07ffffffeh mov cr0,eax jmp far ptr flushr1 flushr1: ; WELCOME BACK TO REAL MODE ; YOU CAN CALL DOS TO PRINT OUT A MESSAGE HERE IF YOU WANT ; DON'T DO IT IN PROTECTED MODE. THE IDT TABLES AREN'T SET UP! A20_off: mov ah,04ch mov al,01h int 21h c3 ends .8086 end ---------------------------Cut here peek32.c-------------------------------- /* 32 Bit peek and poke */ /* by Evan Koenig */ /* Assumptions: gs and fs point to a 32 bit descriptor */ /* */ /* This code was written for Turbo C V2.0. This program*/ /* should be compiled with TCC and TASM. TCC will */ /* automatically invoke TASM. I guess for other */ /* compilers it might be similar. */ #pragma inline #include main() { unsigned int segment,offset,ret,ret2; unsigned long address; unsigned long ret32,real32; printf("Enter a 32 bit address to at. Enter it in hex\n"); scanf ("%lx",&address); asm .386; asm push esi; asm mov esi,dword ptr address; asm mov edx,gs:[esi]; asm mov dword ptr ret32,edx; asm pop esi; asm .8086; printf("32 bit peek returned %lx\n",ret32); }