Right now, all targets require the use of GCC 7.5.x as the linker, which is suboptimal for everyone not using Ubuntu 18.04 LTS. This was done because we need to test the exact linker version customers will use for qualification, and we had to pick one.
The solution we should move towards is using the LLD bundled with Ferrocene as the linker. This means updating the target specs, updating the self-testing tool to check for the right linker, and updating the target documentation.
For bare metal targets, this is as simple as changing the linker, as LLD can work with them by default (and that's actually upstream's behavior, we had to override it). Then the self-test tool can be updated to verify the presence of LLD (the code should already be there, just an enum change should be needed).
For Linux targets though we cannot invoke LLD directly, as LLD does not know where the system libraries are located. Thus, we need to use the system GCC or clang as the default linker, passing -fuse-ld=lld to it. That flag seems to work from GCC 9 onwards. This requires wider changes:
- Change the target spec to always use LLD.
- Change the self-testing tool to check for the presence of LLD, and the system linker (either gcc or clang).
- Add a new check in the self-test tool, that when compiling something, GCC or clang end up invoking LLD with the correct flags. This can be implemented by creating a fake LLD binary that checks the flags are correct: GCC/clang can then be invoked with some flags pointing to the fake LLD, which will error out if the flags are not passed through and the system flags are not present.
- In the safety manual, add a requirement for how GCC/clang should behave, and mention the self-test tool performs that check automatically.
Right now, all targets require the use of GCC 7.5.x as the linker, which is suboptimal for everyone not using Ubuntu 18.04 LTS. This was done because we need to test the exact linker version customers will use for qualification, and we had to pick one.
The solution we should move towards is using the LLD bundled with Ferrocene as the linker. This means updating the target specs, updating the self-testing tool to check for the right linker, and updating the target documentation.
For bare metal targets, this is as simple as changing the linker, as LLD can work with them by default (and that's actually upstream's behavior, we had to override it). Then the self-test tool can be updated to verify the presence of LLD (the code should already be there, just an enum change should be needed).
For Linux targets though we cannot invoke LLD directly, as LLD does not know where the system libraries are located. Thus, we need to use the system GCC or clang as the default linker, passing
-fuse-ld=lldto it. That flag seems to work from GCC 9 onwards. This requires wider changes: