Skip to content

Commit b5c438b

Browse files
Gathroszsparal
authored andcommitted
Bogo Sort in X86_64 (#517)
* adding bogo_sort.s * updating bogo_sort.md
1 parent 47fe49f commit b5c438b

File tree

2 files changed

+151
-0
lines changed

2 files changed

+151
-0
lines changed

contents/bogo_sort/bogo_sort.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,8 @@ In code, it looks something like this:
5555
[import:3-8, lang:"lisp"](code/racket/bogo_sort.rkt)
5656
{% sample lang="st" %}
5757
[import:2-6, lang:"st"](code/smalltalk/bogosort.st)
58+
{% sample lang="asm-x64" %}
59+
[import:93-113, lang:"asm-x64"](code/asm-x64/bogosort.s)
5860
{% sample lang="lisp" %}
5961
[import:20-24, lang:"lisp"](code/lisp/bogo-sort.lisp)
6062
{% endmethod %}
@@ -111,6 +113,8 @@ We are done here!
111113
[import, lang:"lisp"](code/racket/bogo_sort.rkt)
112114
{% sample lang="st" %}
113115
[import, lang:"st"](code/smalltalk/bogosort.st)
116+
{% sample lang="asm-x64" %}
117+
[import, lang:"asm-x64"](code/asm-x64/bogosort.s)
114118
{% sample lang="lisp" %}
115119
[import, lang:"lisp"](code/lisp/bogo-sort.lisp)
116120
{% endmethod %}
Lines changed: 147 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,147 @@
1+
.intel_syntax noprefix
2+
3+
.section .rodata
4+
array:
5+
.align 16
6+
.int 1, 3654, 78, 654, -234, -12, 4, 3, -6, -100
7+
.equ array_len, (.-array) / 4
8+
array_fmt: .string "%d "
9+
lf: .string "\n"
10+
unsorted: .string "Unsorted array: "
11+
sorted: .string "Sorted array: "
12+
13+
.section .text
14+
.global main
15+
.extern printf, rand, srand
16+
17+
# rdi - array ptr
18+
# rsi - array size
19+
print_array:
20+
push r12
21+
push r13
22+
mov r12, rdi # Loop variable
23+
lea r13, [rdi + 4 * rsi] # Pointer after the last element
24+
print_array_loop:
25+
cmp r12, r13 # If we're done iterating over the array then bail
26+
jge print_array_done
27+
mov rdi, OFFSET array_fmt # Otherwise print the current value
28+
mov esi, DWORD PTR [r12]
29+
xor rax, rax
30+
call printf
31+
lea r12, [r12 + 4] # And increment the loop variable pointer
32+
jmp print_array_loop
33+
print_array_done:
34+
mov rdi, OFFSET lf # Print a closing newline
35+
xor rax, rax
36+
call printf
37+
pop r13
38+
pop r12
39+
ret
40+
41+
# rdi - array ptr
42+
# rsi - array size
43+
# RET rax - boolean
44+
is_sorted:
45+
sub rsi, 1 # Getting array + n and *array + n - 1
46+
lea rcx, [rsi - 1]
47+
lea rcx, [rdi + 4 * rcx]
48+
lea rsi, [rdi + 4 * rsi]
49+
is_sorted_loop:
50+
cmp rsi, rdi # Check if array + n - 1 == array
51+
je is_sorted_done
52+
mov edx, DWORD PTR [rsi] # Load value to register
53+
xor rax, rax # Set rax to 0
54+
cmp edx, DWORD PTR [rcx] # Check if array[n] < array[n - 1]
55+
jl is_sorted_return
56+
sub rcx, 4 # If not make pointers go to down an element
57+
sub rsi, 4
58+
jmp is_sorted_loop
59+
is_sorted_done:
60+
mov rax, 1 # If sorted then set rax to 1
61+
is_sorted_return:
62+
ret # Return
63+
64+
# rdi - array ptr
65+
# rsi - array size
66+
shuffle:
67+
push r12
68+
push r13
69+
push r14
70+
push r15
71+
mov r12, rdi # Save parameters
72+
mov r13, rsi
73+
xor r14, r14
74+
shuffle_loop:
75+
cmp r14, r13 # Check if i == array size
76+
je shuffle_done
77+
mov r15d, DWORD PTR [r12 + r14 * 4] # Save array[i]
78+
call rand # Swap a random element with array[i]
79+
xor edx, edx
80+
div r13 # Mod random number to keep in array
81+
mov eax, DWORD PTR [r12 + rdx * 4]
82+
mov DWORD PTR [r12 + r14 * 4], eax
83+
mov DWORD PTR [r12 + rdx * 4], r15d
84+
add r14, 1 # increment then repeat
85+
jmp shuffle_loop
86+
shuffle_done:
87+
pop r15
88+
pop r14
89+
pop r13
90+
pop r12
91+
ret
92+
93+
# rdi - array ptr
94+
# rsi - array size
95+
bogo_sort:
96+
push r12
97+
push r13
98+
mov r12, rdi
99+
mov r13, rsi
100+
bogo_sort_loop:
101+
mov rdi, r12 # Check if the array is sorted
102+
mov rsi, r13
103+
call is_sorted
104+
test rax, rax
105+
jnz bogo_sort_done
106+
mov rdi, r12 # If not then shuffle
107+
mov rsi, r13
108+
call shuffle
109+
jmp bogo_sort_loop
110+
bogo_sort_done:
111+
pop r13
112+
pop r12
113+
ret
114+
115+
main:
116+
# Set up our stack
117+
sub rsp, 40
118+
# We load the array in chunks onto the stack
119+
movaps xmm0, XMMWORD PTR [array]
120+
movaps XMMWORD PTR [rsp], xmm0
121+
movaps xmm0, XMMWORD PTR [array + 16]
122+
movaps XMMWORD PTR [rsp + 16], xmm0
123+
mov rax, QWORD PTR [array + 32]
124+
mov QWORD PTR [rsp + 32], rax
125+
# Print the unsorted array
126+
mov rdi, OFFSET unsorted
127+
xor rax, rax
128+
call printf
129+
mov rdi, rsp
130+
mov rsi, array_len
131+
call print_array
132+
# Sort
133+
mov rdi, rsp
134+
mov rsi, array_len
135+
call bogo_sort
136+
# Print the sorted array
137+
mov rdi, OFFSET sorted
138+
xor rax, rax
139+
call printf
140+
mov rdi, rsp
141+
mov rsi, array_len
142+
call print_array
143+
# Restore the stack pointer, set return value to 0
144+
add rsp, 40
145+
xor rax, rax
146+
ret
147+

0 commit comments

Comments
 (0)