x86 Assembly

Moderators: None (Apply to moderate this forum)
Number of threads: 4563
Number of posts: 16029

This Forum Only
Post New Thread
Single Post View       Linear View       Threaded View      f

Report
Hardware Spec From BIOS OR RAM Posted by steward on 16 Apr 2008 at 9:41 AM
Hello

I am beginner and would like to develope a kernel that shows hardware spec
i know there is an interrupt like int 11 .but i want to show the detail specification like model,vendor ,.... for some devices such as cpu,ram,hard.... and i know there is an address in ram that holds this specification but I dont know that address and dont know how to access this segment,Please
Report
Re: Hardware Spec From BIOS OR RAM Posted by Bret on 16 Apr 2008 at 4:31 PM
: Hello
:
: I am beginner and would like to develope a kernel that shows
: hardware spec
: i know there is an interrupt like int 11 .but i want to show the
: detail specification like model,vendor ,.... for some devices such
: as cpu,ram,hard.... and i know there is an address in ram that holds
: this specification but I dont know that address and dont know how
: to access this segment,Please

Are you referring to the SMBIOS? If so, you can download the specs from Here.
Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 16 Apr 2008 at 10:32 PM
: : Hello
: :
: : I am beginner and would like to develope a kernel that shows
: : hardware spec
: : i know there is an interrupt like int 11 .but i want to show the
: : detail specification like model,vendor ,.... for some devices such
: : as cpu,ram,hard.... and i know there is an address in ram that holds
: : this specification but I dont know that address and dont know how
: : to access this segment,Please
:
: Are you referring to the SMBIOS? If so, you can download the specs
: from Here.

Thanks sir.But How should i use that standard?I said i am beginner.Guid in detail please.
Report
Re: Hardware Spec From BIOS OR RAM Posted by jeffleyda on 17 Apr 2008 at 12:13 PM
This is a really good way to learn hardware and programming-one of the very first programs I wrote in asm was one that detected various bits of hardware and displayed them to the screen. I used int 11 and several others, and then figured out how to talk to hardware directly for more exploring. (this was way before smbios came into being)

SMBIOS is a good resource of information. The method used to get to it is very similar to accessing ACPI information, and I have a program here:

http://www.programmersheaven.com/download/25319/download.aspx
(It only works under plain DOS.)

I think with just a little bit of tweaking, this program could dump out the SMBIOS data instead of ACPI, but you'll need to read the spec to really understand what you're doing.

The downside of SMBIOS is that it's boring. It's basically just a bunch of text sitting in memory that you parse out and display. You won't learn much with that, so I always suggest going directly to the hardware if you want to learn how to really detect things and know how to interface into all the chips on your board, and we can help.

You'll need to go slowly at first and then ask specifics like "how do I talk to PCI devices?", so we can narrow down the scope of our responses.

-jeff!
Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 17 Apr 2008 at 11:50 PM
ok.I will go to Read what u say.but u should help me if i have question.

If anyone else can help more please post his/her reply.

thx alot
Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 21 Apr 2008 at 4:00 AM
I have the same question.I know that there is an address in ram that holds the hardware spec.is there anyway to access that data and show it which can be readable?
Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 21 Apr 2008 at 6:04 AM
: This is a really good way to learn hardware and programming-one of
: the very first programs I wrote in asm was one that detected various
: bits of hardware and displayed them to the screen. I used int 11
: and several others, and then figured out how to talk to hardware
: directly for more exploring. (this was way before smbios came into
: being)
:
: SMBIOS is a good resource of information. The method used to get to
: it is very similar to accessing ACPI information, and I have a
: program here:
:
: http://www.programmersheaven.com/download/25319/download.aspx
: (It only works under plain DOS.)
:
: I think with just a little bit of tweaking, this program could dump
: out the SMBIOS data instead of ACPI, but you'll need to read the
: spec to really understand what you're doing.
:
: The downside of SMBIOS is that it's boring. It's basically just a
: bunch of text sitting in memory that you parse out and display. You
: won't learn much with that, so I always suggest going directly to
: the hardware if you want to learn how to really detect things and
: know how to interface into all the chips on your board, and we can
: help.
:
: You'll need to go slowly at first and then ask specifics like "how
: do I talk to PCI devices?", so we can narrow down the scope of our
: responses.
:
: -jeff!

How should i use smbios.I read its PDF but there was nothing to help me.
Guid please
Report
Re: Hardware Spec From BIOS OR RAM Posted by jeffleyda on 21 Apr 2008 at 7:17 AM
: How should i use smbios.I read its PDF but there was nothing to help
: me.
: Guid please

Not true.
*Everything* you need is in the PDF, you just didn't understand it.

You are probably trying to do something too complicated, especially since you are new to x86 programming. This is not easy stuff to do, especially in assembly.

