![](/img/trans.png)
[英]How to correctly use the "write" syscall on MacOS to print to stdout?
[英]How do I print an integer with the write syscall?
这是一个简单的项目,它从系统时钟创建一个随机数字。 它需要一个数字,将其转换为一个数字,然后加上 48,以便在 ASCII 表中匹配。 我遇到的问题是它不打印任何东西。 据我所知,它需要是一个字符串才能考虑打印。 有没有办法可以“投射”它? 是的,我知道,它是 integer,但假装它在 ascii 表上? 这是我的代码供参考。 除“prnt_clock”外,一切正常。 最后一件事,我不能使用任何 C 代码/功能,所以不,我不能使用 printf。
.global rand
.equ STDOUT, 1
.equ WRITE, 4
rand:
PUSH {LR}
BL get_clock
LDR R1, =time
ADD R1, R1, #5
LDRB R0, [R1]
BL num_to_digit
ADD R0, R0, #48
MOV R1, R0
BL prnt_clock
B rand_leave
get_clock:
MOV R7, #78 @ Get time of day
LDR R0, =time @ address of holder for time_t
MOV R1, #0 @ time zone not needed
SWI 0
MOV PC, LR
// Assumes the number is in R0
num_to_digit:
CMP R0, #9 @ Compare num to 9
SUBGT R0, R0, #10 @ If greater than, substract 10
BGT num_to_digit @ Repeat until its eq or lower than 9
MOV PC, LR @ Comeback to main
prnt_clock:
MOV R0, #STDOUT @ Print to terminal
MOV R2, #1 @ Print only the digit
MOV R7, #WRITE @ Write Syscall
@MOV R3, #0 @ Create a counter
SWI 0
rand_leave:
POP {LR}
MOV PC, LR
.data
time: .space 9
通常,您使用 printf 或其他库来打印 integer。
如果您正在寻找独立程序,请使用编译器编译 C 以用于组装 output:
/*
r3 = magic division number
r2 = division
r0 = integer to be converted
*/
.syntax unified
.equ division, 0x66666667 // 1717986919; (2 ^ 34 + 6) / 10
.section .text
.global _start
_start:
push {ip}
mov r1, #0x0a // 10; newline
push {r1}
mov r7, #0x04 // write syscall
/*
If your architecture is ARMv7 (or above).
movw r3, #:lower16:division // 26215
movt r3, #:upper16:division // 26214
*/
ldr r3, =division
mov r0, #(0x01 << 0x1e) // replace this
_division:
smmul r1, r0, r3
asr r2, r1, #0x02
_modulo:
add r1, r2, r1, lsr #0x1f // 31
add r1, r1, r1, lsl #0x02
sub r0, r0, r1, lsl #0x01
_string:
add r0, #0x30 // 48; '0'
push {r0}
_shift:
mov r0, r2
cmp r0, #0x00
bne _division
_write:
mov r1, sp
ldr r3, [r1]
cmp r3, #0x00
beq _end
mov r0, #0x01 // stdout file descriptor
pop {ip}
mov r2, #0x01 // length
swi 0x00 // execute syscall
bne _write
_end:
pop {ip}
mov r7, #0x01 // exit syscall
mov r0, #0x00 // exit status
swi 0x00 // execute syscall
Github(更多最新): https://raw.githubusercontent.com/GrpeApple/Assembly/test/ARM/src/arm/int2str.S
如果您希望这是您的依赖项: https://raw.githubusercontent.com/GrpeApple/Assembly/test/ARM/src/deps/int2str.S (使用寄存器r0-r2
)
请参阅为什么 GCC 在实现 integer 除法时使用乘以一个奇怪的数字? smmul
/ asr
技巧比实际的除法指令更有效地除以 10。
您使用模数和除法分别获得最后一个 integer 和倒数第二个 integer。 您使用除法检查直到零。
它添加 '0' 的 ascii 值。 我还包括在 ARMv7 的评论中。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.