制作玩具unix os:ld问题

gid*_*eon 3 compiling

因此,我正在关注有关推出您自己的玩具 unix 的教程。

我一直在编译此页面上的示例源代码。这是示例源代码的下载链接

Makefile 看起来像这样:

SOURCES=boot.o main.o
CC=gcc
CFLAGS=-nostdlib -nostdinc -fno-builtin -fno-stack-protector
LDFLAGS=-Tlink.ld
ASFLAGS=-felf

all: $(SOURCES) link
clean:
    -rm *.o kernel
link:
    ld $(LDFLAGS) -o kernel $(SOURCES)
.s.o:
    nasm $(ASFLAGS) $<
Run Code Online (Sandbox Code Playgroud)

在 OSX 上我无法做到,make因为Apple 的 ld不支持-T开关。我尝试在 CentOS 上编译,我得到了这个:

[gideon@centosbox src]$ make 
nasm -felf boot.s
cc -nostdlib -nostdinc -fno-builtin -fno-stack-protector   -c -o main.o main.c
main.c:4: warning: 'struct multiboot' declared inside parameter list
main.c:4: warning: its scope is only this definition or declaration, which is probably not what you want
ld -Tlink.ld -o kernel boot.o main.o
boot.o: could not read symbols: File in wrong format
make: *** [link] Error 1
Run Code Online (Sandbox Code Playgroud)

当然我唯一的问题是 File in wrong format.

这是什么意思?我该如何纠正?

slm*_*slm 5

这些听起来像是在为不同的架构混合代码。请参阅此处:无法读取符号,文件格式错误

摘抄

当您更改架构时,您会收到该错误。那些 CHOST/CFLAGS 设置是新的吗?

问题

  • 我想知道 Toy Unix OS 是否只能构建在 x86 而不是 x64 上。有什么要看的。
  • make clean. 您在 CentOS 上使用的文件是否以任何方式来自 OSX?
  • 我看到boot.o正在使用但没有看到它被编译,除非nasm -felf boot.s构建它,所以也许它是这个文件的 OSX 版本。

修复

如果您查看选项,nasm您会注意到它正在使用开关:

$ nasm -felf boot.s
Run Code Online (Sandbox Code Playgroud)

elf格式是一个32位的格式。在 64 位的较新系统上,您需要将其更改为elf64. 您可以使用以下nasm -hf选项查看这些格式:

$ nasm -hf
...
valid output formats for -f are (`*' denotes default):
  * bin       flat-form binary files (e.g. DOS .COM, .SYS)
    ith       Intel hex
    srec      Motorola S-records
    aout      Linux a.out object files
    aoutb     NetBSD/FreeBSD a.out object files
    coff      COFF (i386) object files (e.g. DJGPP for DOS)
    elf32     ELF32 (i386) object files (e.g. Linux)
    elf64     ELF64 (x86_64) object files (e.g. Linux)
    as86      Linux as86 (bin86 version 0.3) object files
...
Run Code Online (Sandbox Code Playgroud)

所以在 Make 文件中更改这一行:

ASFLAGS=-felf64
Run Code Online (Sandbox Code Playgroud)

并重新运行make

$ make
ld -Tlink.ld -o kernel boot.o main.o
$
Run Code Online (Sandbox Code Playgroud)

解决了这个问题。