Chapter 2 in the spec tells you how to access the SMBIOS information:

"On non-EFI systems, the SMBIOS Entry Point structure, described below, can be located by application software by searching for the anchor-string on paragraph (16-byte) boundaries within the physical memory address range
000F0000h to 000FFFFFh."

That means you must write a routine to search memory looking for a key signature. That key is "_SM_"

The code that I pointed you to does something similar with ACPI-it searches for a key named "RSD PTR" in the routine rsdptrSearch. If you change that key in my code to "_SM_" you will now have step 1 completed!

The address you find _SM_ + 18h is the offset of a 32bit pointer to where all the SMBIOS data lives in memory. There is other information in this table that you will also want to know (SMBIOS version at _SM_+6, # of tables at _SM_+1ch)

From DOS (or other real mode environment) in order to access the data at that high location in memory, you will need to put the CPU into protected mode. I put it into flat real mode in my example code. (routine is called himeminit)

From there it's a matter of reading the data out of memory and displaying it the way you want. The structure of each table is defined in section 3.

My ACPI code does the same type of work. If you download the ACPI specification you will find it is very similar in the way tables are organized in memory, and that may help you understand my code a little better too.
Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 22 Apr 2008 at 3:29 AM
: : How should i use smbios.I read its PDF but there was nothing to help
: : me.
: : Guid please
:
: Not true.
: *Everything* you need is in the PDF, you just didn't understand it.
:
: You are probably trying to do something too complicated, especially
: since you are new to x86 programming. This is not easy stuff to do,
: especially in assembly.
:
: Chapter 2 in the spec tells you how to access the SMBIOS information:
:
: "On non-EFI systems, the SMBIOS Entry Point structure, described
: below, can be located by application software by searching for the
: anchor-string on paragraph (16-byte) boundaries within the physical
: memory address range
: 000F0000h to 000FFFFFh."
:
: That means you must write a routine to search memory looking for a
: key signature. That key is "_SM_"
:
: The code that I pointed you to does something similar with ACPI-it
: searches for a key named "RSD PTR" in the routine rsdptrSearch. If
: you change that key in my code to "_SM_" you will now have step 1
: completed!
:
: The address you find _SM_ + 18h is the offset of a 32bit pointer to
: where all the SMBIOS data lives in memory. There is other
: information in this table that you will also want to know (SMBIOS
: version at _SM_+6, # of tables at _SM_+1ch)
:
: From DOS (or other real mode environment) in order to access the
: data at that high location in memory, you will need to put the CPU
: into protected mode. I put it into flat real mode in my example
: code. (routine is called himeminit)
:
: From there it's a matter of reading the data out of memory and
: displaying it the way you want. The structure of each table is
: defined in section 3.
:
: My ACPI code does the same type of work. If you download the ACPI
: specification you will find it is very similar in the way tables are
: organized in memory, and that may help you understand my code a
: little better too.

Thanks alot
Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 26 Apr 2008 at 1:11 PM
Hi.

I found DMIDecode.c Source code but it is Written in C.
Know i want to Make a disk that in sector 0 is bootloader and in sector 1 is dmidecode.what should i do?guide please
Report
Re: Hardware Spec From BIOS OR RAM Posted by jeffleyda on 28 Apr 2008 at 11:34 AM
: Hi.
:
: I found DMIDecode.c Source code but it is Written in C.
: Know i want to Make a disk that in sector 0 is bootloader and in
: sector 1 is dmidecode.what should i do?guide please
:

Could you possibly make this any more difficult for yourself?
Reading DMI and creating bootsector loaders are *not* beginner tasks. I'll be very impressed if you get this to work without giving up after becoming too frustrated.

I'd make the dmicode.c into a DOS .COM program first. It's MUCH easier to debug and test your code by executing it in DOS than putting it onto a bootsector and rebooting the computer to test every change.

Your program will not be able to use any DOS functions (ie, no INT 21h to print a text string) because from a bootsector, you only have BIOS functions available to you.

Once you have a clean .COM program that works the way you want, it is just a matter of copying it to sector 1 (you'll likely need more than just 512 bytes). You shouldn't need to change any code between DOS .COM and a bootsector. There are lots of examples out there of bootsector code, so that should be easy to find.

-jeff!

Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 28 Apr 2008 at 2:33 PM
: : Hi.
: :
: : I found DMIDecode.c Source code but it is Written in C.
: : Know i want to Make a disk that in sector 0 is bootloader and in
: : sector 1 is dmidecode.what should i do?guide please
: :
:
: Could you possibly make this any more difficult for yourself?
: Reading DMI and creating bootsector loaders are *not* beginner
: tasks. I'll be very impressed if you get this to work without giving
: up after becoming too frustrated.
:
: I'd make the dmicode.c into a DOS .COM program first. It's MUCH
: easier to debug and test your code by executing it in DOS than
: putting it onto a bootsector and rebooting the computer to test
: every change.
:
: Your program will not be able to use any DOS functions (ie, no INT
: 21h to print a text string) because from a bootsector, you only have
: BIOS functions available to you.
:
: Once you have a clean .COM program that works the way you want, it
: is just a matter of copying it to sector 1 (you'll likely need more
: than just 512 bytes). You shouldn't need to change any code between
: DOS .COM and a bootsector. There are lots of examples out there of
: bootsector code, so that should be easy to find.
:
: -jeff!
:
:
and now how can u help me?what should i do?can i use lilo bootloader and demidecode mudule?u know dmidecode is linux module
Report
Re: Hardware Spec From BIOS OR RAM Posted by jeffleyda on 29 Apr 2008 at 7:57 AM
: and now how can u help me?what should i do?can i use lilo bootloader
: and demidecode mudule?u know dmidecode is linux module

You probably could use lilo and this dmicode-I don't know linux well, and you're no longer really working in x86 assembly at that point, so I am unable to help you any further.

What I'd do is write some code in DOS. Start with INT 12h like you first stated, get that information printing to the screen. There are lots of other bits of information you can get from the BIOS Data Area and other interrupts.

That will get you familiar with assembly language.

Then move into converting a small DOS program into a bootloader, which is not that difficult of a step. Meanwhile, tackling DMI and other hardware detection, once you've got some of the basics down, isn't a huge task, but there are many more steps involved than just "int 12" to get the data.

assembly is slow. if your goal is to learn assembly, you need to do lots of "hello world!" programs to get the hang of it first. If you want to learn how to detect hardware and display it all to the screen, perhaps assembly is too much work to make nice displays.

I found one of my first assembly programs that detects hardware and prints it to the screen. 1993! I can't believe I'm posting this...

I used MASM to compile this to a DOS .COM file.


;info
;displays a few system stats.   I want to be able to figure out processor speeds!

	cseg segment
	assume cs: cseg,ds:cseg,es:cseg,ss:cseg

	org 100h
      
main:   jmp go
;----------------------------------------------------------------------------
;define zee variables here
;----------------------------------------------------------------------------
open1     db     0ah,0dh,"Detected configuration: ",0ah,0dh,"-----------------------",0ah,0dh,"$"
hd        db     "Number of hard drives: $"
biosmade  db     "BIOS manufacturer: $"
award     db     "Award$"
phoenix   db     "Phoenix Technologies Ltd.$"
mylex     db     "Mylex$"
flop      db     "Floppy drives: $"
totals    db     "Total drive space for $"
meg       db     "Mb $"
dosver    db     "DOS Version: $"
spam      db     "SPAM: Yes please",0dh,0ah,"$"
numpar    db     "Number of parallel ports: $"
numser    db     "Number of serial ports: $"
mouse     db     "Mouse driver: $"
basemem   db     "Base memory: $"
extended  db     "Extended memory: $"
biosdate  db     "  BIOS date: $"
cpu       db     "CPU type: 80$"
spa1      db     " COM1 address:                        LPT1 address: ",0dh,0ah,"$"
spa2      db     " COM2 address:                        LPT2 address: ",0dh,0ah,"$"
spa3      db     " COM3 address:                        LPT3 address: ",0dh,0ah,"$"
spa4      db     " COM4 address:                        LPT4 address: ",0dh,0ah,"$"
mathco    db     "Math coprocessor: $"
video     db     "Video type: $"
cpu8088   db     "88 or 8086",0dh,0ah,"$"
cpu186    db     "186",0dh,0ah,"$"
cpu286    db     "286",0dh,0ah,"$"
cpu386    db     "386",0dh,0ah,"$"
cpu486    db     "486",0dh,0ah,"$"
none      db     " None     $"
f360      db     " 360kb 5¬",22h,"$"
f120      db     " 1.2Mb 5¬",22h,"$"
f720      db     " 720kb 3«",22h,"$"
f144      db     " 1.44M 3«",22h,"$"
f288      db     " 2.88M 3«",22h,"$"
installed db     "installed",0dh,0ah,"$"
nott      db     "not $"
vga       db     "VGA",0dh,0ah,"$"
mono      db     "Monochrome",0dh,0ah,"$"
crlf      db     0ah,0dh,"$"

;----------------------------------------------------------------------------
;            These are various procedures to tell us what's up
;============================================================================
;check to see if there is a mouse installed
;----------------------------------------------------------------------------
is_mouse_installed proc
	push ax
	push dx
	xor ax,ax                ; clean out the AX register
	int 33h                  ; call interrupt 33h function 0
	cmp ax,0ffffh            ; compare AX and FFFFh (installed)
	jz endmouse              ; it is? Jump to the end!
	lea dx,nott              ; Not installed?  Display the word "not"
	mov ah,9                 ; display string function
	int 21h                  ; interrupt 21h
endmouse:
	pop dx
	pop ax
	ret                      ; end o' procedure
is_mouse_installed endp

;============================================================================
;look for a math coprocessor!
;----------------------------------------------------------------------------
is_there_a_mathco_here proc

	push ax
	push dx
	int 11h                  ; call interrupt 11h  (Equipment check)
	and ax,2                 ; single out bit 1  Coprocessor bit
	cmp ax,2                 ; 2=installed  0=none
	jz endmathco             ; if installed, jump to end
	lea dx,nott              ; else display a NOT!
	mov ah,9                 ; display string function of
	int 21h                  ; interrupt 21h
endmathco:
	pop dx
	pop ax
	ret                      ; end o' procedure!
is_there_a_mathco_here endp
;----------------------------------------------------------------------------
;find what BIOS mfgr
;============================================================================
who_made_the_bios proc
	push dx
	push ax
	push ds                  ; save them registerz
	mov ax,0fe00h            ; looking at FE00:0030 for signatures
	mov ds,ax
	mov ax,ds:[0030h]
	pop ds
	cmp ax,7741h             ; look for AW  (as in AWARD)
	jz awardb
	cmp ax,3538h             ; look for 85  (copyright notice for phoenix boys)
	jz phoenixb
	lea dx,mylex             ; hell, it must be mylex then (bad idea to assume)
	jmp display_bios
awardb:
	lea dx,award             ; load award
	jmp display_bios
phoenixb:
	lea dx,phoenix           ; load phoenix
display_bios:        
	mov ah,9                 ; function 9 of int 21 
	int 21h                  ; display string
	pop ax                   ; restore reggies
	pop dx
	ret
who_made_the_bios endp







;----------------------------------------------------------------------------
;hrey, so is this a vga or monochrome system?  like you can't tell
;============================================================================

find_video_card proc
	push ax                  ; save some registerz
	push dx                  ; 
	mov ah,0fh               ; function F of int 10 is get video params
	int 10h
	cmp al,3                 ; 3=vga 7=mono
	jz itsvga
	lea dx,mono              ; load up MONO!
	jmp endvideo

itsvga:
	lea dx,vga               ; load up VGA!

endvideo:        
	mov ah,9                 ; print it out d00d.
	int 21h
	pop dx                   ; restore some registerz!!!!!!!!
	pop ax
	ret                      ; end o' procedure!
find_video_card endp

;============================================================================
;find the number of parallel and serial ports in this puppy
;----------------------------------------------------------------------------

get_number_of_ports proc

	push cx                  ; save a few regsiters
	push dx
	int 11h                  ; call interrupt 11h  equipment check
	mov bx,ax                ; copy the ax register to bx
	and ax,0e00h             ; single out bits 9-11
	and bx,0c000h            ; single out bits 14-15
	mov cl,9                 ; shift this thing 9 times
	shr ax,cl                  
	add al,30h               ; add a 30 to it to make it a decimal
	mov cl,14                ; shift this puppy 14 times
	shr bx,cl
	add bl,30h               ; add a 30 to this to make it decimal
	pop dx
	pop cx                   ; and then restore them
	ret                      ; end o' procedure!

get_number_of_ports endp


;----------------------------------------------------------------------------
;Hey, how many hard drives we got in this thing?
;============================================================================
number_of_hard_drives proc        

	push ax                  ; save the ole AX register
	push ds                  ; save the DS register
	mov bx,0040h             ; we're gunna look at 0040:0075 for a number
	mov ds,bx                ;
	mov dl,ds:[0075h]        ; pull that number into DL register
	add dl,30h               ; add a 30 to it to make it decimalish
	mov ah,2                 ; print char function for
	int 21h                  ; interrupt 21h  (prints whats in DL get it?)
	pop ds                   ; restore that wacky DS register
	pop ax                   ; and the AX register too
	ret                      ; end o' procedure

number_of_hard_drives endp        

;----------------------------------------------------------------------------
;what is the date the bios was made?
;============================================================================
display_bios_date proc

	push ax                  ; save that Ax register
	push bx                  ; and all the rest of them too
	push cx
	push dx
	push ds                  ; ditto DS
	MOV BX,0F000h            ; BIOS date is at F000:FFF5                
	MOV DS,BX                ; get that data segment to F000              
	MOV BX,0FFF5h            ; whoa!  caps!                
	MOV AH,02                ; function #2, print char in DL             
	MOV CX,0008              ; Gunna print 8 characters              
rollit:        
	MOV DL,ds:[BX]           ; move char into DL to print it                 
	INT 21h                  ; print char               
	INC BX                   ; increment BX by 1              
	loop rollit              ; whip back through 7 more times
	pop ds                   ; restore that DS
	pop dx
	pop cx
	pop bx
	pop ax                   ; restore that AX
	ret                      ; end o' procedure!

display_bios_date endp
;----------------------------------------------------------------------------
;get the cpu type
;============================================================================
whatcpu proc

	pushf                    ;ok,ok, I have NO CLUE as to how this
	pop ax                   ;whole routine works.  it does, so just
	and ah,0fh               ;deal with it.
	push ax
	popf
	pushf
	pop ax
	and ah,0f0h
	cmp ah,0f0h
	jnz step1
	mov ax,2
	mov cl,21h
	shr ax,cl
	test ax,1
	jz  itsa8088

	lea dx,cpu186
	mov ah,9
	int 21h
	jmp endcpu

itsa8088:
	
	lea dx,cpu8088
	mov ah,9
	int 21h
	jmp endcpu

step1:
	pushf
	pop ax
	or ah,0f0h
	push ax
	popf
	pushf
	pop ax
	and ah,0f0h
	jnz step3
	lea dx,cpu286
	mov ah,9
	int 21h
	jmp endcpu

step3:  
	db   90h,  66h, 8bh, 0cch, 66h, 83h   ;32 bit instructions!
	db  0e4h, 0fch, 66h,  9ch, 66h, 58h   ;I'm sooo cool to be able
	db   66h,  8bh, 0d8h, 66h, 35h, 0     ;to do this.
	db    0,    4,    0,  66h, 50h, 66h
	db   9dh,  66h,  9ch, 66h, 58h, 66h
	db   33h, 0c3h

	jnz itsa486
	nop
	nop

	lea dx,cpu386
	mov ah,9
	int 21h
	jmp endcpu

itsa486:
	lea dx,cpu486
	mov ah,9
	int 21h

endcpu:

	ret                      ; end o' procedure!

whatcpu endp
;----------------------------------------------------------------------------
;Display total space
;============================================================================
free_total proc
	push ax                  ; save the AX register
	push bx                  ; and the BX register
	push cx                  ; and the CX register too damnit!
	mov ah,36h               ; function 36h of int21=get free space
	int 21h
	cmp ax,0ffffh
	jz so_long
	push dx                  ; save our DX again (total clusters on disk)
	mul cx                   ; multiply AX*CX (Sectors/clust*bytes/clust)
	mov cx,ax                ; throw the result into CX for storage
	pop ax                   ; restore the DX register from above
	mov bx,3e8h              ; prepare to divide that by 1000
	div bx                   ; do that divide (could be done by 1024 )
	
	cmp dx,500               ; is the remainder bigger than 500?
	jl no_round              ; no, skip it
	inc AX                   ; why, yes it is.  Increase the AX register

no_round:
	
	xor dx,dx                ; clean out the DX register
	mul cx                   ; multiply AX*CX again
	div bx                   ; divide by another 1000 
so_long:        
	mov dx,ax                ; drop the final result into DX
	pop cx                   ; restore that CX
	pop bx                   ; and that BX
	pop ax                   ; and that AX!
	ret                      ; end o' procedure
free_total endp

;----------------------------------------------------------------------------
;get the DOS version
;============================================================================
dos_version proc        
	
	push ax                  ; save the ax register
	push dx
	mov ah,30h               ; function 30 of int 21  
	int 21h                  ; = get dos version  Ah=minor al=major
	mov bx,ax                ; save a copy of AX to BX
	add al,30h               ; add 30 to al to make it decimal
	mov dl,al                ; drop it into DL to print it.
	mov ah,2                 ; function 2
	int 21h                  ; interrupt 21
	mov dl,2eh               ; mov a . into DL
	int 21h                  ; print it
	add bh,30h               ; add BH and 30 to make minor rev a decimal
	mov dl,bh                ; mov BH into DL 
	int 21h                  ; print the minor rev
	pop dx
	pop ax                   ; restore that AX register
	ret                      ; end o' procedure!

dos_version endp

;----------------------------------------------------------------------------
;get the floppy drive numbers and type
;============================================================================
floppies proc

	push ax                  ;save that AX register again
	push si                  ;save the SI register (used as a flag)
	xor si,si                ;clean out the SI register
	mov dl,0                 ;DL=drive # (0=A:)
getflop:        
	mov ah,8                 ;function 8 of int 13
	int 13h                  ;interrupt 13h
	mov ax,11                ;length of string=11 bytes
	mul bx                   ;multiply by the drive type # (0-5)
	lea dx,none              ;start at "None"
	add dx,ax                ;add it to our drive number type counter
	mov ah,9                 ;function 9 of int 21h
	int 21h                  ;is print string.
	cmp si,2                 ;flag set?  
	jz enditnow              ;yes, quit the procedure
	mov si,2                 ;set our flag
	mov dl," "               ;display a space
	mov ah,2
	int 21h
	mov dl,"+"               ;display a plus sign (make it look c00ler)
	int 21h
	mov dl,1                 ;next floppy DL=1=drive B:
	jmp getflop              ;and start over again
enditnow:        
	pop si                   ;restore the SI
	pop ax                   ;restore the AX
	ret
floppies endp

;----------------------------------------------------------------------------
;Hex-->dec    number to convert comes in via DX
;============================================================================

hex2dec proc

	push ax                  ; save that AX
	push bx                  ; save that CX
	push cx                  ; save that DX
	push si                  ; save that SI
	mov ax,dx                ; copy number into AX
	mov si,10                ; SI will be our divisor
	xor cx,cx                ; clean up the CX

non_zero:

	xor dx,dx                ; clean up the DX
	div si                   ; divide by 10
	push dx                  ; push number onto the stack
	inc cx                   ; increment CX to do it more times
	or ax,ax                 ; end of the number?
	jne non_zero             ; no? Keep chuggin' away

write_digits:

	pop dx                   ; get the digit off DX
	add dl,30h               ; add 30 to it to make it decimalish
	call print_char          ; print that puppy out
	loop write_digits        ; keep going!


	pop si                   ; restore that SI
	pop cx                   ; restore that DX
	pop bx                   ; restore that CX
	pop ax                   ; restore that AX
	ret                      ; End o' procedure!

hex2dec endp
;----------------------------------------------------------------------------
;print_char procedure fer printin' 1 digit!
;============================================================================
print_char proc

	push ax                  ; save that AX register
	mov ah,2                 ; function number 2
	int 21h                  ; of interrupt 21
	pop ax                   ; restore that AX register
	ret                      ; end o' procedure!

print_char endp




;find the memory size
;============================================================================

base_mem_size proc
	push ax
	push dx
	int 12h                  ; call interrupt 12 to get base mem size
	mov dx,ax                ; 
	call hex2dec             ; display that number in decimal
	mov dl,6bh               ; print out a 'k'
	mov ah,2
	int 21h
	pop dx
	pop ax
	ret
base_mem_size endp

	
;----------------------------------------------------------------------------        
ext_mem_size proc        
	push ax
	push bx
	push dx
	mov ah,88h               ; function number 88
	int 15h                  ; of interrupt 15 = get extended RAM count
	cmp ax,0                 ; is it 0?  (probably cuz himem.sys)
	mov dx,ax
	jnz disp_mem             ; nope? ok, print that number out then! 

	cli                      ; clear all interrrupts 
	mov dx,0070h             ; port 70h kickin' 30h out to it
	mov ax,0030h             ;
	out dx,al                ;
	mov dx,0071h             ; readin' back in from port 71h
	in al,dx                 ; drop that number into AL
	mov bl,al                ; move that number into BL to save it

	mov dx,0070h             ; back to port 70h
	mov ax,0031h             ; sending out a 31h to get the next byte
	out dx,al                ;
	mov dx,0071h             ; reading back in from port 71h
	in al,dx
	sti                      ; restore all interrupts
	mov dh,al                ; mov the numbers in line into DX
	mov dl,bl
	
disp_mem:
	call hex2dec             ; print out that big ole number
	mov dl,6bh               ; 6bh? yeah! display a k (kilobytes!!)
	mov ah,2                 ; print that char
	int 21h
	pop dx
	pop bx
	pop ax
	ret
       
ext_mem_size endp



;============================================================================
;display all available drive spaces
;----------------------------------------------------------------------------
display_drive_space proc
	
	push ax                   ; save some registerz
	push bx
	push cx
	push dx
	
	
	mov cl,3h                 ; Start with drive C
	
displays:        
	int 1
	mov dl,cl                 ; mov drive number into DL
	call free_total           ; call space getter
	cmp dx,0ffffh             ; DX will be FFFF if invalid
	jz end_it                 ; so end it
	push dx
	mov dl,cl                 ; mov cl register to DL
	add dl,40h                ; add 40 to it to make it a letter
	mov ah,2                  ; function 2
	int 21h                   ; of int 21=dispaly char
	mov dl,":"                ; now display a colon 
	int 21h                   ; 
	pop dx
	call hex2dec              ; otherwise print it
	mov ah,9
	lea dx,meg
	int 21h
	inc cl                    ; and keep going
	jmp displays
end_it:
	pop dx                    ; restore som registerz
	pop cx
	pop bx
	pop ax
	ret                       ; end o' procedure!
display_drive_space endp




;============================================================================
;display serial/parallel port addresses
;----------------------------------------------------------------------------
display_serial proc
	mov ax,0040h             ; we're gunna look at 0040:0000h
	push ds                  ; save that data segment
	mov ds,ax                ; look into a new location
	push di                  ; save that DI register DI will be the count
	push si                  ; save that SI register too
	mov di,0                 ; start at 0
	mov si,0f0fh             ; row,col of our first display section

s_loop:        

	push dx                  ; save dx
	push bx                  ; and bx
	push ax                  ; ax too
	mov ax,0200h             ; function 2
	xor bx,bx                ; page 0 
	mov dx,si                ; SI is the current row/col position
	int 10h                  ; interrupt 10h is set cursor pos
	add si,0100h             ; add another line (row)
	pop ax                   ; restore all those registers
	pop bx
	pop dx
	
	mov ax,ds:[di]           ; move base address of port into AX
	mov cx,ax                ; mov into into CX for safe keeping
	
	cmp cx,0
	jz No_port

	mov dl,ah                ; mov that 1st digit into DL
	add dl,30h               ; add 30h to it to make it decimalish
	mov ah,02                ; print a character
	int 21h
	mov ax,cx                ; mov our copy back into AX
	xor ah,ah                ; clean up the AH register
	mov bx,10h               ; give BL 10h
	mul bx                   ; multiply by 10 to move the numbers up 1
	mov dl,ah                ; mov the next digit into dl
	cmp dl,0ah               ; bigger than 10? must be a letter
	jge add_37               ; if so, go add 37h to it
	add dl,30h               ; else just add 30h to it
	jmp disp_it              ; go display that puppy

add_37:
	add dl,37h               ; duh, yeah add 37h
	
disp_it:        
	mov ah,02                ; display that character too
	int 21h
	mov ax,cx                ; move thast number back into ax
	xor ah,ah                ; clean up the AH
	mul bx                   ; mov the digits up 1
	xor ah,ah                ; clean it off again
	mul bx                   ; mov the digits up again
	mov dl,ah                ; move that baby over to DL
	cmp dl,0ah               ; add either 30 or 37
	jge add_37_again
	add dl,30h
	jmp disp_it_again

add_37_again:

	add dl,37h

disp_it_again:        
	
	mov ah,02                ; display that number
	int 21h
	mov dl,68h               ; print an h (hexadecimal!)
	mov ah,2
	int 21h
	

next_p:  
	inc di                   ; mov the counter up by 2
	inc di

	cmp di,8                 ; are we done with the first 4?
	jnz keepit               ; nope, nevermind
	mov si,0f34h             ; yep, start at the next column



keepit:        
	cmp di,10h               ; are we done with that wacky loop?
	jz end_this              ; god I hope so.
	jmp s_loop


no_port:
				 ; save the DS seggy
	push ds                  ; push the SS in so we can
	push ss                  ; pop it into DS  (tricky eh?)
	pop ds
	mov ah,9                 ; function 
	lea dx,nott
	int 21h
	lea dx,installed
	int 21h
	pop ds
	jmp next_p








end_this:        
	
	pop si
	pop di                   ; restore that Di register
	pop ds                   ; restore that Ds register
	ret
display_serial endp












;============================================================================
;hey wow!  this the beginning of this program!
;============================================================================
;============================================================================
go:
	mov ax,0200h                   ; mov cursor to 0,0
	xor dx,dx
	int 10h
				       ; display a space 4000h times
	mov ah,9h                      ; to clear the screen you ninny
	mov cx,4000
	mov al," "
	mov bx,7
	int 10h
	
	mov ax,0200h                   ; move that cursor back up to 0,0
	xor dx,dx
	int 10h
      
	mov ah,9
	lea dx,open1                   ; display opening message lines
	int 21h                        
	
	lea dx,cpu                     ; display the cpu type line
	int 21h
	call whatcpu                   ; call routine to display it
	

	lea dx,mathco                  ; print mathco message
	int 21h
	call is_there_a_mathco_here
	
	lea dx,installed               ; print installed
	int 21h
		   
	lea dx,hd                      ; display number of hard drives msg
	int 21h                       
	call number_of_hard_drives     ; call routine to display number

	lea dx,crlf                    ; send a CR/LF
	int 21h

	
;        lea dx,totals                  ; print out some totals for drive spce
;        int 21h


;        call display_drive_space

;        lea dx,crlf
;        int 21h





	lea dx,flop                    ; display message about floppies
	int 21h
	call floppies                  ; call routine to display number/type

	lea dx,crlf                    ; send a CR/LF
	int 21h
	       
	lea dx,biosmade
	int 21h
	
	call who_made_the_bios         ; yes, call that procedure
	
	lea dx,biosdate                ; display message about BIOS date
	int 21h
	call display_bios_date         ; call routine to display it
	
	lea dx,crlf                    ; send a CR/LF
	int 21h
	
	
	lea dx,spam                    ; ha!  this is a joke
	int 21h                        ; a funny one too!
	
	lea dx,dosver                  ; display message about DOS version
	int 21h
	call dos_version               ; call routine to display it

	lea dx,crlf                    ; send a CR/LF
	int 21h
	

	lea dx,mouse                   ; display a mouse message
	int 21h
	call is_mouse_installed        ; is it there?
	lea dx,installed               ; display "installed"
	int 21h

	

	lea dx,video                   ; Display video card type
	int 21h
	call find_video_card
	

	lea dx,basemem                 ; do the bass memory thing
	int 21h
	call base_mem_size
	
	lea dx,crlf
	int 21h

	lea dx,extended                ; display memory size
	int 21h                          
	call ext_mem_size              

	lea dx,crlf
	int 21h

	lea dx,numser                  ;display serial ports
	int 21h
	call get_number_of_ports
	mov dl,al
	mov ah,2
	int 21h                        ;print out the actual number of 'em

	mov ax,0200h                   ;locate to 0Dhx25h
	mov dx,0e25h
	xor bx,bx
	int 10h
	

	mov ah,9
	lea dx,numpar                  ;print out the number of parallel
	int 21h
	call get_number_of_ports
	mov dl,bl
	mov ah,2
	int 21h                        ;print the actual number 
	
	mov ah,9                       ;send a CR/LF
	lea dx,crlf
	int 21h
	
	lea dx,spa1                    ; print serial/parallel port 1
	int 21h                        ; and a CR/LF
	lea dx,spa2                    ; repeat this 3 more times
	int 21h
	lea dx,spa3
	int 21h
	lea dx,spa4
	int 21h
     
	
	call display_serial            ; display the addresses for 'em

	mov ax,4c00h                   ; end this puppy
	int 21h

cseg ends
end main






Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 29 Apr 2008 at 9:03 AM
Thanks alot for your attention.I will work on it.and certainly inform you.

You are best
Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 30 Apr 2008 at 3:14 PM
Hi,
At first thanks for your code.But finally i found the Smbios source code in assembly.i attatch the code.I want to know your opinion seriously about this code.and other request is that:

is it possible to use .EXE file as a Kernel in floppy?or at first it should be in binary.
for ex:at sector 0 is bootloader and sector 1 is kernel.

is it possible?
password is in your mail box.
Attachment: 2243smbios.rar (77081 Bytes | downloaded 328 times)
Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 30 Apr 2008 at 10:08 PM
Can you compile the smbios.asm?How?
Because i can not compile it with TASM:

Turbo Assembler Version 3.2 Copyright (c) 1988, 1992 Borland International

Assembling file: c:\tasm\tasm\1\smbios.asm to smbios.OBJ
*Warning* MASM.INC(15) Pass-dependent construction encountered
*Warning* c:\tasm\tasm\1\smbios.asm(34) Reserved word used as symbol: STACK
Error messages: None
Warning messages: 2
Passes: 1
Remaining memory: 960 bytes
**Fatal** Out of memory



thx
Report
Re: Hardware Spec From BIOS OR RAM Posted by steward on 1 May 2008 at 9:36 AM
Other question is that how can i put the binary code of the kernel in sector 1.because after compile i think the file is more than 512 byte.

What should i do?
Report
Re: Hardware Spec From BIOS OR RAM Posted by MT2002 on 3 May 2008 at 12:55 PM
: Other question is that how can i put the binary code of the kernel
: in sector 1

Don't. That code would crash at the very first instruction in a bootloader do to the org 0x100. (It should be 0x7c00, where the Bios loads sector 0 to) Not doing so causes a jump to an incorrect location in memory.

In either case, there are alot of other problems with the code that wont work for bootloaders (int 0x21 does not exist, for example)

(This is what it sounds like you are wanting to do, anyways.)

That code is for DOS--Not bootable.

[.:EvolutionEngine][.:MicroOS Operating System][Website :: OS Development Series]



 

Recent Jobs

Official Programmer's Heaven Blogs
Web Hosting | Browser and Social Games | Gadgets

Popular resources on Programmersheaven.com
Assembly | Basic | C | C# | C++ | Delphi | Flash | Java | JavaScript | Pascal | Perl | PHP | Python | Ruby | Visual Basic
© Copyright 2011 Programmersheaven.com - All rights reserved.
Reproduction in whole or in part, in any form or medium without express written permission is prohibited.
Violators of this policy may be subject to legal action. Please read our Terms Of Use and Privacy Statement for more information.
Operated by CommunityHeaven, a BootstrapLabs company.