nasm 中的十六进制数相乘
Multiplying hexadecimal numbers in nasm
简短版本:如何将十六进制数与 asm 相乘,结果将存储在哪里以及如何访问它并将其移动到 eax
注册?
更长的版本,它解释了为什么我需要这样做以及采用哪种格式:
我想要一个字节数组来存储我要输出到显存中的一些字符的ASCII码。我可以这样输出两个字符:
org 100 h
start:
mov ax, 0003h
int 10h
mov ax, 0b800h
mov es, ax
mov di, 100
mov eax, 1f651f48h
stosd
ret
这将在屏幕左上角附近的某处以蓝底白字输出He
。但我想打印 'Hello world!'。所以我想我将符号代码存储在一个数组中,通过加法和乘法形成像 1f651f48h
这样的十六进制数,然后使用 rep
命令循环输出它们。
但是我不明白如何组成这样的十六进制数。我真的不明白我在这里使用的数字是否需要在 eax
或 ax
中,或者我如何获取结果。所以我想请求一些解释。
此数字的工作原理:1f
是一个属性,用于蓝底白字。 65
是e
的ASCII码,48
是h
的ASCII码。所以我需要将 48 乘以 10000(所有数字都是十六进制)并添加到 1f001f00h
,然后将 65 添加到先前操作的结果并将其全部移动到 eax
寄存器。
我也对寄存器的使用感到困惑。 cx
寄存器用于 'loop iterations'; bx
将用于遍历数组;结果数字需要放在 eax
中。这让我只剩下 edx
用于临时计算,是否可以只用这个来做我需要的事情?
我在 qemu 中的 freedos 仿真下使用 NASM。
How this number works: 1f is an attribute, this is for white letters on blue background. 65 is the ASCII code for e, 48 is for h. So I'd need to multiply 48 by 10000 (all numbers are hexadecimal) and add to 1f001f00h, then add 65 to the result of the previous actions and move it all to the eax register.
如果按照此计算,您会在屏幕上看到 WhiteOnBlue "eH",而不是您期望的 "He"!
这里的好消息是您不需要任何计算来显示文本。
只需定义消息,然后在循环中从中获取单个字符并将其显示在屏幕上。
由于这是一个 .COM 文件 (org 100h
),DS
段寄存器已经正确设置。
org 100h
start:
mov ax, 0003h ;Text video mode 80x25
int 10h
mov ax, 0B800h ;Segment of video memory
mov es, ax
mov di, 100 ;Address in video memory
cld
mov si, msg ;Where is the message
Again:
lodsb ;Get 1 character into AL
cmp al, 0 ;Is it terminating zero?
je EndOfLoop ;Yes
mov ah,1Fh ;Combine with attribute
stosw ;Store AX in video memory
jmp Again ;Continu the loop
EndOfLoop:
ret
msg db 'Hello world!',0
简短版本:如何将十六进制数与 asm 相乘,结果将存储在哪里以及如何访问它并将其移动到 eax
注册?
更长的版本,它解释了为什么我需要这样做以及采用哪种格式:
我想要一个字节数组来存储我要输出到显存中的一些字符的ASCII码。我可以这样输出两个字符:
org 100 h
start:
mov ax, 0003h
int 10h
mov ax, 0b800h
mov es, ax
mov di, 100
mov eax, 1f651f48h
stosd
ret
这将在屏幕左上角附近的某处以蓝底白字输出He
。但我想打印 'Hello world!'。所以我想我将符号代码存储在一个数组中,通过加法和乘法形成像 1f651f48h
这样的十六进制数,然后使用 rep
命令循环输出它们。
但是我不明白如何组成这样的十六进制数。我真的不明白我在这里使用的数字是否需要在 eax
或 ax
中,或者我如何获取结果。所以我想请求一些解释。
此数字的工作原理:1f
是一个属性,用于蓝底白字。 65
是e
的ASCII码,48
是h
的ASCII码。所以我需要将 48 乘以 10000(所有数字都是十六进制)并添加到 1f001f00h
,然后将 65 添加到先前操作的结果并将其全部移动到 eax
寄存器。
我也对寄存器的使用感到困惑。 cx
寄存器用于 'loop iterations'; bx
将用于遍历数组;结果数字需要放在 eax
中。这让我只剩下 edx
用于临时计算,是否可以只用这个来做我需要的事情?
我在 qemu 中的 freedos 仿真下使用 NASM。
How this number works: 1f is an attribute, this is for white letters on blue background. 65 is the ASCII code for e, 48 is for h. So I'd need to multiply 48 by 10000 (all numbers are hexadecimal) and add to 1f001f00h, then add 65 to the result of the previous actions and move it all to the eax register.
如果按照此计算,您会在屏幕上看到 WhiteOnBlue "eH",而不是您期望的 "He"!
这里的好消息是您不需要任何计算来显示文本。
只需定义消息,然后在循环中从中获取单个字符并将其显示在屏幕上。
由于这是一个 .COM 文件 (org 100h
),DS
段寄存器已经正确设置。
org 100h
start:
mov ax, 0003h ;Text video mode 80x25
int 10h
mov ax, 0B800h ;Segment of video memory
mov es, ax
mov di, 100 ;Address in video memory
cld
mov si, msg ;Where is the message
Again:
lodsb ;Get 1 character into AL
cmp al, 0 ;Is it terminating zero?
je EndOfLoop ;Yes
mov ah,1Fh ;Combine with attribute
stosw ;Store AX in video memory
jmp Again ;Continu the loop
EndOfLoop:
ret
msg db 'Hello world!',0