如何将Windows通用CRT链接到使用nasm编译的obj文件 [英] How to link Windows universal CRT to obj file compiled with nasm
问题描述
环境:Windows10.我碰巧正在使用MinGW版本的 ld
进行链接,但是如果使用Visual Studio link.exe
,我很高兴.使事情变得更简单.
Environment: Windows 10. I happen to be using a MinGW version of ld
for linking, but I'm happy to use the visual studio link.exe
if it makes things simpler.
我在nasm中有以下基本程序:
I have the following basic program in nasm:
global _main
extern _printf
section .text
_main:
push message
call _printf
add esp, 4
ret
message:
db 'Hello, World', 10, 0
它可以使用
nasm -f win32 test.nasm
当尝试将其链接到Windows CRT(ucrt.lib)时,出现以下错误:
When trying to link it to the windows CRT (ucrt.lib), I get the following error:
$ ld -o test.exe test.obj
test.obj:test.nasm:(.text+0x6): undefined reference to `printf'
好,所以我需要将链接器指向ucrt库:
Ok, so I need to point the linker at the ucrt library:
$ ld -o test.exe /c/Program\ Files\ \(x86\)/Windows\
Kits/10/Lib/10.0.14393.0/ucrt/x86/ucrt.lib test.obj
test.obj:test.nasm:(.text+0x6): undefined reference to `printf'
尝试使用Visual Studio链接器进行等效操作:
Trying the equivalent with the visual studio linker:
d:\Code\nasm>link -out:test.exe -entry:main -subsystem:console test.obj
Microsoft (R) Incremental Linker Version 14.10.25017.0
Copyright (C) Microsoft Corporation. All rights reserved.
test.obj : error LNK2001: unresolved external symbol _printf
test.exe : fatal error LNK1120: 1 unresolved externals
这引起了两个问题:
-
为什么其中一个试图找到
printf
,而另一个试图找到_printf
?我知道有一个下划线约定,但似乎两个链接器都不理解.
Why does one of these try to find
printf
and the other,_printf
? I get that there's an underscore convention, but it doesn't seem to be understood by both linkers.
我使用了 objdump -t
来查看ucrt.lib文件中的符号.我不会粘贴整个列表,但其中包含以下条目:
I used objdump -t
to look at the symbols in the ucrt.lib file. I won't paste the entire list, but it contains entries such as:
[4](秒1)(fl 0x00)(ty 0)(scl 2)(nx 0)0x00000000 __imp ____ conio_common_vcprintf
[5](秒3)(fl 0x00)(ty 0)(scl 2)(nx 0)0x00000000 ___ conio_common_vcprintf
[4](秒1)(fl 0x00)(ty 0)(scl 2)(nx 0)0x00000000 __imp ____ conio_common_vcprintf_p
printf
和 _printf
都没有出现在列表中.这是否意味着该库未导出该文件?如果没有,我应该链接哪个库?
Neither printf
nor _printf
appears in the list. Does this mean it's not exported by that library? If not, which library should I be linking?
根据这篇MS文章, ucrt.lib
是c运行时和C标准库的事实上的库.
According to this MS article, ucrt.lib
is the de-facto library for the c runtime and C standard library.
推荐答案
感谢Michael Petch的评论,看来我需要手动链接1个或更多与完全不同位置的额外lib.ucrt.lib
库.printf 的相关文件是 legacy_stdio_definitions.lib
,我在 VS2017 安装目录的一个子目录深处找到了它,而不是 ucrt.lib
Windows SDK安装目录.
Thanks to a comment from Michael Petch, it looks like I need to manually link 1 or more extra libs which are in a completely separate location from the ucrt.lib
library. The relevant one for printf is legacy_stdio_definitions.lib
, which I found deep in a sub-dir of my VS2017 install directory, as opposed to the ucrt.lib
which is in the Windows SDK install directory.
printf
的定义是在 stdio.h
中内联提供的,除非定义了宏 _NO_CRT_STDIO_INLINE
,我想通常是在构建时在VS工具链中.
The definition of printf
is provided inline in stdio.h
unless the macro _NO_CRT_STDIO_INLINE
is defined, which I guess it usually is when building inside the VS toolchain.
这篇关于如何将Windows通用CRT链接到使用nasm编译的obj文件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!