Extending SDK
After Porting LLVM-MOS to a platform, please consider submitting your port for inclusion in the LLVM-MOS SDK. We'd like the SDK to be a nice out-of-the-box way to write code for any 6502 platform, and contributions along those lines are greatly appreciated.
This guide follows the Porting Guide above; make sure you've at least skimmed it before continuing, otherwise this guide likely won't make as much sense.
Review[edit | edit source]
Completing the porting guide produced the following artifacts:
A linker script, link.ld
:
MEMORY {
ram : ORIGIN = 0x0000, LENGTH = 0x10000
user_ram (rw) : ORIGIN = 0x0200, LENGTH = 0xfe00
}
SECTIONS { INCLUDE c.ld }
__rc0 = 0x00;
INCLUDE imag-regs.ld
ASSERT(__rc0 == 0x00, "Inconsistent zero page map.")
ASSERT(__rc31 == 0x1f, "Inconsistent zero page map.")
/* Top of stack would be 0x10000, but wrap around. */
__stack = 0
OUTPUT_FORMAT { FULL(ram) SHORT(_start) }
A command line to build a binary:
mos-common-clang -o main -Os main.c -lexit-loop -linit-stack
This is enough to set up a freestanding platform in the SDK.
CMake[edit | edit source]
As mentioned previously, our SDK uses CMake to build. If you haven't done so already, check out and build the SDK sources using CMake.
Let's call our platform xyzzy
, for old times' sake. Make a xyzzy
subdirectory under the mos-platform directory for the platform to live in. Tell CMake that the new directory exists by adding add_subdirectory(xyzzy)
to mos-platform/CMakeLists.txt. This will cause CMake to look for a CMakeLists.txt
file in the xyzzy
subdirectory, which will tell it how to build the xyzzy
platform.
Platform Definition[edit | edit source]
A minimal platform CMakeLists.txt
for xyzzy
is just platform(xyzzy)
. Building and installing the SDK afterwards will then produce a mos-xyzzy-clang
symlink that tells Clang to use the platform.
This produces an incomplete target with nothing in it. Our target should be complete though; it should be possible to produce binaries from it. So we can tell CMake that by using platform(xyzzy COMPLETE)
.
This will cause CMake to link for a link.ld
file in the xyzzy
subdirectory. Placing the link.ld
file there allows the build and install to succeed and causes mos-xyzzy-clang
to automatically use that linker script.
This still doesn't allow producing binaries though; the command line used for this was mos-common-clang
, not mos-clang
. Since the xyzzy
platform is based off of the common
platform, we need to change the platform definition to platform(xyzzy COMPLETE PARENT common)
. With this, mos-xyzzy-clang
can produce executables.
Platform Libraries[edit | edit source]
There's one remaining part of the command line to deal with: -lexit-loop and -linit-stack
. These libraries need to be included in the platform libraries for xyzzy
.
For each platform, the Clang driver expects the following files to be available to the linker:
File | Description |
---|---|
link.ld
|
Linker Script |
crt0.o
|
Mandatory entry/exit functionality |
libcrt0.a
|
Optional entry/exit functionality |
libcrt.a
|
C runtime |
libc.a
|
C standard library |
link.ld
has already been discussed. crt0.o
and libcrt0.a
contain routines used at the beginning and end of a program. libcrt0.a
contains functionality that may or may not be included, depending on what symbols are referenced in the program, while crt0.o
contains the essential scaffolding to start and end a program. libcrt.a
contains routines used to implement compiler functionality like multiplication and division, while libc.a
contains the C standard library and support for some C++ language features.
We can't just include -lexit-loop
and -linit-stack
on the command line; the above files are structured so that compiler flags like -nostartfiles
do what they logically should. So, we need to include libexit-loop.a
and libinit-stack.a
into the appropriate platform library, libcrt0.a
.
To do so, we add to the xyzzy
CMakeLists.txt
:
platform(xyzzy COMPLETE PARENT common)
if(NOT CMAKE_CROSSCOMPILING)
return()
endif()
add_platform_library(xyzzy-crt0)
merge_libraries(xyzzy-crt0
common-crt0
common-init-stack
common-exit-loop
)
The early return just makes sure the following libraries aren't compiled for the host; they're 6502 code, so they need to be compiled with llvm-mos.
The remainder of the code creates a libcrt0.a
for xyzzy
that bundles in the libcrt0.a
, libinit-stack.a
, and libexit-loop.a
libraries from the common
platform. The other libraries bleed through from the common
platform, while the libcrt0.a
for xyzzy
will be used in preference to the one from libcommon
With this, mos-xyzzy-clang
will behave like to the original command line, and the platform is now fully incorporated into the SDK.