summaryrefslogtreecommitdiff
path: root/cpu/os.asm
diff options
context:
space:
mode:
Diffstat (limited to 'cpu/os.asm')
-rw-r--r--cpu/os.asm259
1 files changed, 259 insertions, 0 deletions
diff --git a/cpu/os.asm b/cpu/os.asm
new file mode 100644
index 0000000..1617d6b
--- /dev/null
+++ b/cpu/os.asm
@@ -0,0 +1,259 @@
+# CONVENTION:
+# return value for functions : in register A
+# arguments for functions : registers A, B, C, D
+# all registers are caller-saved, except SP which is preserved by function calls
+
+.text
+ jal run_unit_tests
+
+ li A msghello
+ jal ser_out_msg
+
+ push Z
+main_loop:
+ # Process serial input
+ jal check_input
+ jz A end_process_input
+ jal run_cmd
+end_process_input:
+
+ # Process clock ticking
+ pop D
+ li B _clock
+ lw B 0(B)
+ add D D B
+ push D
+
+ jz B main_loop
+ li A msgtick
+ jal ser_out_msg
+ j main_loop
+
+# PROCEDURE: run_cmd
+# ROLE: execute and clear command stored in cmdline
+# ARGUMENTS: none
+run_cmd:
+ push RA
+
+ li A prompt
+ jal ser_out_msg
+ li A cmdline
+ jal ser_out_msg
+ li A endl
+ jal ser_out_msg
+
+ li A error
+ jal ser_out_msg
+
+ li A cmdline_used
+ sw Z 0(A)
+
+ pop RA
+ jr RA
+
+
+# PROCEDURE: ser_out_msg
+# ROLE: write null-terminated string to serial output
+# ARGUMENTS: address of string in register A
+ser_out_msg:
+ li C _output
+ser_out_msg_loop:
+ lb B 0(A)
+ jz B ser_out_msg_ret
+ sb B 0(C)
+ incri A 1
+ j ser_out_msg_loop
+ser_out_msg_ret:
+ jr RA
+
+# PROCEDURE: check_input
+# ROLE: check if an input byte is available. if it is, and is different from '\n' (10), add it to cmdline
+# ARGUMENTS: none
+# RETURN VALUE: 1 if read byte was '\n', 0 otherwise
+# WARNING: no buffer overflow check.
+check_input:
+ li A _input
+ lb A 0(A)
+ jz A check_input_ret
+ move B A
+ sei A A '\n'
+ jz A add_b_to_string
+ move B Z
+add_b_to_string:
+ push A
+ li A cmdline
+ li D cmdline_used
+ lw C 0(D)
+ add A A C
+ sb B 0(A)
+ incri C 1
+ sw C 0(D)
+ pop A
+ jz A check_input
+check_input_ret:
+ jr RA
+
+# PROCEDURE: run_unit_tests
+# ROLE: check that CPU features work correctly ; displays message to serial output
+# ARGUMENTS: none
+run_unit_tests:
+ push RA
+
+ li A testbegin
+ jal ser_out_msg
+
+ move B Z
+
+unit_test_begin:
+ li D testlist
+ add D D B
+ lw D 0(D)
+ jz D unit_tests_done
+
+ push B
+ push D
+ li A teststr
+ add A A B
+ lw A 0(A)
+ jal ser_out_msg
+ pop D
+ jalr D
+ li A testfail
+ jz B unit_test_failed
+ li A testok
+unit_test_failed:
+ jal ser_out_msg
+
+ pop B
+ addi B B 2
+ j unit_test_begin
+
+unit_tests_done:
+ pop RA
+ jr RA
+
+
+unit_test_0: # Addition / substraction
+ li B 1
+
+ li C 12
+ li D 44
+ add C C D
+ sei A C 56
+ and B B A
+
+ li C -7
+ li D 7
+ add C C D
+ se A C Z
+ and B B A
+
+ li C 32767
+ li D 32767
+ add C C D
+ li D 2
+ sub D Z D
+ se A C D
+ and B B A
+
+ jr RA
+
+unit_test_1: # Unsigned multiplication
+ li B 1
+
+ li C 12
+ li D 44
+ mulu C C D
+ move D E
+ sei A C 528
+ and B B A
+ se A D Z
+ and B B A
+
+ li C 744
+ li D 1244
+ mulu C C D
+ move D E
+ sei A C 8032
+ and B B A
+ sei A D 14
+ and B B A
+
+ jr RA
+
+unit_test_2: # Unsigned division
+ li B 1
+
+ li C 60
+ li D 5
+ divu C C D
+ move D E
+ sei A C 12
+ and B B A
+ se A D Z
+ and B B A
+
+ li C 14129
+ li D 477
+ divu C C D
+ move D E
+ sei A C 31
+ and B B A
+ sei A D 272
+ and B B A
+
+ jr RA
+unit_test_3: # Signed multiplication/division
+ li B 0
+ jr RA
+
+
+
+# READ-ONLY PROGRAM DATA
+
+# General strings
+msghello:
+ ascii "\nHello, world!\n"
+msgtick:
+ ascii " ..."
+prompt:
+ ascii "\n$ "
+endl:
+ ascii "\n"
+error:
+ ascii "Sorry but I'm to stupid to understand that.\n"
+
+# For unit-tests
+testlist:
+ word unit_test_0 unit_test_1 unit_test_2 unit_test_3 0
+teststr:
+ word test0 test1 test2 test3 0
+testbegin:
+ ascii "Runing CPU unit tests...\n"
+testok:
+ ascii "OK\n"
+testfail:
+ ascii "FAIL\n"
+test0:
+ ascii "Addition/substraction..........."
+test1:
+ ascii "Unsigned multiplication........."
+test2:
+ ascii "Unsigned division..............."
+test3:
+ ascii "Signed multiplication/division.."
+
+
+
+.data
+# Space where command-line is buffered from serial input
+cmdline:
+ byte 256
+# Number of bytes used in the command-line buffer
+cmdline_used:
+ word 1
+
+
+
+
+