OSDev.org

The Place to Start for Operating System Developers
It is currently Thu Mar 28, 2024 2:32 am

All times are UTC - 6 hours




Post new topic Reply to topic  [ 14 posts ] 
Author Message
 Post subject: BOOTBOOT Font Linking problem
PostPosted: Fri Jul 02, 2021 3:29 pm 
Offline

Joined: Thu Jul 01, 2021 3:24 pm
Posts: 16
I distributed the example kernel's files (kernel.cpp, bootboot.h, font.psf) across my directory structure (src, lib, Fonts) and tried to compile them. However, when it tries to link the kernel.o and the font.o, it gives me an error saying reference to "binary font psf start" is undefined. I am using the exact same commands as given in the example kernel, and they worked when the directory structure was the same as that provided on Gitlab. My question is, does the directory structure affect the linking with the font binary object file? If not, what could be the possible problem?


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Fri Jul 02, 2021 4:22 pm 
Offline
Member
Member

Joined: Tue Feb 18, 2020 3:29 pm
Posts: 1071
What objdump say about your font file? Have you ran objcopy to turn it into an ELF?

_________________
"How did you do this?"
"It's very simple — you read the protocol and write the code." - Bill Joy
Projects: NexNix | libnex | nnpkg


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Fri Jul 02, 2021 4:34 pm 
Offline
Member
Member

Joined: Mon Mar 25, 2013 7:01 pm
Posts: 5099
LyricalRain wrote:
does the directory structure affect the linking with the font binary object file?

No.

LyricalRain wrote:
If not, what could be the possible problem?

Maybe you made a mistake when you updated the paths in the makefile. Are there any other errors?


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Fri Jul 02, 2021 10:30 pm 
Offline

Joined: Mon Nov 02, 2020 4:53 pm
Posts: 20
with objcopy, the name of the exported symbol changes depending on where the file is located. it's kinda annoying. to figure out what it is for your file, do `nm font.o` and replace the symbol name in your code with the correct one that nm outputs


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Fri Jul 02, 2021 10:33 pm 
Offline

Joined: Mon Nov 02, 2020 4:53 pm
Posts: 20
Octocontrabass wrote:
LyricalRain wrote:
does the directory structure affect the linking with the font binary object file?

No.


Yes.


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Fri Jul 02, 2021 11:25 pm 
Offline
Member
Member
User avatar

Joined: Thu Oct 13, 2016 4:55 pm
Posts: 1584
monarrk wrote:
Octocontrabass wrote:
LyricalRain wrote:
does the directory structure affect the linking with the font binary object file?
No.
Yes.
Yes, it does change the variable's name unfortunately.
monarrk wrote:
with objcopy, the name of the exported symbol changes depending on where the file is located. it's kinda annoying. to figure out what it is for your file, do `nm font.o` and replace the symbol name in your code with the correct one that nm outputs
Exactly. FYI my Makefile uses ld, not objcopy, but the same.

To solve the issue, you have several options:
1. you can adjust the variable name
2. in your Makefile, you can switch directories temporarily, so that you always run "ld -b binary" (or "objcopy") in the current working directory, hence removing the path from the variable's name
3. in your Makefile, copy the file and then delete the copy (this is what I do for example here)
4. convert the binary into a C byte array (for example I do this here)

The advantage of "ld -r -b binary" (or "objcopy") is that it is fast.
The disadvantage is that path matters and it is not fully portable, doesn't work on MacOS for example and LLVM toolchain doesn't have "objcopy" (or at least it didn't had, maybe they have added it since I've last checked).

