安装qemu后是否有运行任何ARM程序集文件(.s)的命令 [英] Is there a command to run any ARM assembly file (.s) after having installed qemu

查看:18
本文介绍了安装qemu后是否有运行任何ARM程序集文件(.s)的命令的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我最近运行了以下命令来安装 qemu.

I have recently run the following commands to install qemu.

sudo apt-get install qemu-user
sudo mkdir -p /opt/arm/10
wget 'https://developer.arm.com/-/media/Files/downloads/gnu-a/10.2-2020.11/binrel/gcc-arm-10.2-2020.11-x86_64-arm-none-linux-gnueabihf.tar.xz?revision=d0b90559-3960-4e4b-9297-7ddbc3e52783&la=en&hash=985078B758BC782BC338DB947347107FBCF8EF6B' -O gcc-arm-10.2-2020.11-x86_64-arm-none-linux-gnueabihf.tar.xz
sudo tar Jxf  gcc-arm-10.2-2020.11-x86_64-arm-none-linux-gnueabihf.tar.xz  -C /opt/arm/10

现在没有了.我想在我的 linux 子系统上编译和执行的 ARM 文件.如果有人可以提供有关此问题的演练,那就太好了.我已经包括了一个不.下面是一些示例文件的链接.我正在寻找能够成功编译和运行所有这些文件的通用命令.就像在 C 中 gcc -o test test.c 将编译和运行任何 C 文件一样.我没有树莓派

Now there are a no. of ARM files i would like to compile and execute on my linux subsystem. It would be great if someone could provide a walkthrough for this issue. I have included a no. of links below to some example files. I am looking for a general command that will successfully compile and run all these files. Just like in C where gcc -o test test.c would compile and run any C file. I do not have a raspberry pi

这里有几个 ARM 程序示例:

Here r a few example ARM programs:

.global _start
_start:
        MOV R1, #X
        MOV R2, #Y
        MOV R3, #Z
        MUL R5, R1, R1
        MUL R6, R2, R2
        ADD R5, R6
        MUL R6, R3, R3
        CMP R5, R6
        BEQ _same
        MOV R4, #0
        B _exit
_same:
        MOV R4, #1
_exit:
        MOV R0,  R4
        MOV R7,  #1
        SWI 0
.data

.global _start
_start:
        LDR R1, =X
        LDR R2, =Y
        LDR R3, =T
        LDR R4, [R1]
        STR R4, [R3]
        LDR R4, [R2]
        STR R4, [R1]
        LDR R4, [R3]
        STR R4, [R2]
_exit:
        MOV R0, #0
        MOV R7, #1
        SWI 0

.data
X: .word 0x16
Y: .word 0x21
T: .word 0x00

@ binary search for V in 25 element array.
        @ returns index for V if V is in the array.
        @ otherwise returns length of array (25).

        .global _start
_start:
        @ populate the array A
        LDR R1,=A
        MOV R2,#0x00
_populate_array:
        CMP R2,#MAX @ i == 25
        BEQ _search
        STR R2,[R1]
        ADD R1,#0x04
        ADD R2,#0x1
        B _populate_array
_search:
        MOV R6, #4      @ R6 == 4 
        MOV R1, #0      @ R1 == left
        MOV R2, #MAX    @ R2 == right
        SUB R2, #1      @ R2 = MAX-1
