Jump to content

Program Hangs When Enabling A20

- - - - -

  • Please log in to reply
No replies to this topic

#1
dargueta

dargueta

    Writes binary right handed and hex left handed

  • Moderators
  • 4,720 posts
  • Programming Language:C, Java, C++, PHP, Python, Perl, Assembly, Bash, Others
  • Learning:JavaScript
I'm writing a loader for an operating system class I'll be taking (figured I'd get ahead while I can), so I decided to test the A20 enabler. For some reason, it hangs before it can read the status of port 60h. Any ideas?

A few notes about my code:
1) This is just a tester, so it's not that efficient.
2) I'm using DEBUG.EXE to compile this, hence the hard-coded addresses.
3) Because I'm hard-coding addresses, you'll see a lot of NOP padding so that if I change the program later it won't be such a pain to go through the entire program and changing all the addresses manually.
4) This program sets A20 and then checks to see how much memory is present in the system. I know Windows will block it at some point, but at least it will work in a sense.


jmp	01f0

;

;DATA

;0103 - MEMSTATUS (0:continue, 1:stop)

db	0

;0104 - EnableAddrLine

db	"Enabling A20 Line...$"

;0119 - OK

db	"OK",0d,0a,"$"

;011E - Error

db	"ERROR!$"

;0125 - Memory

db	"Total Memory:$"

;0133 - KB

db	"KB$"

;0136 - Press any key

db	0d,0a,"Press any key...$"

nop

;014A - Text buffer, 16 chars

db	"$$$$$$$$$$$$$$$$"

;015A - Waiting for command ready

db	0d,0a,"Waiting for controller ready signal...$"

;0183 - Waiting for data

db	0d,0a,"Waiting for controller to return data...$"

;01AE - RESERVED FOR EXPANSION

db	"#RESERVED#"

;

;END OF DATA - 01B7

;

;--------------------------------------------------

;VOID INTTOASCII(DWORD) @ 01B8

;dumps decimal representation of DWORD to buffer

;--------------------------------------------------

;EAX = number to convert

db	66

pop	ax

;EDX = 0, carries the modulus

db	66

xor	dx,dx

;set [BX] to point to end of buffer

mov	bx,0158

;set ECX = 0ah, force DIV into 32-bit mode

db	66

mov	cx,000a

dw	0000

;01C6 - div loop

db	66

div	cx

;edx contains remainder, we're interested in DL

;convert num to char, works only in bases <= 10

add	dl,30

;store char in buffer

mov	[bx],dl

;point to previous char in buffer

dec	bx

;is EAX = 0?

db	66

or	ax,ax

jnz	01c6

;we're done, EAX = 0.

;01D4 - fill rest of buffer with spaces.

cmp	bx,014a

jz	01df

mov	byte ptr [bx],20

jmp	01d4

;01DC - return

ret

;

;

;--------------------------------------------------

;VOID GPFAULTHANDLE(VOID) @ 01E0

;--------------------------------------------------

mov	byte ptr [0103],1

iret

nop

nop

nop

nop

nop

nop

nop

nop

nop

nop

;

;

;---------------------------------------------------

;VOID MAIN(VOID) @ 01F0

;---------------------------------------------------

;print loading string

mov	ah,09

mov	dx,0104

int	21h

;;;;;;print wait for ready message

mov	ah,09

mov	dx,015a

int	21h

nop

;disable interrupts

cli

;0200 - wait for controller to be ready for input

xor	ax,ax

in	al,64

and	ax,2

jz	0200

;controller is ready. send read status command

mov	al,0d

out	64,al

;;;;;;print wait for data message

sti

mov	ah,09

mov	dx,0183

int	21h

cli

nop

nop

;0218 - wait for controller output

xor	ax,ax

in	al,64

and	ax,1

jz	0218

;controller is ready. read status

xor	ax,ax

in	al,60

;save status on stack

push	ax

;;;;;;print wait for ready message

sti

mov	ah,09

mov	dx,015a

int	21h

cli

nop

;0230 - wait for controller to be ready for input

xor	ax,ax

in	al,64

and	ax,2

jz	0230

;controller is ready. send write status command

mov	al,d1

out	64,al

;;;;;;print wait for data message

sti

mov	ah,09

mov	dx,0183

int	21h

cli

nop

nop

;0248 - wait for controller output

xor	ax,ax

in	al,64

and	ax,1

jz	0248

;controller is ready, set A20 enable bit and write

pop	ax

or	al,2

out	60,al

;check to see if it was set - read back status.

;;;;;;print wait for ready message

sti

mov	ah,09

mov	dx,015a

int	21h

cli

;0260 - wait for controller to be ready for input

xor	ax,ax

in	al,64

and	ax,2

jz	0260

;controller is ready. send read status command.

mov	al,0d

out	64,al

;;;;;;print wait for data message

sti

mov	ah,09

mov	dx,0183

int	21h

cli

nop

nop

;0278 - wait for controller output

xor	ax,ax

in	al,64

and	ax,1

jz	0278

;controller is ready. read status.

xor	ax,ax

in	al,60

;check to see if A20 is enabled

and	al,2

jnz	02a0

;

;0289

;error occurred. print and quit.

;print error message.

sti

mov	ah,09

mov	dx,011e

int	21h

;print press any key message

mov	dx,0136

int	21h

;pause

mov	ah,00

int	16h

;exit

mov	ax,4cff

int	21h

nop

;

;02A0

;no error occurred.

;print OK message.

sti

mov	ah,09

mov	dx,0119

int	21h

;do memcheck.

;hook general protection fault interrupt 0dh

;get original interrupt vector

;returned in ES:BX

mov	ax,350d

int	21h

;save to stack

push	bx

push	es

;reset vector to handler at DS:01E0

mov	ax,250d

mov	dx,01e0

int	21h

;begin memcheck

db	66

xor	bx,bx

nop

nop

nop

nop

nop

nop

;02C0 - memcheck loop

cmp	byte ptr [0103],1

jz	02ce

db	67

mov	dl,[bx]

db	66

inc	bx

jmp	02c0

;02CE - end memcheck loop

;divide by 1024 to get KB

mov	cl,0a

db	66

shr	bx,cl

;get decimal string of memory size

db	66

push	bx

call	01b8

;print memory size string

mov	ah,09

mov	dx,0125

int	21h

;print decimal number representing memory size

mov	dx,014a

int	21h

;print KB string

mov	dx,0133

int	21h

;pause

mov	ah,00

int	16h

;reset old interrupt vector

pop	dx

pop	ds

mov	ax,250d

int	21h

;exit

mov	ax,4c00

int	21h

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

;end of program at 02F9

nop

nop

nop

nop

nop

nop

nop

nop

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;

;padded so it's exactly 0x200

;bytes long.






1 user(s) are reading this topic

0 members, 1 guests, 0 anonymous users