initial
This commit is contained in:
commit
3eee14d4bd
7
.gitignore
vendored
Normal file
7
.gitignore
vendored
Normal file
@ -0,0 +1,7 @@
|
||||
*.aux
|
||||
*.log
|
||||
*.toc
|
||||
*.out
|
||||
.#*
|
||||
_minted/
|
||||
*.pdf
|
240
book.tex
Normal file
240
book.tex
Normal file
@ -0,0 +1,240 @@
|
||||
\documentclass{report}
|
||||
\usepackage{hyperref}
|
||||
%\usepackage{dirtytalk}
|
||||
\usepackage{scrextend}
|
||||
\usepackage{graphicx}
|
||||
%\usepackage{wrapfig}
|
||||
\usepackage{minted}
|
||||
\usepackage[svgnames]{xcolor}
|
||||
\usepackage[T1]{fontenc}
|
||||
\usepackage{inconsolata}
|
||||
|
||||
\title{Dreamcast from scratch the hard way}
|
||||
\hypersetup{colorlinks=true,urlcolor=blue}
|
||||
|
||||
\begin{document}
|
||||
\maketitle
|
||||
\tableofcontents
|
||||
|
||||
\chapter{Motivation}
|
||||
\begin{listing}[H]
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{C}
|
||||
int main() {
|
||||
printf("hello, world");
|
||||
return 0;
|
||||
}
|
||||
\end{minted}
|
||||
\caption{Example of a listing.}
|
||||
\label{lst:example}
|
||||
\end{listing}
|
||||
|
||||
\chapter{Toolchain}
|
||||
This section shows how to build and install a toolchain for compiling C and C++
|
||||
source code to SH4 (Dreamcast) binaries.
|
||||
|
||||
\section{Toolchain download}
|
||||
|
||||
Download and extract source archives for Binutils and GCC; this could be done for example like this:
|
||||
|
||||
\begin{listing}[H]
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{shell}
|
||||
cd ~
|
||||
|
||||
curl -LO https://ftp.gnu.org/gnu/binutils/binutils-2.45.tar.xz
|
||||
curl -LO https://ftp.gnu.org/gnu/gcc/gcc-15.1.0/gcc-15.1.0.tar.xz
|
||||
|
||||
tar xJf binutils-2.45.tar.xz
|
||||
tar xJf gcc-15.1.0.tar.xz
|
||||
\end{minted}
|
||||
\caption{Toolchain download and extract}
|
||||
\label{lst:toolchain-download-extract}
|
||||
\end{listing}
|
||||
|
||||
\section{Binutils configuration}
|
||||
|
||||
The binutils configuration script is easy to invoke. The only option needed is:
|
||||
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{shell}
|
||||
--target=sh4-none-elf
|
||||
\end{minted}
|
||||
|
||||
The \texttt{target} option causes the binutils build system to create a
|
||||
cross-assembler\footnote{assuming you aren't running binutils on a computer that
|
||||
also contains an SH4 CPU} that is capable of generating code for the SH4
|
||||
(Dreamcast) CPU. This also causes all installed commands to be prefixed with
|
||||
\texttt{sh4-none-elf-}, for example: \texttt{sh4-none-elf-ld} for the binutils
|
||||
linker.
|
||||
|
||||
These ``target triples'' are underdocumented.
|
||||
|
||||
While nearly any \texttt{sh*-*-*} triplet would have worked, a secondary goal of
|
||||
choosing this specific triplet is to not conflict with the name chosen for the
|
||||
KallistiOS toolchain, \texttt{sh-elf}.
|
||||
|
||||
The complete configure command is:
|
||||
|
||||
\begin{listing}[H]
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{shell}
|
||||
mkdir ~/binutils-2.45/build
|
||||
cd ~/binutils-2.45/build
|
||||
../configure --target=sh4-none-elf
|
||||
\end{minted}
|
||||
\caption{Binutils configure}
|
||||
\label{lst:binutils-configure}
|
||||
\end{listing}
|
||||
|
||||
\section{Binutils build and install}
|
||||
|
||||
Build and install binutils with:
|
||||
|
||||
\begin{listing}[H]
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{shell}
|
||||
cd ~/binutils-2.45/build
|
||||
|
||||
make -j$(nproc)
|
||||
|
||||
make install
|
||||
\end{minted}
|
||||
\caption{Binutils build and install}
|
||||
\label{lst:binutils-build-install}
|
||||
\end{listing}
|
||||
|
||||
You may need to prefix the \texttt{make install} command with \texttt{sudo} or
|
||||
\texttt{su} depending on your system.
|
||||
|
||||
Note that binutils must be installed correctly prior to proceeding. You can test
|
||||
this by running the command \texttt{sh4-none-elf-ld -v}. If
|
||||
\texttt{sh4-none-elf} binutils is properly installed, you will get output
|
||||
identical to:
|
||||
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{shell}
|
||||
GNU ld (GNU Binutils) 2.45
|
||||
\end{minted}
|
||||
|
||||
\section{GCC configuration}
|
||||
The GCC we will build in particular will have no support for linking with
|
||||
a C standard library. In Dreamcast game development, the C standard library
|
||||
isn't particularly useful (e.g: string manipulation functions are hardly used).
|
||||
|
||||
Anything we do need that we could have used from the C standard library we will
|
||||
reimplement ourselves.
|
||||
|
||||
While it is obvious that the GCC developers don't support this use-case as well
|
||||
as they could, the only problem occurs when GCC automatically emits a call to
|
||||
\texttt{memcpy} or \texttt{memzero} in code that did not explicitly call either.
|
||||
Most of the time, such calls can be removed by changing optimization levels or
|
||||
refactoring code. In other cases, it may be situationally convenient to
|
||||
implement either as trivial one-line loops.
|
||||
|
||||
To compile gcc, invoke the \texttt{./configure} script with the appropriate
|
||||
options. Here are explanations for a few of the more interesting options:
|
||||
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{shell}
|
||||
--with-endian=little
|
||||
\end{minted}
|
||||
|
||||
The SH4 CPU in the Dreamcast is jumpered to little endian mode, and CPU
|
||||
endianness is not reconfigurable without physical modification.
|
||||
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{shell}
|
||||
--with-cpu=m4-single
|
||||
\end{minted}
|
||||
|
||||
\texttt{m4-single} is a floating point calling convention where functions assume
|
||||
the SH4 CPU is in ``single precision'' mode on function entry. In this ABI,
|
||||
functions that use double precision operations require extra instructions (and
|
||||
CPU cycles) to switch to double precision mode on function entry, and switch
|
||||
back to single precision mode prior to function return.
|
||||
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{shell}
|
||||
--disable-hosted-libstdcxx
|
||||
\end{minted}
|
||||
|
||||
This disables all libstdcxx features that depend on exceptions and heap
|
||||
allocation. For example, \texttt{<list>} and \texttt{<vector>} are not
|
||||
available, but \texttt{<bit>} and \texttt{<type\_traits>} are available.
|
||||
|
||||
The cppreference.com article on
|
||||
\href{https://en.cppreference.com/w/cpp/freestanding.html}{freestanding} has
|
||||
more information on which features are (not) available with a freestanding
|
||||
libstdc++ build.
|
||||
|
||||
The complete configure command is:
|
||||
|
||||
\begin{listing}[H]
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{shell}
|
||||
mkdir ~/gcc-15.1.0/build
|
||||
cd ~/gcc-15.1.0/build
|
||||
../configure \
|
||||
--target=sh4-none-elf \
|
||||
--with-endian=little \
|
||||
--with-cpu=m4-single \
|
||||
--without-newlib \
|
||||
--without-headers \
|
||||
--disable-nls \
|
||||
--disable-shared \
|
||||
--disable-multilib \
|
||||
--disable-decimal-float \
|
||||
--disable-threads \
|
||||
--disable-libatomic \
|
||||
--disable-libgomp \
|
||||
--disable-libquadmath \
|
||||
--disable-libssp \
|
||||
--disable-libvtv \
|
||||
--disable-hosted-libstdcxx \
|
||||
--disable-libstdcxx-pch \
|
||||
--disable-libstdcxx-verbose \
|
||||
--disable-libstdcxx-filesystem-ts \
|
||||
--disable-libstdcxx-threads \
|
||||
--disable-libstdcxx-backtrace \
|
||||
--enable-languages=c,c++ \
|
||||
--disable-bootstrap
|
||||
\end{minted}
|
||||
\caption{GCC configure}
|
||||
\label{lst:gcc-configure}
|
||||
\end{listing}
|
||||
|
||||
\section{GCC build and install}
|
||||
|
||||
Build and install gcc with:
|
||||
|
||||
\begin{listing}[H]
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em]{shell}
|
||||
cd ~/gcc-15.1.0/build
|
||||
|
||||
make -j$(nproc)
|
||||
|
||||
make install
|
||||
\end{minted}
|
||||
\caption{GCC build and install}
|
||||
\label{lst:gcc-build-install}
|
||||
\end{listing}
|
||||
|
||||
You will notice that the time required to build GCC is significantly longer than
|
||||
the time required to build binutils.
|
||||
|
||||
You may need to prefix the \texttt{make install} command with \texttt{sudo} or
|
||||
\texttt{su} depending on your system.
|
||||
|
||||
If installed correctly, you should be able to run the \texttt{sh4-none-elf-gcc -v}
|
||||
command, which should produce output identical to:
|
||||
|
||||
\begin{minted}[bgcolor=Beige, bgcolorpadding=0.5em, breaklines, breakanywhere]{text}
|
||||
Using built-in specs.
|
||||
COLLECT_GCC=sh4-none-elf-gcc
|
||||
COLLECT_LTO_WRAPPER=/usr/local/libexec/gcc/sh4-none-elf/15.1.0/lto-wrapper
|
||||
Target: sh4-none-elf
|
||||
Configured with: ../configure --target=sh4-none-elf --with-endian=little --with-cpu=m4-single --without-newlib --without-headers --disable-nls --disable-shared --disable-multilib --disable-decimal-float --disable-threads --disable-libatomic --disable-libgomp --disable-libquadmath --disable-libssp --disable-libvtv --disable-hosted-libstdcxx --disable-libstdcxx-pch --disable-libstdcxx-verbose --disable-libstdcxx-filesystem-ts --disable-libstdcxx-threads --disable-libstdcxx-backtrace --enable-languages=c,c++ --disable-bootstrap
|
||||
Thread model: single
|
||||
Supported LTO compression algorithms: zlib zstd
|
||||
gcc version 15.1.0 (GCC)
|
||||
\end{minted}
|
||||
|
||||
\chapter{Dreamcast hardware registers}
|
||||
|
||||
\section{An absolute minimal demo}
|
||||
|
||||
The objective of this section is to get code running on Dreamcast while avoiding
|
||||
as much boilerplate as possible.
|
||||
|
||||
\end{document}
|
Loading…
x
Reference in New Issue
Block a user