summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorpommicket <pommicket@gmail.com>2022-11-11 12:15:24 -0500
committerpommicket <pommicket@gmail.com>2022-11-11 12:15:24 -0500
commitdd9d3dc6f1a466feb13e19f4c98cd911508f53d4 (patch)
treed7e28780d5d93b72b57682c5780d0f3207345ba3
parent7b14e052884a1cebf77045d66a686cadfe4d38f6 (diff)
readmeHEADtrunk
-rw-r--r--README.md55
-rw-r--r--tests/sdl.c6
-rw-r--r--tests/tests.rs2
3 files changed, 60 insertions, 3 deletions
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..11f7ae7
--- /dev/null
+++ b/README.md
@@ -0,0 +1,55 @@
+# tinyld
+
+a linker for making tiny 32-bit linux executables.
+
+*Just after* making this, I found out that something similar already existed here:
+https://github.com/Shizmob/smol/ -- although smold's executables are giving me segfaults
+for some reason.
+This linker is worse in terms of output size, but the executables are more standard-compliant
+and don't rely on undocumented ELF magic. The difference isn't even that big (in the 10s of bytes)
+after compressing with `xz` -- so if you're using [this handy executable unpacker](https://gitlab.com/PoroCYon/vondehi),
+you'll get about the same output size.
+
+## Executable sizes
+
+Exit using inline assembly (tests/tiny.c): **93 bytes**
+
+Hello world: **369 bytes** (252 bytes `xz`-compressed)
+
+Open a window, get a GL context, and call `glClearColor`, `glClear` each frame (tests/sdl.c): **881 bytes**
+(532 bytes `xz`-compressed)
+
+## Installation
+
+You will need a [rust installation](https://www.rust-lang.org/tools/install).
+
+```
+cargo install --path .
+```
+
+## Usage
+
+`gcc-multilib`/`g++-multilib` are needed for 32-bit headers for C/C++.
+
+Example: create a file called `hello.c` containing
+```
+#include <stdio.h>
+#include <stdlib.h>
+
+void entry(void) {
+ printf("Hello, world!\n");
+ exit(0);
+}
+```
+
+then run `tinyld hello.c -o hello`. You now have an executable called `hello` which prints `Hello, world!`.
+
+To add libaries, use e.g. `tinyld my_sdl_program.c libSDL2.so`.
+
+You can use C++, but exceptions probably won't work, and `cout`/`cin` don't seem to work either
+(you should be using `printf` anyways if you want a smaller executable).
+
+Only 32-bit x86 ELF is supported. If you give tinyld a 64-bit executable it will die.
+If you're compiling your own object files, you need to add `-fno-pic` otherwise tinyld will die.
+
+For more information, see `tinyld --help`.
diff --git a/tests/sdl.c b/tests/sdl.c
index a3c3d8f..31331c0 100644
--- a/tests/sdl.c
+++ b/tests/sdl.c
@@ -8,8 +8,10 @@ int main(void) {
SDL_Init(SDL_INIT_EVERYTHING);
SDL_Window *window = SDL_CreateWindow("hi", 0, 0, 1280, 720, SDL_WINDOW_SHOWN|SDL_WINDOW_OPENGL);
SDL_GLContext ctx = SDL_GL_CreateContext(window);
- PFNGLCLEARPROC glClear = SDL_GL_GetProcAddress("glClear");
- PFNGLCLEARCOLORPROC glClearColor = SDL_GL_GetProcAddress("glClearColor");
+ // we save a byte this way since we don't need an extra relocation.
+ void *(*volatile get_proc_address)() = SDL_GL_GetProcAddress;
+ PFNGLCLEARPROC glClear = get_proc_address("glClear");
+ PFNGLCLEARCOLORPROC glClearColor = get_proc_address("glClearColor");
SDL_GL_SetSwapInterval(1);
while (true) {
SDL_Event event;
diff --git a/tests/tests.rs b/tests/tests.rs
index 24e1881..761fe41 100644
--- a/tests/tests.rs
+++ b/tests/tests.rs
@@ -52,7 +52,7 @@ mod tests {
fn tiny_c() {
let mut linker = test_linker();
add(&mut linker, "tiny.c", true);
- link(&linker, "test.out", "entry");
+ link(&linker, "tiny.out", "entry");
let output = run("tiny.out");
assert!(output.stdout.is_empty());
}