That's why I've created bin2h.c. The advantage is 100% portability, "ld" compatibility doesn't matter, no additional tool required (like "objcopy").
The disadvantage is that generating a byte array and then compiling it into binary is slower than just converting a binary into ELF (you won't notice this for a small file like a font, but for example with mkbootimg which has several megabytes of firmware files too it is noticeable). Further advantage is that you can also add compression to it if you want, I do that with mkbootimg for example.
Another version of bin2h.c can be found here. This version uses stb's compressor, and it also can convert entire directories into byte arrays recursively.

Cheers,
bzt


Last edited by bzt on Fri Jul 02, 2021 11:31 pm, edited 1 time in total.

Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Fri Jul 02, 2021 11:29 pm 
Offline
Member
Member

Joined: Mon Mar 25, 2013 7:01 pm
Posts: 5099
bzt wrote:

Wouldn't it be easier (and faster) to use the incbin directive in an assembly file instead of an array in a C header?


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Fri Jul 02, 2021 11:44 pm 
Offline
Member
Member
User avatar

Joined: Thu Oct 13, 2016 4:55 pm
Posts: 1584
Octocontrabass wrote:
bzt wrote:

Wouldn't it be easier (and faster) to use the incbin directive in an assembly file instead of an array in a C header?
No, not for me. Assembly isn't portable and not all compilers support inline Assembly. Adding a new language to the mix is not easier, and that's something that I deliberately wanted to avoid as it requires an additional tool in the toolchain (but I couldn't avoid it entirely with Go, because Go is a shitty, particularly badly designed language).
Right now all the mykernel examples (save Go) are only using their main language nothing else (and with Go I managed to shrink the Assembly to a single "ret" instruction which is luckily portable :-)).

But of course the OP might consider incbin, because in a real kernel you can't escape the Assembly dependency, and if so, they could just as well use it.

EDIT: here's a good collection of embedding options. It mentions using winres too that we haven't considered so far (but that only works with PE format).

Cheers,
bzt


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Sat Jul 03, 2021 12:13 am 
Offline

Joined: Thu Jul 01, 2021 3:24 pm
Posts: 16
Thank you for your replies! I thought the directory thing must be it but I couldn't pinpoint the error.


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Sat Jul 03, 2021 1:45 am 
Offline
Member
Member

Joined: Wed Aug 30, 2017 8:24 am
Posts: 1593
bzt wrote:
No, not for me. Assembly isn't portable and not all compilers support inline Assembly.
Normally not, but in this case:
Code:
.section ".rodata",  "a", @progbits
.global font_start
.type font_start, @object
font_start:
.incbin "font.psf"
.global font_end
.type font_end, @object
font_end:
That should work for all ELF architectures. For PE the section name would be ".rdata", which you can abstract with a preprocessor directive, as necessary. Also, name mangling can be added as necessary (which I think was only needed for 32-bit Windows, but I'm not sure about 64-bit Windows). Since the file contains no architecture specific code, any version of GNU as should be able to compile this, no matter the target architecture, and probably also some other assemblers. The C interface is "extern const char font_start[], font_end[]".

And if you need to support MSVC, the only major C compiler to not use a GNU as compatible assembler, then just add a second version for MSVC. I'm sure it also has something like "incbin". Sometimes portability is just having a version for every supported possibility.

_________________
Carpe diem!


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Sat Jul 03, 2021 7:44 am 
Offline
Member
Member
User avatar

Joined: Thu Oct 13, 2016 4:55 pm
Posts: 1584
nullplan wrote:
Code:
.section ".rodata",  "a", @progbits
.global font_start
.type font_start, @object
font_start:
.incbin "font.psf"
.global font_end
.type font_end, @object
font_end:
That should work for all ELF architectures.
I seriously doubt that the FreePascal or the Rust compiler for example can do anything with this code... (Pascal uses a different inline asm syntax, and Rust for example doesn't really support global labels in inline asm).
As I've said, it was an important goal to only use the main language with its compiler, but nothing else, which means no additional tools nor assemblers. This is why Assembly is out of question for the mykernel examples (in a real kernel project, where an assembler is a must have sure, you can use "incbin" too, or "file" or "bininc" or whatever syntax your chosen assembler supports).

nullplan wrote:
For PE the section name would be ".rdata", which you can abstract with a preprocessor directive, as necessary.
Unlike C, Pascal and Ada, for example the Go compiler doesn't have a preprocessor at all. (And it can't import variables from another object file, just functions with a very overcomplicated way, btw. so even if you compile this with an assembler, there's no way to access the included data from Go. FYI, ld and objconv doesn't work either with Go, I had to use the bin2h way, furthermore, Go can't store initialized static byte arrays, so I had to use a string constant... Ugly and dirty workaround. You have probably figured that out, my dislike towards Go is because I had the most issues and trouble with that port. That's a shitty, not a well-tough language which required the most workarounds by far. Oh, and the official compiler doesn't work for bare metal, not even their own tutorials compile with that, you _must_ use the GNU compiler, gccgo.)

nullplan wrote:
Since the file contains no architecture specific code, any version of GNU as should be able to compile this, no matter the target architecture, and probably also some other assemblers. The C interface is "extern const char font_start[], font_end[]".
ld does exactly the same, but needs no additional assembler to achieve that goal. First, doesn't matter what language you use, you'll need the linker anyway, you can't leave that out; second, it creates the object no matter the target architecture. So, why not use the tool that we already have?

nullplan wrote:
And if you need to support MSVC
I don't think MSVC can compile Pascal, Ada or Go for example. The GNU compiler can. (That put aside, I do support MSVC C/C++ for kernels, the bootboot.h is written carefully in a way to support the messed up MSVC pragma syntax too, but I don't provide a mykernel example for that compiler.)

Cheers,
bzt


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Sat Jul 03, 2021 12:17 pm 
Offline
Member
Member

Joined: Mon Mar 25, 2013 7:01 pm
Posts: 5099
bzt wrote:
FreePascal

The FreePascal compiler uses gas as its assembler, which means it's not an additional tool.

bzt wrote:
inline asm

I don't think anyone is suggesting using inline assembly.

bzt wrote:
ld does exactly the same, but needs no additional assembler to achieve that goal. First, doesn't matter what language you use, you'll need the linker anyway, you can't leave that out; second, it creates the object no matter the target architecture. So, why not use the tool that we already have?

But ld and gas are both part of binutils. If you have one, you have both.


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Sun Jul 04, 2021 10:01 am 
Offline
Member
Member
User avatar

Joined: Thu Oct 13, 2016 4:55 pm
Posts: 1584
Octocontrabass wrote:
I don't think anyone is suggesting using inline assembly.
Yes, because you've failed to understand the main goal. I repeat it for the third time: only one kind of language source files per directory allowed. In pas: only pascal sources. In ada: only ada sources. In cpp: only C++ sources. Hence only inline asm can be considered at best. Having a separate Assembly file is out of question because it goes against the main goal. And yes, I've failed to fulfill this goal with Go (but I could mitigate it to a common Assembly file for all platforms), and yes, your project might have a different goal than my mykernel examples.

Octocontrabass wrote:
But ld and gas are both part of binutils. If you have one, you have both.
I've never said binutils is a dependency. I only said "A linker". That could be Gold ld or LLVM lld too, those are command line compatible with GNU ld (mostly). With the C and C++ examples, you should be able to use ANY compiler, and ANY linker, there's absolutely nothing GNU specific in the code or in the linker scripts (and bootboot.h is written with ifdef guards to support MSVC too). The failure with Go and depending on gccgo is no reason to limit the other languages to GNU too. (Admittedly I only provide Makefiles for that, simply because I don't have the capacity to support all possible compilers. But contributions are welcome any time ;-) If you have a working vcproj for mykernel, open a PR, and I can promise I'll add it.)

Cheers,
bzt


Top
 Profile  
 
 Post subject: Re: BOOTBOOT Font Linking problem
PostPosted: Sun Jul 04, 2021 6:08 pm 
Offline
Member
Member

Joined: Sun Jun 23, 2019 5:36 pm
Posts: 618
Location: North Dakota, United States
There's no need to use assembly at all for including binary files in Rust. That's actually a bit overkill and you rarely ever should have to do that. The bootloader I use doesn't even do that for the kernel -- the kernel and bootloader are linked together though. To include binary data in a rust project, use include_bytes!, like so:

Code:
let font_data = include_bytes!("font.bin");

Quite a useful macro, that is.


Top
 Profile  
 
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 14 posts ] 

All times are UTC - 6 hours


Who is online

Users browsing this forum: No registered users and 70 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Search for:
Jump to:  
Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group