带有非内联汇编的Qt C ++项目

时间:2012-03-15 20:40:25

标签: qt assembly qt-creator qmake

我使用的是Windows XP,最新的Qt Creator和QtSDK以及内置的gcc编译器。

问题是,如何在C ++ Qt项目中使用完整程序集。 我知道如何使用内联汇编,但我不知道如何在Qt C ++项目中进行非内联(在单独的.asm文件中编写)完整程序集。

Qt C ++项目是否可以实现,如果是这样,怎么做?

编辑:

* 专业档案

TEMPLATE = app
CONFIG += console
CONFIG -= qt

SOURCES += \
    calc.S

calc.S

section .data
        hello: db 'Hello world!', 10
        helloLen: equ $-hello

section .text
        global _start

_start:
        mov eax, 4
        mov ebx, 1
        mov ecx, hello
        mov edx, helloLen
        int 80h

proexit:
        mov eax, 1
        mov ebx, 0
        int 80h

编译错误

..\plain_cpp\calc.S: Assembler messages:
..\plain_cpp\calc.S:1: Error: no such instruction: `section .data'
..\plain_cpp\calc.S:2: Error: no such instruction: `db 72ello world!4410'
..\plain_cpp\calc.S:3: Error: no such instruction: `equ $-hello'
..\plain_cpp\calc.S:5: Error: no such instruction: `section .text'
..\plain_cpp\calc.S:6: Error: no such instruction: `global _start'
..\plain_cpp\calc.S:9: Error: too many memory references for `mov'
..\plain_cpp\calc.S:10: Error: too many memory references for `mov'
..\plain_cpp\calc.S:11: Error: too many memory references for `mov'
..\plain_cpp\calc.S:12: Error: too many memory references for `mov'
..\plain_cpp\calc.S:13: Error: junk `h' after expression
..\plain_cpp\calc.S:13: Error: suffix or operands invalid for `int'
..\plain_cpp\calc.S:16: Error: too many memory references for `mov'
..\plain_cpp\calc.S:17: Error: too many memory references for `mov'
..\plain_cpp\calc.S:18: Error: junk `h' after expression
..\plain_cpp\calc.S:18: Error: suffix or operands invalid for `int'

编辑2 - AT& T样式

PRO档案

TEMPLATE = app
CONFIG += console
CONFIG -= qt

SOURCES += \
    calc.S

calc.S

.data
hello:
    .string "Hello World\n"

.globl  main
main:
    movl $4, %eax
    movl $1, %ebx
    movl $hello,%ecx
    movl $12,%edx
    int $0x80

    ret

错误

undefined reference to `WinMain@16'
collect2: ld returned 1 exit status

3 个答案:

答案 0 :(得分:2)

虽然 @karlphillip 方法一般都是正确的,但你应该记住一些指定窗口的东西:

  1. 编译 @karlphillip 的代码时,会出现MinGw标准库文件产生的链接器错误:

    c:/mingw/bin/../lib/gcc/mingw32/4.6.1/../../../libmingw32.a(main.o): In function `main':
    C:\MinGW\msys\1.0\src\mingwrt/../mingw/main.c:73: undefined reference to `WinMain@16'
    

    那不是你的main,而是libmingw32.a的主要内容。它希望WinMain作为您的代码的入口点。问题是WinMain是Microsoft定义的Windows应用程序的默认入口点。 libmingw32.a定义了从实际入口点调用的实际main。那个主要做了一些事情而不是叫WinMain。但显然你没有定义WinMain

    在这个简单的例子中,你实际上不需要标准库,那么你可以删除标准库并使用命令行编译上面的代码

    gcc -Wl,-subsystem,console 1.S -nostdlib
    

    它应该等同于Qt设置QMAKE_CXXFLAGS+=-nostdlib

    然后上面的代码编译,并且...... segfaults 。然后转到第2点:

  2. int 80h是特定的linux系统调用。似乎它在Windows上不起作用。您应该在Windows上调用WriteConsole以写入stdin。但作为“概念证明”,您可以运行以下代码:

    .text
    .globl  main
    main:
        movl $1, %eax
    ret
    

    这会将程序的退出代码设置为1.

  3. 修改 如果你想要包含标准库的 Hello world 示例,你可以试试这个:

    .data
    hello:
        .string "Hello World\n"
    
    .text
    .global _WinMain@16
    _WinMain@16:
        push $hello
        call _puts
        add $4, %esp
    
        ret
    

    使用gcc 1.S

    进行编译

答案 1 :(得分:1)

我建议你阅读this tutorial来正确设置Qt Creator进行组装。

修改

您的问题是 qmake 会调用 gcc 来编译汇编代码,而您正在使用 Intel语法。您需要转换汇编代码以使用AT& T语法

<强> calc.S

.data
hello:
    .string "Hello World\n"

.globl  main
main:
    movl $4, %eax
    movl $1, %ebx
    movl $hello,%ecx
    movl $12,%edx
    int $0x80

    ret

<强> calc.pro

TEMPLATE = app
CONFIG += console
CONFIG -= qt

SOURCES += \
    calc.S

将这两个文件粘贴到同一目录中,然后执行qmake,然后执行make

<强>输出:

$ ./calc 
Hello World

答案 2 :(得分:0)

您是否在* .pro文件中尝试了SOURCES += yourfile.asm