aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.gitignore2
-rw-r--r--config.asm2
-rw-r--r--makefile12
-rwxr-xr-xoptim.sh53
-rw-r--r--readme.md22
-rw-r--r--sort.asm4
6 files changed, 83 insertions, 12 deletions
diff --git a/.gitignore b/.gitignore
index f17708e..d07bda3 100644
--- a/.gitignore
+++ b/.gitignore
@@ -3,3 +3,5 @@ sort.o
data.o
csort.o
csort
+
+*.asme
diff --git a/config.asm b/config.asm
index 5ff521a..3d65a55 100644
--- a/config.asm
+++ b/config.asm
@@ -1,2 +1,2 @@
-%define USE_SYSCALL 0
+%define USE_SYSCALL 1 ; better for most arrays
%define TIMEOUT 1
diff --git a/makefile b/makefile
index a2bec28..04b17c8 100644
--- a/makefile
+++ b/makefile
@@ -1,11 +1,11 @@
all: asm
asm:
- @nasm -f elf64 -o sort.o sort.asm
- @nasm -f elf64 -o data.o data.asm
- @gcc -no-pie -o sort data.o sort.o
+ @nasm -O3 -f elf64 -o sort.o sort.asm
+ @nasm -O3 -f elf64 -o data.o data.asm
+ @gcc -O3 -no-pie -o sort data.o sort.o
c:
- @nasm -f elf64 -o data.o data.asm
- @gcc -no-pie -c -o csort.o benchmark/sort.c
- @gcc -no-pie -o csort data.o csort.o
+ @nasm -O3 -f elf64 -o data.o data.asm
+ @gcc -O3 -no-pie -c -o csort.o benchmark/sort.c -Wno-pointer-to-int-cast
+ @gcc -O3 -no-pie -o csort data.o csort.o
diff --git a/optim.sh b/optim.sh
new file mode 100755
index 0000000..04accf9
--- /dev/null
+++ b/optim.sh
@@ -0,0 +1,53 @@
+#!/bin/bash
+
+TRIALS=100
+SUCCESSES=10
+
+echo "if this takes too long, either choose a random timeout from the trials, adapt the script accordingly, or just use smaller numbers hehe"
+
+set -e
+
+make c
+REFERENCE=$(./csort)
+
+function test() {
+ make asm
+ for i in $(seq $TRIALS); do
+ output=$(stdbuf -i0 -o0 -e0 ./sort)
+ if [ "$output" != "$REFERENCE" ]; then
+ return 1
+ fi
+ done
+ return 0
+}
+
+function substitute() {
+ sed -ie "/^%define TIMEOUT/s/ [0-9]\+/ $1/" config.asm
+}
+
+# TODO: Multithreading
+minimum=4294967295
+successes=0
+timeout=1
+while true; do
+ substitute $timeout
+ if test; then
+ successes=$((successes + 1))
+ echo "$successes/$SUCCESSES with $timeout"
+
+ if [ $timeout -le $minimum ]; then
+ minimum=$timeout
+ fi
+
+ if [ $successes -eq $SUCCESSES ]; then
+ break
+ fi
+
+ timeout=$((timeout - timeout / 3))
+ else
+ timeout=$((timeout * 2))
+ fi
+done
+
+substitute $minimum
+echo "Done. Timeout $minimum will probably work most of the time."
diff --git a/readme.md b/readme.md
index 2531502..0acdb1d 100644
--- a/readme.md
+++ b/readme.md
@@ -2,9 +2,20 @@
> efficiently sleeping with (sub-)nanosecond precision and asm threads
+## Benchmarks
+
+With *good* numbers and *optimized* timeouts, sleepsort can achieve
+similar performance as C’s `qsort`.
+
+Example using the included array in `data.asm`:
+
+``` bash
+time ./sort # real 0.008s
+time ./csort # real 0.002s
+```
+
## Dependencies
-- ed
- nasm
- gcc
- make
@@ -12,7 +23,12 @@
## Usage
``` bash
-ed sort.asm # edit array and choose coolsleep/boringsleep
-make
+$EDITOR data.asm # edit array
+$EDITOR config.asm # choose syscall/busyloop strategy
+./optim.sh # find optimal sleep timeout
./sort
```
+
+## Usefulness
+
+None
diff --git a/sort.asm b/sort.asm
index feb91cb..4d6693c 100644
--- a/sort.asm
+++ b/sort.asm
@@ -32,7 +32,7 @@ end:
; uses nanosleep syscall
sleep:
- mov rax, TIMEOUT ; 0x424242
+ mov rax, TIMEOUT
mov rcx, rsi
mul rcx
push qword rax ; ns
@@ -48,7 +48,7 @@ sleep:
; uses busy loop
sleep:
- mov rax, TIMEOUT ; 0x4242424
+ mov rax, TIMEOUT
mov rcx, rsi
mul rcx
.loop: