gpt4 book ai didi

gcc - 约束 "Rah"和 "Ral"在扩展内联汇编中意味着什么?

转载 作者:行者123 更新时间:2023-12-03 16:11:02 24 4
gpt4 key购买 nike

该问题是由另一个论坛上某人提出的问题启发的。在以下代码中,扩展的内联汇编约束RahRal是什么意思。我以前没有看过这些:

#include<stdint.h>

void tty_write_char(uint8_t inchar, uint8_t page_num, uint8_t fg_color)
{
asm (
"int $0x10"
:
: "b" ((uint16_t)page_num<<8 | fg_color),
"Rah"((uint8_t)0x0e), "Ral"(inchar));
}

void tty_write_string(const char *string, uint8_t page_num, uint8_t fg_color)
{
while (*string)
tty_write_char(*string++, page_num, fg_color);
}

/* Use the BIOS to print the first command line argument to the console */
int main(int argc, char *argv[])
{
if (argc > 1)
tty_write_string(argv[1], 0, 0);

return 0;
}
特别是使用 RahRal作为此代码中的约束:
asm (
"int $0x10"
:
: "b" ((uint16_t)page_num<<8 | fg_color),
"Rah"((uint8_t)0x0e), "Ral"(inchar));
对于 GCC Documentation或x86/x86 simple constraintsmachine constraints没有 lh约束。 R是任何旧式寄存器, a是AX/EAX/RAX寄存器。
我不明白什么?

最佳答案

您正在查看的是旨在在具有BIOS的基于x86的PC上以实模式运行的代码。 Int 0x10 是BIOS服务,可以写入控制台。特别是 Int 0x10/AH=0x0e 是将单个字符写入TTY(终端)。
这本身并不能解释约束的含义。要了解RahRal的约束,您必须了解该代码不是由标准版本的GCC/CLANG编译的。它由一个名为 ia16-gcc 的GCC端口进行编译。它是针对8086/80186和80286及兼容处理器的特殊端口。它不会生成386指令,也不会在代码生成中使用32位寄存器。 GCC的该实验版本针对DOS(FreeDOS,MSDOS)和ELKS等16位环境。
网上很难找到ia16-gcc的HTML格式文档,但是我为最近的GCC 6.3.0 versions of the documentation on GitHub制作了一份副本。该文档是通过从源代码构建ia16-gcc并使用make生成HTML产生的。如果您查看Intel IA-16的机器限制-config/ia16,现在应该可以看到发生了什么事情:

Ral The al register.

Rah The ah register.


此版本的GCC不再自己理解 R约束。您正在查看的内联程序集与 Int 0x10/Ah=0xe的参数匹配:
VIDEO - TELETYPE OUTPUT
AH = 0Eh
AL = character to write
BH = page number
BL = foreground color (graphics modes only)

Return:
Nothing

Desc: Display a character on the screen, advancing the cursor
and scrolling the screen as necessary


其他资讯
该文档确实列出了可用于IA16目标的所有约束:
Intel IA-16—config/ia16/constraints.md
a
The ax register. Note that for a byte operand,
this constraint means that the operand can go into either al or ah.

b
The bx register.

c
The cx register.

d
The dx register.

S
The si register.

D
The di register.

Ral
The al register.

Rah
The ah register.

Rcl
The cl register.

Rbp
The bp register.

Rds
The ds register.

q
Any 8-bit register.

T
Any general or segment register.

A
The dx:ax register pair.

j
The bx:dx register pair.

l
The lower half of pairs of 8-bit registers.

u
The upper half of pairs of 8-bit registers.

k
Any 32-bit register group with access to the two lower bytes.

x
The si and di registers.

w
The bx and bp registers.

B
The bx, si, di and bp registers.

e
The es register.

Q
Any available segment register—either ds or es (unless one or both have been fixed).

Z
The constant 0.

P1
The constant 1.

M1
The constant -1.

Um
The constant -256.

Lbm
The constant 255.

Lor
Constants 128 … 254.

Lom
Constants 1 … 254.

Lar
Constants -255 … -129.

Lam
Constants -255 … -2.

Uo
Constants 0xXX00 except -256.

Ua
Constants 0xXXFF.

Ish
A constant usable as a shift count.

Iaa
A constant multiplier for the aad instruction.

Ipu
A constant usable with the push instruction.

Imu
A constant usable with the imul instruction except 257.

I11
The constant 257.

N
Unsigned 8-bit integer constant (for in and out instructions).

有许多新的约束和一些重新利用的约束。
特别是AX寄存器的 a约束与其他针对32位和64位代码的GCC版本不同。如果传递的值为8位值,则编译器可以自由选择带有 a约束的AH或AL。这意味着 a约束有可能在扩展的内联汇编语句中出现两次。
您可以使用以下命令将代码编译为DOS EXE:
ia16-elf-gcc -mcmodel=small -mregparmcall -march=i186 \
-Wall -Wextra -std=gnu99 -O3 int10h.c -o int10h.exe
这个目标是80186。您可以通过省略 -march=i186来生成8086兼容代码。 main的生成代码类似于:
00000000 <main>:
0: 83 f8 01 cmp ax,0x1
3: 7e 1d jle 22 <tty_write_string+0xa>
5: 56 push si
6: 89 d3 mov bx,dx
8: 8b 77 02 mov si,WORD PTR [bx+0x2]
b: 8a 04 mov al,BYTE PTR [si]
d: 20 c0 and al,al
f: 74 0d je 1e <tty_write_string+0x6>
11: 31 db xor bx,bx
13: b4 0e mov ah,0xe
15: 46 inc si
16: cd 10 int 0x10
18: 8a 04 mov al,BYTE PTR [si]
1a: 20 c0 and al,al
1c: 75 f7 jne 15 <main+0x15>
1e: 31 c0 xor ax,ax
20: 5e pop si
21: c3 ret
22: 31 c0 xor ax,ax
24: c3 ret
当使用命令行运行时, int10h.exe "Hello, world!"应该打印:

Hello, world!



特殊说明:GCC的IA16端口是非常试验性的,确实存在一些代码生成错误,尤其是在使用更高的优化级别时。目前,我不会将其用于关键任务应用程序。

关于gcc - 约束 "Rah"和 "Ral"在扩展内联汇编中意味着什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62686259/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com