使用MSVC工具生成裸机二进制文件的过程是什么
在GNU领域,cc
编译或as
将源汇编成对象文件,ld
将对象文件链接到ELF(使用链接器脚本(,然后objcopy
将ELF中的相关部分作为";固件二进制";。我想做同样的事情,但只使用微软风投提供的工具。
我一直在用以下ARM64startup.s
:进行测试
AREA .text, CODE, READONLY
start
LDR w1, =0xDEADBEEF
B .
END
假设这只是用0xDEADBEEF加载X1寄存器的低32位,然后旋转。组装我运行的代码:
armasm64.exe startup.s
我猜想,如果我有一个peripherals.c
源文件,我需要将startup.s
和peripherals.c
链接到一个可执行文件(COFF?,PE?(中。最后,我需要去掉任何COFF/PE头,这样ARM MCU就可以在加载时执行代码。
免责声明:我不在我的专业领域内,在阅读了一些微软文档后,以及在提出问题三天后,我提出了一个基于我使用MSVC工具进行的一些测试的答案,但还没有提出答案。我希望这个答案能引发更多知情的答案,这样我就可以很高兴地收回它
问题的答案";使用MSVC工具生成裸金属二进制文件的过程是什么"可能是:";没有";。
aarch64-pe.asm
:
AREA .text, CODE, READONLY
EXPORT start
start
LDR w1, =0xDEADBEEF
B .
END
(符号"start"需要使用EXPORT
指令公开,以便由链接器解析(。
组装:
armasm64.exe aarch64-pe.asm
现在,例如,aarch64(版本14.28.29334.0(的链接器只支持有限的目标子系统列表:
BOOT_APPLICATION,
CONSOLE,
WINDOWS,
NATIVE,
POSIX,
EFI_APPLICATION, EFI_BOOT_SERVICE_DRIVER, EFI_ROM, EFI_RUNTIME_DRIVER
从Microsoft和EFI文档来看,似乎所有这些子系统都需要一个能够理解PECOFF
格式的加载程序,或者在BOOT_APPLICATION
子系统的情况下能够运行到BCD WMI Provider
环境中。
不存在所谓的";BAREMETAL";子系统。当尝试使用0x0000000040000000
作为基地址链接除EFI_ROM
以外的每个子系统的aarch64-pe.obj时,链接器退出,显示相同的错误,抱怨起始地址不能小于4GiB:
D:optmsvcarm64>for %I in (BOOT_APPLICATION CONSOLE WINDOWS NATIVE POSIX EFI_APPLICATION EFI_BOOT_SERVICE_DRIVER EFI_ROM EFI_RUNTIME_DRIVER) do link /entry:start /BASE:0x0000000040000000 /subsystem:%I aarch64-pe.obj
D:optmsvcarm64>link /entry:start /BASE:0x0000000040000000 /subsystem:BOOT_APPLICATION aarch64-pe.obj
Microsoft (R) Incremental Linker Version 14.28.29334.0
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : fatal error LNK1355: invalid base address 0x40000000; ARM64 image cannot have base address below 4GB
D:optmsvcarm64>link /entry:start /BASE:0x0000000040000000 /subsystem:CONSOLE aarch64-pe.obj
Microsoft (R) Incremental Linker Version 14.28.29334.0
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : fatal error LNK1355: invalid base address 0x40000000; ARM64 image cannot have base address below 4GB
D:optmsvcarm64>link /entry:start /BASE:0x0000000040000000 /subsystem:WINDOWS aarch64-pe.obj
Microsoft (R) Incremental Linker Version 14.28.29334.0
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : fatal error LNK1355: invalid base address 0x40000000; ARM64 image cannot have base address below 4GB
D:optmsvcarm64>link /entry:start /BASE:0x0000000040000000 /subsystem:NATIVE aarch64-pe.obj
Microsoft (R) Incremental Linker Version 14.28.29334.0
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : fatal error LNK1355: invalid base address 0x40000000; ARM64 image cannot have base address below 4GB
D:optmsvcarm64>link /entry:start /BASE:0x0000000040000000 /subsystem:POSIX aarch64-pe.obj
Microsoft (R) Incremental Linker Version 14.28.29334.0
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : fatal error LNK1355: invalid base address 0x40000000; ARM64 image cannot have base address below 4GB
D:optmsvcarm64>link /entry:start /BASE:0x0000000040000000 /subsystem:EFI_APPLICATION aarch64-pe.obj
Microsoft (R) Incremental Linker Version 14.28.29334.0
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : fatal error LNK1355: invalid base address 0x40000000; ARM64 image cannot have base address below 4GB
D:optmsvcarm64>link /entry:start /BASE:0x0000000040000000 /subsystem:EFI_BOOT_SERVICE_DRIVER aarch64-pe.obj
Microsoft (R) Incremental Linker Version 14.28.29334.0
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : fatal error LNK1355: invalid base address 0x40000000; ARM64 image cannot have base address below 4GB
D:optmsvcarm64>link /entry:start /BASE:0x0000000040000000 /subsystem:EFI_ROM aarch64-pe.obj
Microsoft (R) Incremental Linker Version 14.28.29334.0
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : warning LNK4075: ignoring '/BASE' due to '/SUBSYSTEM:EFI_ROM' specification
D:optmsvcarm64>link /entry:start /BASE:0x0000000040000000 /subsystem:EFI_RUNTIME_DRIVER aarch64-pe.obj
Microsoft (R) Incremental Linker Version 14.28.29334.0
Copyright (C) Microsoft Corporation. All rights reserved.
LINK : fatal error LNK1355: invalid base address 0x40000000; ARM64 image cannot have base address below 4GB
这可能是裸金属嵌入式系统的问题,或者这可能需要MMU可用并且已经由。。。裸机程序以MMU从小于4GiB的起始地址禁用开始。
当针对aarch64-pe.efi运行dumpbin.exe
时,由于ldr
指令位于0x0000000180001000
,并且文件类型设置为DLL
,所以基址似乎设置为0000000180000000
。
dumpbin.exe /disasm aarch64-pe.efi
File Type: DLL
0000000180001000: 18000041 ldr w1,0000000180001008
0000000180001004: 14000000 b 0000000180001004
0000000180001008: DEADBEEF
Summary
1000 .rdata
1000 .text
当对以0x0000000100000000
为基地址的链接器生成的可执行文件执行dumpbin.exe
时,文件类型一致为EXECUTABLE IMAGE
。
更重要的是,dumpbin.exe
似乎也不提供将生成的可执行文件转换为标准格式,如s-record
或intel hex
。
因此,我的结论是,MSVC工具本身暂时不允许构建aarch64裸金属应用程序。