使用 printf 组件打印新行

发布于 2024-12-21 19:00:29 字数 1350 浏览 2 评论 0原文

您好,我正在尝试编写一些使用 printf 打印给定字符串的汇编代码。我在 .data 部分中使用之前声明我的字符串,测试示例如下所示:

extern printf
extern fflush

LINUX        equ     80H      ; interupt number for entering Linux kernel
EXIT         equ     60       ; Linux system call 1 i.e. exit ()

section .data
    outputstringfmt: db "%s", 0
    sentence0: db "Hello\nWorld\n", 0


segment .text
    global  main


main:
    mov r8, sentence0
    push r8
    call print_sentence
    add rsp, 8
    call os_return

print_sentence:
    push rbp
    mov rbp, rsp
    push r12
    mov r12, [rbp + 16]
    push rsi
    push rdi
    push r8
    push r9
    push r10
    mov rsi, r12
    mov rdi, outputstringfmt
    xor rax, rax
    call printf
    xor rax, rax
    call fflush
    pop r10
    pop r9
    pop r8
    pop rdi
    pop rsi
    pop r12
    pop rbp
    ret

os_return:
    mov  rax, EXIT      ; Linux system call 1 i.e. exit ()
    mov  rdi, 0     ; Error code 0 i.e. no errors
    syscall     ; Interrupt Linux kernel 64-bit

然后我按如下方式编译:

nasm -f elf64 test.asm; gcc -m64 -o test test.o

最后运行:

./test

我的输出如下:

Hello\nWorld\n

我真的不想将句子0分成以下:

sentence0: db "Hello", 10, 0
sentence1: db "World", 10, 0

然后调用打印两次。有更好的方法吗?

提前致谢!

Hi I'm trying to write some assembly code that uses printf to print a given string. I am declaring my strings before use in the .data section and a test example looks as follows:

extern printf
extern fflush

LINUX        equ     80H      ; interupt number for entering Linux kernel
EXIT         equ     60       ; Linux system call 1 i.e. exit ()

section .data
    outputstringfmt: db "%s", 0
    sentence0: db "Hello\nWorld\n", 0


segment .text
    global  main


main:
    mov r8, sentence0
    push r8
    call print_sentence
    add rsp, 8
    call os_return

print_sentence:
    push rbp
    mov rbp, rsp
    push r12
    mov r12, [rbp + 16]
    push rsi
    push rdi
    push r8
    push r9
    push r10
    mov rsi, r12
    mov rdi, outputstringfmt
    xor rax, rax
    call printf
    xor rax, rax
    call fflush
    pop r10
    pop r9
    pop r8
    pop rdi
    pop rsi
    pop r12
    pop rbp
    ret

os_return:
    mov  rax, EXIT      ; Linux system call 1 i.e. exit ()
    mov  rdi, 0     ; Error code 0 i.e. no errors
    syscall     ; Interrupt Linux kernel 64-bit

I'm then compiling as follows:

nasm -f elf64 test.asm; gcc -m64 -o test test.o

And finally running:

./test

My output is as follows:

Hello\nWorld\n

I really don't want to split sentence0 up into the following:

sentence0: db "Hello", 10, 0
sentence1: db "World", 10, 0

and then call the print twice. Is there a better way to do it?

Thanks in advance!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

陌路终见情 2024-12-28 19:00:29

NASM 接受单引号 ('...') 或双引号 ("...") 中的字符串,它们是等效的,并且不提供任何转义;或反引号 (`...`),它提供对 C 风格转义的支持,这正是您想要的。

(请参阅文档中的第 3.4.2 节“字符串”< /a>.)

要在内存中的数据中获取实际的 ASCII 换行符,而不是文字反斜杠 n:

sentence0: db `Hello\nWorld\n`, 0

或者手动执行:

sentence0: db 'Hello', 10, 'World`, 10, 0

YASM(另一个 NASM 语法汇编器)不接受反引号,因此手动选项是您唯一的选择。

顺便说一句,如果您的格式字符串中没有任何实际格式(省略尾随换行符),您可以调用 puts 而不是 printf 。

NASM accepts strings in single quotes ('...') or double quotes ("..."), which are equivalent, and do not provide any escapes; or in backquotes (`...`), which provide support for C-style escapes, which is what you want.

(See section 3.4.2, "Character Strings", in the documentation.)

To get actual ASCII newlines in your data in memory, rather than literal backslash n:

sentence0: db `Hello\nWorld\n`, 0

Or do it manually:

sentence0: db 'Hello', 10, 'World`, 10, 0

YASM (another NASM-syntax assembler) doesn't accept backticks, so the manual option is your only choice there.

And BTW, you can call puts instead of printf if you don't have any actual formatting in your format string (leave out the trailing newline).

z祗昰~ 2024-12-28 19:00:29

要输出的字符串中有换行符 (\n)。它们应该位于被视为换行符的格式字符串中。这解决了一半的问题:

outputstringfmt: db "%s\n%s\n", 0
sentence0: db "Hello", 0
sentence1: db "World", 0

像这样的东西应该在每个单词后打印换行符:

outputstringfmt: db "%s", 0
sentence0: db "Hello", 10 , "World", 10 , 0

You have the newlines (\n) in the string to be output. They should be in the format string to be treated as newlines. This solves half of your problem:

outputstringfmt: db "%s\n%s\n", 0
sentence0: db "Hello", 0
sentence1: db "World", 0

And something like this should print newlines after each word:

outputstringfmt: db "%s", 0
sentence0: db "Hello", 10 , "World", 10 , 0
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文