In this post, I write about how to make the SOFTWARE.BIG1
file with NASM, I experiment with the segmentation of RAM and I use the
%include directive.
In the post
"Getting a new tool", I wrote why I needed to extend my toolbox and I got NASM as a new tool
which I planned to use together with DEBUG.EXE. In the two posts before this
one, I wrote about what the directives ORG and
SECTION are and how to use them. I also
explained that the directive SECTION can be
used to define segments. At this point, I have to show how to use this new
tool (NASM) to make the SOFTWARE.BIG file and continue
my exploration of the deep binary space. I thought that meanwhile
creating a demonstrative SOFTWARE.BIG (just to demonstrate how to do it), I
could also take this opportunity to experiment a little bit on two aspects:
Segments in RAM have no predefined purpose in 8086 real-mode
In 8086 16-bit real mode, every segment is a consecutive block of 64KB RAM.
Just it. There is no additional constraint about being one of such segment
read-only, or not executable and so on. The segments are just 64KB of RAM that
the programmer can use as he/she wants. There is no concept of a code segment
or a data segment. To demonstrate it I have created a program that defines
seven segments with the use of the directive
SECTION. I named the segments by colours to
remark the fact that segments are free from labels but it is the use that the
programmer makes of them that gives meaning to the segments.
;##############################################################################
; Learn NASM - 03.asm
;
;
; Build with:
; nasm -f bin "Learn NASM - 03.asm" -l "Learn NASM - 03.lst" -o "SOFTWARE.BIG"
;##############################################################################
org 0x7c00 ; Loading point of SOFTWARE.BIG in RAM
;
;##############################################################################
; Full definition of section IN COMBINATION WITH -f bin !!!
;
; Sections can be aligned at a specified boundary following the previous
; section with align=, or at an arbitrary byte-granular position with start=.
;
; align= -> can be any power of 2.
; start= -> is a flat address (example: 0x01_7C00) where the section starts
; in memory.
; vstart= -> the virtual start address, which will be used for the calculation
; of all memory references within that section
;##############################################################################
section _general_reset start=0x0_7c00
section _red start=0x0_7c30 vstart=0x00
section _blue start=0x1_7c30 vstart=0x00
section _green start=0x2_7c30 vstart=0x00
section _yellow start=0x3_7c30 vstart=0x00
section _pink start=0x4_7c30 vstart=0x00
section _orange start=0x5_7c30 vstart=0x00
;##############################################################################
; General reset
; SHUTTLE2 leaves CS = DS = ES = SS = 0x0000 and I want to set:
; DS = _blue
; ES = _green
; SS = _orange
; CS = _red
;##############################################################################
section _general_reset
;----------------------------------------
; Validation signature for SOFTWARE.BIG
;----------------------------------------
DB 0xA2, 0xDD, 0x7B, 0x8B, 0x87, 0x00, 0x05, 0x3D, \
0xFF, 0xFF, 0x74, 0x19, 0x3D, 0x02, 0x00, 0x72
cli ; deactivate interrupts
mov ax, 0x17c3 ; DS = _blue
mov ds, ax ;
mov ax, 0x27c3 ; ES = _green
mov es, ax ;
mov ax, 0x57c3 ; SS = _orange
mov ss, ax ;
mov sp, 0xfffe ;
sti ; reactivate interrupts
jmp 0x07c3:_entry_point ; Jump _entry_point: --->
;##############################################################################
;
; PROGRAM START
;
;##############################################################################
section _red
;
; <---
;
_entry_point:
mov si, _bbb ; SI -> "CS =...".
call 0x07c3:_SHOW_STR ;
mov si, _aaa ; SI -> "Press any key for next jump...".
call 0x07c3:_SHOW_STR ;
;
;--------------------------------------------------------------------------
; wait for key press...
;--------------------------------------------------------------------------
xor ax, ax ; int 16/ah = 00 : keyboard get keystroke
int 0x16 ; returns: ah = BIOS scan code
; al = ASCII character
jmp 0x17c3:_nowBlue ; Jump _nowBlue: --->
section _blue
;
; <---
;
_nowBlue:
mov si, _ccc ; SI -> "CS =...".
call 0x07c3:_SHOW_STR ;
mov si, _aaa ; SI -> "Press any key for next jump...".
call 0x07c3:_SHOW_STR ;
;
;--------------------------------------------------------------------------
; wait for key press...
;--------------------------------------------------------------------------
xor ax, ax ; int 16/ah = 00 : keyboard get keystroke
int 0x16 ; returns: ah = BIOS scan code
; al = ASCII character
jmp 0x27c3:_nowGreen ; Jump _nowGreen: --->
section _green
;
; <---
;
_nowGreen:
mov si, _ddd ; SI -> "CS =...".
call 0x07c3:_SHOW_STR ;
mov si, _aaa ; SI -> "Press any key for next jump...".
call 0x07c3:_SHOW_STR ;
;
;--------------------------------------------------------------------------
; wait for key press...
;--------------------------------------------------------------------------
xor ax, ax ; int 16/ah = 00 : keyboard get keystroke
int 0x16 ; returns: ah = BIOS scan code
; al = ASCII character
jmp 0x37c3:_nowYellow ; Jump _nowYellow: --->
section _yellow
;
; <---
;
_nowYellow:
mov si, _eee ; SI -> "CS =...".
call 0x07c3:_SHOW_STR ;
mov si, _aaa ; SI -> "Press any key for next jump...".
call 0x07c3:_SHOW_STR ;
;
;--------------------------------------------------------------------------
; wait for key press...
;--------------------------------------------------------------------------
xor ax, ax ; int 16/ah = 00 : keyboard get keystroke
int 0x16 ; returns: ah = BIOS scan code
; al = ASCII character
jmp 0x47c3:_nowPink ; Jump _nowPink: --->
section _pink
;
; <---
;
_nowPink:
mov si, _fff ; SI -> "CS =...".
call 0x07c3:_SHOW_STR ;
mov si, _aaa ; SI -> "Press any key for next jump...".
call 0x07c3:_SHOW_STR ;
;
;--------------------------------------------------------------------------
; wait for key press...
;--------------------------------------------------------------------------
xor ax, ax ; int 16/ah = 00 : keyboard get keystroke
int 0x16 ; returns: ah = BIOS scan code
; al = ASCII character
jmp 0x57c3:_nowOrange ; Jump _nowOrange: --->
section _orange
;
; <---
;
_nowOrange:
mov si, _ggg ; SI -> "CS =...".
call 0x07c3:_SHOW_STR ;
mov si, _hhh ; SI -> "Press any key for next jump...".
call 0x07c3:_SHOW_STR ;
;--------------------------------------------------------------------------
; wait for key press and terminate
;--------------------------------------------------------------------------
xor ax, ax ; int 16/ah = 00 : keyboard get keystroke
int 0x16 ; returns: ah = BIOS scan code
; al = ASCII character
;
jmp 0xffff:0000 ; Total system reset since INT19 hangs
; on HP Elitebook
;##############################################################################
; All messages in section _blue
;##############################################################################
section _blue
_aaa:
db "Press any key for next jump...", 0x0d, 0x0a, 0x00
_bbb:
db "CS = _red", 0x0d, 0x0a, 0x00
_ccc:
db "CS = _blue", 0x0d, 0x0a, 0x00
_ddd:
db "CS = _green", 0x0d, 0x0a, 0x00
_eee:
db "CS = _yellow", 0x0d, 0x0a, 0x00
_fff:
db "CS = _pink", 0x0d, 0x0a, 0x00
_ggg:
db "CS = _orange", 0x0d, 0x0a, 0x00
_hhh:
db "Press any key to reboot...", 0x0d, 0x0a, 0x00
;##############################################################################
;
; SHOW_STR: SHOW STRing
;
; This procedure shows a string on the video starting at address [DS:SI]
; and terminating as soon as it finds the byte 0x00
;
; INPUT: [DS:SI] at start of string (1st char)
; OUTPUT: [DS:SI] at end of string (char 0x00)
; REGISTER USAGE: AX, BX
; THIS ONE CALLS: int10
;
;##############################################################################
section _red
_SHOW_STR:
push ax ; Preserve extra used registers.
push bx ;
jmp _show_str_start ; JUMP _show_str_start: --->
;
;<---
;
_one_char_on_screen: ;
;---------------------------------------
; standard setup for displaying
; characters on the screen
;---------------------------------------
mov ah, 0x0e ; int10/ah = 0e : video teletype out
; al = character to write
mov bx, 0x07 ; bh = page number
; bl = foreground color (graphics mode only)
; int10 returns nothing
int 0x10 ;
;
;<---
;
_show_str_start: ;
lodsb ; AL = [DS:SI]; SI = SI + 1
cmp al, 0x00 ; flags = AL - 0x00
; Unsigned comparison:
jne _one_char_on_screen ; JumpNotEqual _one_char_on_screen: --->
;
;--------------------------------------------------------------------------
; END of local procedure SHOW_STR
;--------------------------------------------------------------------------
pop bx ; Restore extra used registers.
pop ax ;
retf ;
I assigned the Stack Segment Register (SS) to _orange and the Data
Segment Register (DS) to _blue, but this doesn't mean that the RAM segments
_orange and _blue are just stack and data. In fact, I used all
segments for code as well and I jumped from the first to the last segment
every time executing a small portion of code. In this way, I showed that, for
instance, the RAM segment _orange can be a Stack Segment and a Code
Segment at the same time.
Another important aspect of this program was that I created a large
SOFTWARE.BIG (about 321 KB) that my boot loader
SHUTTLE2
had to load by scanning the FAT one cluster after the other hence this was
also a test for my boot loader
SHUTTLE2
at the same time.
I embedded the procedure SHOW_STR in the _red segment to bring
the messages on the screen, but since the value of the CS segment had to
change from jump to jump, I planned to use FAR CALL and
FAR RETURN. The FAR CALL is realized with the syntax
call seg:off and the
FAR RETURN with the OPCODE retf.
Please note that when using the option
-f bin with NASM, the names of the
sections are not labels!
This means that call _red:_SHOW_STR is not
legal and one has to use the numeric value of the segment defined with the
SECTION directive like this:
call 0x07c3:_SHOW_STR2.
|
Fig. A - Screenshot
|
In
Fig. A
you see the screenshot on my test notebook and this concludes this experiment.
How to use the %include directive with NASM.
The %include directive is used by the
preprocessor of NASM. The preprocessor replaces all lines where the
%include directive appears with the file that
the same directive is pointing to. If the included file contains again a new
%include directive, the preprocessor repeats
the same process on and on again until all
%include directives are properly replaced by
the content of the file they are pointing to.
I wanted to take advantage of this functionality and I thought to organize my
projects in the following way.
|
Fig. B - Organization of a SOFTWARE.BIG project
|
I created a main folder which contained the MAIN ASM-file of the project
together with an INC-file and a subfolder with the same name as the MAIN
ASM-file (see
Fig. B). My idea was to use the MAIN ASM-file as the entry point of the project.
The subfolder named following the MAIN ASM-file was the place to keep all the
used service procedures. This was my way to organize the
library for the project. Finally, I used the INC-file to list all the
sub-procedure that the MAIN procedure needed and that were stored inside the
library folder.
Here follows an example that I created to test this idea and illustrate it at
the same time. Additionally, based on the experience made in the previous
paragraph, I decided to use three segments only: _justCode, _justData and
_justStack.
;##############################################################################
; "Learn NASM - 04.nsm"
;
;
; Build with:
; nasm -f bin "Learn NASM - 04.asm" -l "Learn NASM - 04.lst" -o "SOFTWARE.BIG"
;##############################################################################
org 0x7c00 ; Loading point of SOFTWARE.BIG in RAM
; The function of the ORG directive is to specify
; the origin address which NASM will assume
; the program begins at when it is loaded
; into memory. Its sole function is to specify one
; offset which is added to all internal address
; references within the section (section) unless
; one redefine the section with a vstart= option.
;
; IMPORTANT!!!
; -> org can be used only one time in the whole
; source code.
; -> org can be placed anywhere in the source code
; (but only once).
; -> org can be used only with -f bin output file
; format (it is not the same as in MASM).
;##############################################################################
; Full definition of section IN COMBINATION WITH -f bin !!!
;
; IMPORTANT!!!
; In case of -f bin, section CAN BE USED to define a segment but IT IS NOT a
; synonymous for SEGMENT
;
; Sections can be aligned at a specified boundary following the previous
; section with align=, or at an arbitrary byte-granular position with start=.
;
; align= -> can be any power of 2.
; start= -> is a flat address (example: 0x01_7C00) where the section starts
; in memory.
; vstart= -> the virtual start address, which will be used for the calculation
; of all memory references within that section
;##############################################################################
section _general_reset start=0x0_7c00
section _justCode start=0x0_7c30 vstart=0x00
section _justData start=0x1_7c30 vstart=0x00
section _justStack start=0x2_7c30 vstart=0x00
;##############################################################################
; Include all required service procedures.
;##############################################################################
%include ".\Learn NASM - 04.inc"
;##############################################################################
; General reset
; SHUTTLE2 leaves CS = DS = ES = SS = 0x0000 and I want to set:
; ES = DS = _justData
; SS = _justStack
; CS = _justCode
;##############################################################################
section _general_reset
;----------------------------------------
; Validation signature for SOFTWARE.BIG
;----------------------------------------
DB 0xA2, 0xDD, 0x7B, 0x8B, 0x87, 0x00, 0x05, 0x3D, \
0xFF, 0xFF, 0x74, 0x19, 0x3D, 0x02, 0x00, 0x72
cli ; deactivate interrupts
mov ax, 0x17c3 ; DS = _justData
mov ds, ax ;
mov es, ax ;
mov ax, 0x27c3 ; SS = _justStack
mov ss, ax ;
mov sp, 0xfffe ;
sti ; reactivate interrupts
jmp 0x07c3:_entry_point ; Jump _entry_point: --->
;##############################################################################
;
; PROGRAM START
;
;##############################################################################
;---------------------------------
; Start chat
;---------------------------------
section _justData
_aaa:
db " Landing Module II:", 0x0d, 0x0a
db " Hello Huston, we have a good landing.", 0x0d, 0x0a
db 0x0d, 0x0a, 0x00
;
; <---
;
section _justCode
_entry_point:
mov si, _aaa ; SI -> "Hello Huston...".
call _SHOW_STR ;
;
section _justData
_bbb:
db "Huston:", 0x0d, 0x0a
db "God Job! We confirm from here that all systems are ok.", 0x0d, 0x0a
db "You can close the mission. Thank you!", 0x0d, 0x0a, 0x0d, 0x0a, 0x00
section _justCode
mov si, _bbb ; SI -> "God Job!...".
call _SHOW_STR ;
;
section _justData
_ccc:
db " Landing Module II:", 0x0d, 0x0a
db " OK Huston, we shut down the systems", 0x0d, 0x0a
db " and close the mission.", 0x0d, 0x0a, 0x00
section _justCode
mov si, _ccc ; SI -> "OK Huston...".
call _SHOW_STR ;
;
;
;--------------------------------------------------------------------------
; wait for key press and terminate
;--------------------------------------------------------------------------
xor ax, ax ; int 16/ah = 00 : keyboard get keystroke
int 0x16 ; returns: ah = BIOS scan code
; al = ASCII character
;
jmp 0xffff:0000 ; Total system reset since INT 19H hangs
; on HP Elitebook
;##############################################################################
; INCLUDE file for "Learn NASM - 04.nsm"
;
; This file lists all required file that need to be included.
;##############################################################################
%include ".\Learn NASM - 04\show_string.asm"
In the list file, you can see the effect of the repeated
%include which had generated a huge, single
text file that NASM assembled all together.
1 ;##############################################################################
2 ; "Learn NASM - 04.nsm"
3 ;
4 ;
5 ; Build with:
6 ; nasm -f bin "Learn NASM - 04.asm" -l "Learn NASM - 04.lst" -o "SOFTWARE.BIG"
7 ;##############################################################################
8
9 org 0x7c00 ; Loading point of SOFTWARE.BIG in RAM
10 ; The function of the ORG directive is to specify
11 ; the origin address which NASM will assume
12 ; the program begins at when it is loaded
13 ; into memory. Its sole function is to specify one
14 ; offset which is added to all internal address
15 ; references within the section (section) unless
16 ; one redefine the section with a vstart= option.
17 ;
18 ; IMPORTANT!!!
19 ; -> org can be used only one time in the whole
20 ; source code.
21 ; -> org can be placed anywhere in the source code
22 ; (but only once).
23 ; -> org can be used only with -f bin output file
24 ; format (it is not the same as in MASM).
25
26
27 ;##############################################################################
28 ; Full definition of section IN COMBINATION WITH -f bin !!!
29 ;
30 ; IMPORTANT!!!
31 ; In case of -f bin, section CAN BE USED to define a segment but IT IS NOT a
32 ; synonymous for SEGMENT
33 ;
34 ; Sections can be aligned at a specified boundary following the previous
35 ; section with align=, or at an arbitrary byte-granular position with start=.
36 ;
37 ; align= -> can be any power of 2.
38 ; start= -> is a flat address (example: 0x01_7C00) where the section starts
39 ; in memory.
40 ; vstart= -> the virtual start address, which will be used for the calculation
41 ; of all memory references within that section
42 ;##############################################################################
43 section _general_reset start=0x0_7c00
44 section _justCode start=0x0_7c30 vstart=0x00
45 section _justData start=0x1_7c30 vstart=0x00
46 section _justStack start=0x2_7c30 vstart=0x00
47
48
49 ;##############################################################################
50 ; Include all required service procedures.
51 ;##############################################################################
52 %include ".\Learn NASM - 04.inc"
53 <1> ;##############################################################################
54 <1> ; INCLUDE file for "Learn NASM - 04.nsm"
55 <1> ;
56 <1> ; This file lists all required file that need to be included.
57 <1> ;##############################################################################
58 <1>
59 <1> %include ".\Learn NASM - 04\show_string.asm"
60 <2> ;##############################################################################
61 <2> ; "show_string.asm"
62 <2> ; _SHOW_STR: SHOW STRing
63 <2> ;
64 <2> ; This procedure shows a string on the video starting at address [DS:SI]
65 <2> ; and terminating as soon as it finds the byte 0x00
66 <2> ;
67 <2> ; INPUT: [DS:SI] at start of string (1st char)
68 <2> ; OUTPUT: [DS:SI] at end of string (char 0x00)
69 <2> ; REGISTER USAGE: AX, BX
70 <2> ; THIS ONE CALLS: INT 10H
71 <2> ;
72 <2> ;##############################################################################
73 <2> ;
74 <2> ;<--- MAIN ENTRY POINT
75 <2> ;
76 <2> section _justCode
77 <2> _SHOW_STR:
78 00000000 50 <2> push ax ; Preserve extra used registers.
79 00000001 53 <2> push bx ;
80 00000002 EB07 <2> jmp _show_str_start ; JUMP _show_str_start: --->
81 <2>
82 <2> ;
83 <2> ;<---
84 <2> ;
85 <2> _one_char_on_screen: ;
86 <2> ;---------------------------------------
87 <2> ; standard setup for displaying
88 <2> ; characters on the screen
89 <2> ;---------------------------------------
90 00000004 B40E <2> mov ah, 0x0e ; int10/ah = 0e : video teletype out
91 <2> ; al = character to write
92 00000006 BB0700 <2> mov bx, 0x07 ; bh = page number
93 <2> ; bl = foreground color (graphics mode only)
94 <2> ; int10 returns nothing
95 00000009 CD10 <2> int 0x10 ;
96 <2>
97 <2> ;
98 <2> ;<---
99 <2> ;
100 <2> _show_str_start: ;
101 0000000B AC <2> lodsb ; AL = [DS:SI]; SI = SI + 1
102 0000000C 3C00 <2> cmp al, 0x00 ; flags = AL - 0x00
103 <2> ; Unsigned comparison:
104 0000000E 75F4 <2> jne _one_char_on_screen ; JumpNotEqual _one_char_on_screen: --->
105 <2> ;
106 <2> ;--------------------------------------------------------------------------
107 <2> ; END of local procedure SHOW_STR
108 <2> ;--------------------------------------------------------------------------
109 00000010 5B <2> pop bx ; Restore extra used registers.
110 00000011 58 <2> pop ax ;
111 00000012 C3 <2> ret ;
60 <1>
53
54
55 ;##############################################################################
56 ; General reset
57 ; SHUTTLE2 leaves CS = DS = ES = SS = 0x0000 and I want to set:
58 ; ES = DS = _justData
59 ; SS = _justStack
60 ; CS = _justCode
61 ;##############################################################################
62 section _general_reset
63 ;----------------------------------------
64 ; Validation signature for SOFTWARE.BIG
65 ;----------------------------------------
66 00000000 A2DD7B8B8700053DFF- DB 0xA2, 0xDD, 0x7B, 0x8B, 0x87, 0x00, 0x05, 0x3D, 0xFF, 0xFF, 0x74, 0x19, 0x3D, 0x02, 0x00, 0x72
66 00000009 FF74193D020072
68
69 00000010 FA cli ; deactivate interrupts
70 00000011 B8C317 mov ax, 0x17c3 ; DS = _justData
71 00000014 8ED8 mov ds, ax ;
72 00000016 8EC0 mov es, ax ;
73 00000018 B8C327 mov ax, 0x27c3 ; SS = _justStack
74 0000001B 8ED0 mov ss, ax ;
75 0000001D BCFEFF mov sp, 0xfffe ;
76 00000020 FB sti ; reactivate interrupts
77 00000021 EA[1300]C307 jmp 0x07c3:_entry_point ; Jump _entry_point: --->
78
79
80
81
82
83 ;##############################################################################
84 ;
85 ; PROGRAM START
86 ;
87 ;##############################################################################
88 ;---------------------------------
89 ; Start chat
90 ;---------------------------------
91 section _justData
92 _aaa:
93 00000000 202020202020202020- db " Landing Module II:", 0x0d, 0x0a
93 00000009 202020202020202020-
93 00000012 20204C616E64696E67-
93 0000001B 204D6F64756C652049-
93 00000024 493A0D0A
94 00000028 202020202020202020- db " Hello Huston, we have a good landing.", 0x0d, 0x0a
94 00000031 202020202020202020-
94 0000003A 202048656C6C6F2048-
94 00000043 7573746F6E2C207765-
94 0000004C 206861766520612067-
94 00000055 6F6F64206C616E6469-
94 0000005E 6E672E0D0A
95 00000063 0D0A00 db 0x0d, 0x0a, 0x00
96
97
98 ;
99 ; <---
100 ;
101 section _justCode
102 _entry_point:
103 00000013 BE[0000] mov si, _aaa ; SI -> "Hello Huston...".
104 00000016 E8E7FF call _SHOW_STR ;
105 ;
106
107 section _justData
108 _bbb:
109 00000066 487573746F6E3A0D0A db "Huston:", 0x0d, 0x0a
110 0000006F 476F64204A6F622120- db "God Job! We confirm from here that all systems are ok.", 0x0d, 0x0a
110 00000078 576520636F6E666972-
110 00000081 6D2066726F6D206865-
110 0000008A 726520746861742061-
110 00000093 6C6C2073797374656D-
110 0000009C 7320617265206F6B2E-
110 000000A5 0D0A
111 000000A7 596F752063616E2063- db "You can close the mission. Thank you!", 0x0d, 0x0a, 0x0d, 0x0a, 0x00
111 000000B0 6C6F73652074686520-
111 000000B9 6D697373696F6E2E20-
111 000000C2 5468616E6B20796F75-
111 000000CB 210D0A0D0A00
112
113 section _justCode
114 00000019 BE[6600] mov si, _bbb ; SI -> "God Job!...".
115 0000001C E8E1FF call _SHOW_STR ;
116 ;
117
118 section _justData
119 _ccc:
120 000000D1 202020202020202020- db " Landing Module II:", 0x0d, 0x0a
120 000000DA 202020202020202020-
120 000000E3 20204C616E64696E67-
120 000000EC 204D6F64756C652049-
120 000000F5 493A0D0A
121 000000F9 202020202020202020- db " OK Huston, we shut down the systems", 0x0d, 0x0a
121 00000102 202020202020202020-
121 0000010B 20204F4B2048757374-
121 00000114 6F6E2C207765207368-
121 0000011D 757420646F776E2074-
121 00000126 68652073797374656D-
121 0000012F 730D0A
122 00000132 202020202020202020- db " and close the mission.", 0x0d, 0x0a, 0x00
122 0000013B 202020202020202020-
122 00000144 2020616E6420636C6F-
122 0000014D 736520746865206D69-
122 00000156 7373696F6E2E0D0A00
123
124 section _justCode
125 0000001F BE[D100] mov si, _ccc ; SI -> "OK Huston...".
126 00000022 E8DBFF call _SHOW_STR ;
127 ;
128 ;
129 ;--------------------------------------------------------------------------
130 ; wait for key press and terminate
131 ;--------------------------------------------------------------------------
132 00000025 31C0 xor ax, ax ; int 16/ah = 00 : keyboard get keystroke
133 00000027 CD16 int 0x16 ; returns: ah = BIOS scan code
134 ; al = ASCII character
135 ;
136 00000029 EA0000FFFF jmp 0xffff:0000 ; Total system reset since INT 19H hangs
137 ; on HP Elitebook
138
139
140
141
142
143
144
145
146
You can see the program "Learn NASM - 04" (packed inside the SOFTWARE.BIG
file) running in the next picture (Fig. C).
|
Fig. C - "Learn NASM - 04" running in real-mode
|
Comments
Post a Comment