_loop:
        CMP R1, R2      @ is left>right ?
        BGT _fail

        @ compute new middle position
        ADD R3, R1, R2  @ R3 = left + right
        LSR R3, R3, #1  @ middle = (left + right)/2
        @ each integer element uses 4 bytes of memory
        @ R7 is the memory address for the middle integer value in array A
        MUL R7, R3, R6  @ R7 = middle * 4

        @ obtain middle value at middle position
        LDR R4, =A      @ R4 == &A    (load address of A's 1st byte)
        ADD R4, R7      @ R4 == &A[m] (add offset of m to that address)
        LDR R5, [R4]    @ R5 == A[m]  (get value in A at that address)

        @ compare middle value to searched for value V
        CMP R5, #V      @ V==A[m]?
        BEQ _exit       @ we've found the value V
        BGT _left       @ is V somewhere in left half?
        
        @ if not, V must be somewhere in right half if at all
        MOV R1, R3      @ left = middle
        ADD R1, #1      @ left = left + 1
        B _loop

_left:                  @ A[m]<V (V would be somewhere in left half)
        MOV R2, R3      @ right = middle;
        SUB R2, #1      @ right = right - 1
        B _loop
        
_fail: 
        MOV R3, #MAX
_exit:
        MOV R0, R5
        MOV R7, #1
        SWI 0
.data
.equ MAX, 25
A: .rept MAX
   .word 0
   .endr
.equ V, 17

.global main
main:
    @ Stack the return address (lr) in addition to a dummy register (ip) to
    @ keep the stack 8-byte aligned.
    push    {ip, lr}

    @ Load the argument and perform the call. This is like 'printf("...")' in C.
    ldr     r0, =message
    bl      printf

    @ Exit from 'main'. This is like 'return 0' in C.
    mov     r0, #0    @ Return 0.

    @ Pop the dummy ip to reverse our alignment fix, and pop the original lr
    @ value directly into pc — the Program Counter — to return.
    pop     {ip, pc}

    @ --------------------------------
    @ Data for the printf calls. The GNU assembler's ".asciz" directive
    @ automatically adds a NULL character termination.
message:
    .asciz "Hello, world.\n"

@ Here's how we will use the ARM registers R1-R5:
        @
        @ R1 - address of the next word
        @ R2 - the character counter
        @ R3 - contents of the next word
        @ R4 - next byte
        @ R5 - byte count

        .global _start

        @ program starts here
_start:
        LDR R1, =mystring

        @ initialise the character count (R2) to be 0
        MOV R2,#0

nextw:
        @ load the address of the next word into R3
        LDR R3,[R1]
        @ add 4 to the byte count
        MOV R5, #4

nextb:
        @ load next byte from word into R4
        MOV R4, R3
        @ use bitmask to get next byte value
        AND R4, #MASK
        @ if byte in R4 is 0, then we've found the "end of string" value
        CMP R4, #EOS
        BEQ endl
        @ otherwise, increment the character count by 1
    ADD R2, #1
        @ decrement bytes by 1
        SUB R5, #1
        @ while (bytes !=0) from the slide
        CMP R5, #0
        BEQ incr
        @ shift the contents of the word 8 bits right
        LSR R3, #8
        B nextb

incr:
        @ move to the next word address
        ADD R1,#4
        B nextw

endl:
        @ end of string '0' value found, we're done.
        @
        @ return character count as exit value
        MOV R0, R2
        MOV R7, #1
        SWI 0

.data
.equ MASK, 0x000000ff
.equ EOS, 0
mystring: .asciz "0123456789"

@ try other string examples
@ mystring: .asciz "thunderbirds"

提前谢谢!

推荐答案

你的问题的答案是否定的,因为这取决于你的汇编代码所针对的系统,以及它在做什么(我只是在这里提到它,但实际上并没有 ARM 汇编文件这样的东西,因为这样的文件可能使用不同的指令集,例如 arm/a32,或 thumb2/t32).

The answer to your question is no, because it depends on the system your assembly code was targeting, and on what it is doing (I am just mentioning it here, but there is not really such a thing as an ARM assembly file, since such a file may use different instruction sets, such as arm/a32, or thumb2/t32).

例如,在使用 gcc 的 Linux 系统上编译时,默认情况下假定入口点是 main,而不是 _start - 这就是为什么你的第一个程序有稍作修改 - 您可以使用诸如 meldwinmerge 用于识别修改/未修改版本之间的差异.该程序还必须使用 Linux 系统调用接口,您的所有程序都是如此.请参阅 此处了解更多关于SVC/SWI和Linux系统调用接口的信息.

For example, when compiling on a Linux system with gcc, the entry point is assumed to be main by default, not _start - this is why you first program had to be slightly modified - you could have used a program such as meld or winmerge for identifying the differences between the modified/unmodified versions. The program has to use the Linux system calls interface as well, which is the case of all your programs. See here for more information on SVC/SWI and the Linux system calls interface.

这篇文章 也值得一读,以了解在调用入口点之前发生了什么.

This article is a worth reading as well for understanding what does happen prior to the entry point to be called.

如果你想直接在仿真的 ARM 处理器上执行程序,使用 qemu-system-armarm-none-eabi-gcc 将是解决方案,但我不会推荐它,直到您知识渊博.

And if you wanted to execute programs directly running on an emulated ARM processor, using qemu-system-arm and arm-none-eabi-gcc would be the solution, but I would not recommend it until you will be more knowledgeable.

如果你想熟悉 Windows 上的 ARM 汇编,使用 WSL 和 qemu-arm 是一个很好的解决方案.

If you want to become familiar with ARM assembly on Windows, using WSL and qemu-arm is an excellent solution.

我在这里假设您在提供的示例程序中将 _start 替换为 main.

I am assuming here you replaced _start by main in the example programs you provided.

您的第一个程序甚至无法组装 - 在将其用于问题之前确保它可以组装.

Your first program cannot even be assembled - make sure it does prior to use it in a question.

你的第二个程序使用:

/opt/arm/10/gcc-arm-10.2-2020.11-x86_64-arm-none-linux-gnueabihf/bin/arm-none-linux-gnueabihf-gcc -static -o 2 2.s
 qemu-arm 2

你的第三个程序使用:

/opt/arm/10/gcc-arm-10.2-2020.11-x86_64-arm-none-linux-gnueabihf/bin/arm-none-linux-gnueabihf-gcc -static -o 3 3.s
 qemu-arm 3

你的第四个程序使用:

 /opt/arm/10/gcc-arm-10.2-2020.11-x86_64-arm-none-linux-gnueabihf/bin/arm-none-linux-gnueabihf-gcc -static -o 4 4.s
qemu-arm 4
Hello, world.

你的第五个程序使用:

/opt/arm/10/gcc-arm-10.2-2020.11-x86_64-arm-none-linux-gnueabihf/bin/arm-none-linux-gnueabihf-gcc -static -o 5 5.s
qemu-arm 5

最重要的是,一旦修改,除了第一个需要修复的程序之外,所有程序都使用唯一"命令编译,并使用唯一"命令执行.

Bottom line, once modified, all you programs but the first one, that need to be fixed, were compiled with a 'unique' command, and executed with a 'unique' other one.

您可以通过以下方式稍微简化用于编译/运行程序的命令:

You can somewhat simplify the commands to be used for compiling/running your programs by:

在 WSL 中安装 binfmt-support:

Installing binfmt-support in WSL:

sudo apt-get install binfmt-support

创建一个名为 etc/binfmt.d/qemu-arm.conf 的文件,包含这两行:

Creating a file named etc/binfmt.d/qemu-arm.conf containing those two lines:

# /etc/binfmt.d/qemu-arm.conf                                                                                                                                                                                                                                         
:arm:M::\x7fELF\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x02\x00\x28\x00:\xff\xff\xff\xff\xff\xff\xff\x00\xff\xff\xff\xff\xff\xff\xff\xff\xfe\xff\xff\xff://opt/qemu-4.2.0-static/bin/qemu-arm:OC

这将导致您的系统透明地使用 qemu-arm 来运行您的可执行文件:

This will cause your system to transparently use qemu-arm for running your executable:

qemu-arm 4
Hello, world.

然后可以替换为:

./4
Hello, world.

将 arm-none-linux-gnueabihf 工具链可执行文件的位置添加到您的 PATH.例如,这可以通过将以下行添加到用户主目录中的 .bashrc 文件来完成:

Adding the location for the arm-none-linux-gnueabihf toolchain executables to your PATH. This can be for example be done by adding the following line to the .bashrc file present in your user home directory:

PATH=/opt/arm/10/gcc-arm-10.2-2020.11-x86_64-arm-none-linux-gnueabihf/bin:${PATH}

用于编译的命令可以是:

The command for compiling could then be:

 arm-none-linux-gnueabihf-gcc -static -o 4 4.s

这篇关于安装qemu后是否有运行任何ARM程序集文件(.s)的命令的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