aboutsummaryrefslogtreecommitdiffstats
path: root/c/libc.s
diff options
context:
space:
mode:
Diffstat (limited to 'c/libc.s')
-rw-r--r--c/libc.s84
1 files changed, 58 insertions, 26 deletions
diff --git a/c/libc.s b/c/libc.s
index 4fca5e3..29031e9 100644
--- a/c/libc.s
+++ b/c/libc.s
@@ -1,19 +1,48 @@
.module libc
- .globl _writes, _nl, _readc, _sexit, _getpid
+ .globl _writes, _putc, _puts, _nl, _strlen, _readc, _sexit, _getpid, _getargs
+ ;; SDCC sm83 sdcccall(1): 1st arg -> A (byte) or DE (pointer); ret A / BC.
+ ;; rst $30 (the trap) clobbers BC/DE/HL; SDCC treats them caller-saved, so
+ ;; wrappers need not preserve them - but we compute cleanly regardless.
.area _CODE
+
;; void writes(const char *buf /*DE*/, unsigned char len /*A*/)
_writes:
- push hl
- push de
- push bc
ld b, a
- ld c, #3 ; SYS_WRITE
+ ld c, #3 ; SYS_WRITE
rst #0x30
- pop bc
- pop de
- pop hl
ret
- ;; void nl(void) - CRLF straight to serial
+
+ ;; char *getargs(void) -> BC : the arg string (command line past word 1).
+ ;; The shell leaves "cmd\0args\0" at 0xA000, inherited by the child via fork.
+_getargs:
+ ld hl, #0xa000
+1$: ld a, (hl)
+ inc hl
+ or a
+ jr nz, 1$
+ ld b, h
+ ld c, l
+ ret
+
+ ;; void putc(char c /*A*/)
+_putc:
+ ld (0xff01), a
+ ld a, #0x81
+ ld (0xff02), a
+ ret
+
+ ;; void puts(const char *s /*DE*/) - write until NUL (no newline)
+_puts:
+1$: ld a, (de)
+ or a
+ ret z
+ ld (0xff01), a
+ ld a, #0x81
+ ld (0xff02), a
+ inc de
+ jr 1$
+
+ ;; void nl(void) - CRLF
_nl:
ld a, #0x0d
ld (0xff01), a
@@ -24,31 +53,34 @@ _nl:
ld a, #0x81
ld (0xff02), a
ret
- ;; unsigned char readc(void) -> A
+
+ ;; unsigned char strlen(const char *s /*DE*/) -> A
+_strlen:
+ ld c, #0
+1$: ld a, (de)
+ or a
+ jr z, 2$
+ inc c
+ inc de
+ jr 1$
+2$: ld a, c
+ ret
+
+ ;; char readc(void) -> A (4 = EOF)
_readc:
- push hl
- push de
- push bc
- ld c, #2 ; SYS_READ
+ ld c, #2 ; SYS_READ
rst #0x30
- pop bc
- pop de
- pop hl
ret
- ;; void sexit(unsigned char code /*A*/)
+
+ ;; void sexit(unsigned char code /*A*/) - never returns
_sexit:
ld b, a
- ld c, #0 ; SYS_EXIT
+ ld c, #0 ; SYS_EXIT
rst #0x30
ret
+
;; unsigned char getpid(void) -> A
_getpid:
- push hl
- push de
- push bc
- ld c, #8 ; SYS_GETPID
+ ld c, #8 ; SYS_GETPID
rst #0x30
- pop bc
- pop de
- pop hl
ret