Skip to content

Commit 2257f41

Browse files
enable stdio on rp6502 target (#395)
* rp6502 xstack bump to 512 * xstack bump to 512 * xstack bump to 512 * connect stdio * upgrade api to use ria.s * remove header * style * style * nits
1 parent 04fb58a commit 2257f41

29 files changed

+449
-220
lines changed

mos-platform/rp6502/CMakeLists.txt

+2
Original file line numberDiff line numberDiff line change
@@ -36,11 +36,13 @@ add_platform_library(rp6502-c
3636
lrand.c
3737
lseek.c
3838
open.c
39+
oserror.s
3940
phi2.c
4041
putchar.c
4142
read_xram.c
4243
read_xstack.c
4344
read.c
45+
ria.s
4446
stdin_opt.c
4547
sysremove.c
4648
sysrename.c

mos-platform/rp6502/clock.c

+2-7
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,4 @@
1-
#include <rp6502.h>
1+
#include "rp6502.h"
22
#include <time.h>
33

4-
long clock(void) {
5-
RIA.op = RIA_OP_CLOCK;
6-
while (RIA.busy & RIA_BUSY_BIT)
7-
;
8-
return (long)RIA.a | ((long)RIA.x << 8) | ((long)RIA.sreg << 16);
9-
}
4+
long clock(void) { return ria_call_long(RIA_OP_CLOCK); }

mos-platform/rp6502/clock_getres.c

+5-14
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,9 @@
1-
#include <rp6502.h>
1+
#include "rp6502.h"
22
#include <time.h>
33

4+
int __clock_gettimespec(struct timespec *ts, unsigned char op);
5+
46
int clock_getres(clockid_t clock_id, struct timespec *res) {
5-
RIA.a = clock_id;
6-
RIA.x = clock_id >> 8;
7-
RIA.op = RIA_OP_CLOCK_GETRES;
8-
while (RIA.busy & RIA_BUSY_BIT)
9-
;
10-
int ax = RIA.a | (RIA.x << 8);
11-
if (ax >= 0) {
12-
res->tv_sec = (long)RIA.xstack | ((long)RIA.xstack << 8) |
13-
((long)RIA.xstack << 16) | ((long)RIA.xstack << 24);
14-
res->tv_nsec = (long)RIA.xstack | ((long)RIA.xstack << 8) |
15-
((long)RIA.xstack << 16) | ((long)RIA.xstack << 24);
16-
}
17-
return ax;
7+
ria_set_ax(clock_id);
8+
return __clock_gettimespec(res, RIA_OP_CLOCK_GETRES);
189
}

mos-platform/rp6502/clock_gettime.c

+6-15
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,9 @@
1-
#include <rp6502.h>
1+
#include "rp6502.h"
22
#include <time.h>
33

4-
int clock_gettime(clockid_t clock_id, struct timespec *res) {
5-
RIA.a = clock_id;
6-
RIA.x = clock_id >> 8;
7-
RIA.op = RIA_OP_CLOCK_GETTIME;
8-
while (RIA.busy & RIA_BUSY_BIT)
9-
;
10-
int ax = RIA.a | (RIA.x << 8);
11-
if (ax >= 0) {
12-
res->tv_sec = RIA.xstack | (RIA.xstack << 8) | ((long)RIA.xstack << 16) |
13-
((long)RIA.xstack << 24);
14-
res->tv_nsec = RIA.xstack | (RIA.xstack << 8) | ((long)RIA.xstack << 16) |
15-
((long)RIA.xstack << 24);
16-
}
17-
return ax;
4+
int __clock_gettimespec(struct timespec *ts, unsigned char op);
5+
6+
int clock_gettime(clockid_t clock_id, struct timespec *tp) {
7+
ria_set_ax(clock_id);
8+
return __clock_gettimespec(tp, RIA_OP_CLOCK_GETTIME);
189
}
+12
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
#include "rp6502.h"
2+
#include <time.h>
3+
4+
/* Internal method shared by clock_getres and clock_gettime. */
5+
int __clock_gettimespec(struct timespec *ts, unsigned char op) {
6+
int ax = ria_call_int_errno(op);
7+
if (ax >= 0) {
8+
ts->tv_sec = ria_pop_long();
9+
ts->tv_nsec = ria_pop_long();
10+
}
11+
return ax;
12+
}

mos-platform/rp6502/clock_settime.c

+5-15
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,9 @@
1-
#include <rp6502.h>
1+
#include "rp6502.h"
22
#include <time.h>
33

44
int clock_settime(clockid_t clock_id, const struct timespec *tp) {
5-
RIA.a = clock_id;
6-
RIA.x = clock_id >> 8;
7-
RIA.xstack = tp->tv_nsec >> 24;
8-
RIA.xstack = tp->tv_nsec >> 16;
9-
RIA.xstack = tp->tv_nsec >> 8;
10-
RIA.xstack = tp->tv_nsec;
11-
RIA.xstack = tp->tv_sec >> 24;
12-
RIA.xstack = tp->tv_sec >> 16;
13-
RIA.xstack = tp->tv_sec >> 8;
14-
RIA.xstack = tp->tv_sec;
15-
RIA.op = RIA_OP_CLOCK_SETTIME;
16-
while (RIA.busy & RIA_BUSY_BIT)
17-
;
18-
return RIA.a | (RIA.x << 8);
5+
ria_set_ax(clock_id);
6+
ria_push_long(tp->tv_nsec);
7+
ria_push_long(tp->tv_sec);
8+
return ria_call_int_errno(RIA_OP_CLOCK_SETTIME);
199
}

mos-platform/rp6502/close.c

+4-7
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,7 @@
1-
#include <rp6502.h>
1+
#include <fcntl.h>
2+
#include "rp6502.h"
23

34
int close(int fd) {
4-
RIA.a = fd;
5-
RIA.x = fd >> 8;
6-
RIA.op = RIA_OP_CLOSE;
7-
while (RIA.busy & RIA_BUSY_BIT)
8-
;
9-
return RIA.a | (RIA.x << 8);
5+
ria_set_ax(fd);
6+
return ria_call_int_errno(RIA_OP_CLOSE);
107
}

mos-platform/rp6502/codepage.c

+1-6
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,3 @@
11
#include "rp6502.h"
22

3-
int codepage(void) {
4-
RIA.op = RIA_OP_CODEPAGE;
5-
while (RIA.busy & RIA_BUSY_BIT)
6-
;
7-
return RIA.a | (RIA.x << 8);
8-
}
3+
int codepage(void) { return ria_call_int(RIA_OP_CODEPAGE); }

mos-platform/rp6502/exit.c

+1-2
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
#include "rp6502.h"
22

33
void _Exit(int status) {
4-
RIA.a = status;
5-
RIA.x = status >> 8;
4+
ria_set_ax(status);
65
RIA.op = RIA_OP_EXIT;
76
}

mos-platform/rp6502/getchar.c

+4-6
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,11 @@
11
#include "rp6502.h"
22
#include <stdio.h>
3+
#include <unistd.h>
34

45
int __getchar(void) {
5-
RIA.xstack = 1;
6-
RIA.a = 0;
7-
RIA.op = RIA_OP_READ_XSTACK;
8-
while (RIA.busy & RIA_BUSY_BIT)
9-
;
10-
if (RIA.a)
6+
ria_push_char(1);
7+
ria_set_a(STDIN_FILENO);
8+
if (ria_call_int_errno(RIA_OP_READ_XSTACK) == 1)
119
return RIA.xstack;
1210
return EOF;
1311
}

mos-platform/rp6502/lrand.c

+1-6
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,3 @@
11
#include "rp6502.h"
22

3-
long lrand(void) {
4-
RIA.op = RIA_OP_LRAND;
5-
while (RIA.busy & RIA_BUSY_BIT)
6-
;
7-
return (long)RIA.a | ((long)RIA.x << 8) | ((long)RIA.sreg << 16);
8-
}
3+
long lrand(void) { return ria_call_long(RIA_OP_LRAND); }

mos-platform/rp6502/lseek.c

+21-13
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,23 @@
1-
#include <rp6502.h>
1+
#include "rp6502.h"
2+
#include <stdio.h>
3+
#include <unistd.h>
24

3-
long lseek(int fd, long offset, int whence) {
4-
RIA.a = fd;
5-
RIA.x = fd >> 8;
6-
RIA.xstack = offset >> 24;
7-
RIA.xstack = offset >> 16;
8-
RIA.xstack = offset >> 8;
9-
RIA.xstack = offset;
10-
RIA.xstack = whence;
11-
RIA.op = RIA_OP_LSEEK;
12-
while (RIA.busy & RIA_BUSY_BIT)
13-
;
14-
return (long)RIA.a | ((long)RIA.x << 8) | ((long)RIA.sreg << 16);
5+
off_t lseek(int fd, off_t offset, int whence) {
6+
switch (whence) {
7+
case SEEK_CUR:
8+
ria_push_char(RIA_SEEK_CUR);
9+
break;
10+
case SEEK_END:
11+
ria_push_char(RIA_SEEK_END);
12+
break;
13+
case SEEK_SET:
14+
ria_push_char(RIA_SEEK_SET);
15+
break;
16+
default:
17+
ria_push_int(whence);
18+
break;
19+
}
20+
ria_push_long(offset);
21+
ria_set_ax(fd);
22+
return ria_call_long_errno(RIA_OP_LSEEK);
1523
}

mos-platform/rp6502/open.c

+8-9
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,18 @@
11
#include <errno.h>
2-
#include <rp6502.h>
2+
#include <fcntl.h>
3+
#include "rp6502.h"
34
#include <string.h>
45

6+
int __mappederrno(unsigned char code);
7+
58
int open(const char *name, int flags, ...) {
69
size_t namelen = strlen(name);
710
if (namelen > 255) {
811
RIA.errno = EINVAL;
9-
return -1;
12+
return __mappederrno(RIA.errno);
1013
}
1114
while (namelen)
12-
RIA.xstack = name[--namelen];
13-
RIA.a = flags;
14-
RIA.x = flags >> 8;
15-
RIA.op = RIA_OP_OPEN;
16-
while (RIA.busy & RIA_BUSY_BIT)
17-
;
18-
return RIA.a | (RIA.x << 8);
15+
ria_push_char(name[--namelen]);
16+
ria_set_ax(flags);
17+
return ria_call_int_errno(RIA_OP_OPEN);
1918
}

mos-platform/rp6502/oserror.s

+82
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
; Copyright 2024 LLVM-MOS Project
2+
; Licensed under the Apache License, Version 2.0 with LLVM Exceptions.
3+
; See https://github.com/llvm-mos/llvm-mos-sdk/blob/main/LICENSE for license
4+
; information.
5+
6+
; Originally from cc65. Modified from original version.
7+
8+
;
9+
; 2000-05-17, Ullrich von Bassewitz
10+
; 2014-05-28, Greg King
11+
;
12+
; int __osmaperrno (unsigned char oserror);
13+
; /* Map a system-specific error into a system-independent code. */
14+
;
15+
16+
.include "errno.inc"
17+
.include "rp6502.inc"
18+
19+
.text
20+
.globl __osmaperrno
21+
__osmaperrno:
22+
ldx #ErrTabSize
23+
1: cmp ErrTab-2,x ; Search for the error code
24+
beq 1f ; Jump if found
25+
dex
26+
dex
27+
bne 1b ; Next entry
28+
29+
; Code not found, return EUNKNOWN
30+
31+
lda #<EUNKNOWN
32+
ldx #>EUNKNOWN
33+
rts
34+
35+
; Found the code
36+
37+
1: lda ErrTab-1,x
38+
ldx #$00 ; High byte always zero
39+
rts
40+
41+
.rodata
42+
43+
ErrTab:
44+
.byte RIA_ENOENT , ENOENT
45+
.byte RIA_ENOMEM , ENOMEM
46+
.byte RIA_EACCES , EACCES
47+
.byte RIA_ENODEV , ENODEV
48+
.byte RIA_EMFILE , EMFILE
49+
.byte RIA_EBUSY , EBUSY
50+
.byte RIA_EINVAL , EINVAL
51+
.byte RIA_ENOSPC , ENOSPC
52+
.byte RIA_EEXIST , EEXIST
53+
.byte RIA_EAGAIN , EAGAIN
54+
.byte RIA_EIO , EIO
55+
.byte RIA_EINTR , EINTR
56+
.byte RIA_ENOSYS , ENOSYS
57+
.byte RIA_ESPIPE , ESPIPE
58+
.byte RIA_ERANGE , ERANGE
59+
.byte RIA_EBADF , EBADF
60+
.byte RIA_ENOEXEC , ENOEXEC
61+
; .byte RIA_EUNKNOWN , EUNKNOWN
62+
.byte FR_DISK_ERR , EIO
63+
; .byte FR_INT_ERR , EUNKNOWN
64+
.byte FR_NOT_READY , EBUSY
65+
.byte FR_NO_FILE , ENOENT
66+
.byte FR_NO_PATH , ENOENT
67+
.byte FR_INVALID_NAME , EINVAL
68+
.byte FR_DENIED , EACCES
69+
.byte FR_EXIST , EEXIST
70+
.byte FR_INVALID_OBJECT , EINVAL
71+
.byte FR_WRITE_PROTECTED , EACCES
72+
.byte FR_INVALID_DRIVE , ENODEV
73+
; .byte FR_NOT_ENABLED , EUNKNOWN
74+
; .byte FR_NO_FILESYSTEM , EUNKNOWN
75+
; .byte FR_MKFS_ABORTED , EUNKNOWN
76+
; .byte FR_TIMEOUT , EUNKNOWN
77+
.byte FR_LOCKED , EBUSY
78+
.byte FR_NOT_ENOUGH_CORE , ENOMEM
79+
.byte FR_TOO_MANY_OPEN_FILES , EMFILE
80+
.byte FR_INVALID_PARAMETER , EINVAL
81+
82+
ErrTabSize = . - ErrTab

mos-platform/rp6502/phi2.c

+1-6
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,3 @@
11
#include "rp6502.h"
22

3-
int phi2(void) {
4-
RIA.op = RIA_OP_PHI2;
5-
while (RIA.busy & RIA_BUSY_BIT)
6-
;
7-
return RIA.a | (RIA.x << 8);
8-
}
3+
int phi2(void) { return ria_call_int(RIA_OP_PHI2); }

mos-platform/rp6502/putchar.c

+4-5
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,9 @@
11
#include "rp6502.h"
22
#include <stdio.h>
3+
#include <unistd.h>
34

45
void __putchar(char c) {
5-
RIA.xstack = c;
6-
RIA.a = 1;
7-
RIA.op = RIA_OP_WRITE_XSTACK;
8-
while (RIA.busy & RIA_BUSY_BIT)
9-
;
6+
ria_push_char(c);
7+
ria_set_a(STDOUT_FILENO);
8+
ria_call_int_errno(RIA_OP_WRITE_XSTACK);
109
}

mos-platform/rp6502/read.c

+3-2
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
1-
#include <rp6502.h>
1+
#include "rp6502.h"
2+
#include <unistd.h>
23

34
int read(int fildes, void *buf, unsigned count) {
45
int total = 0;
56
while (count) {
6-
unsigned blockcount = (count > 256) ? 256 : count;
7+
unsigned blockcount = (count > 512) ? 512 : count;
78
int bytes_read = read_xstack(&((char *)buf)[total], blockcount, fildes);
89
if (bytes_read < 0)
910
return bytes_read;

mos-platform/rp6502/read_xram.c

+5-11
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,8 @@
1-
#include <rp6502.h>
1+
#include "rp6502.h"
22

33
int read_xram(unsigned buf, unsigned count, int fildes) {
4-
RIA.xstack = buf >> 8;
5-
RIA.xstack = buf;
6-
RIA.xstack = count >> 8;
7-
RIA.xstack = count;
8-
RIA.a = fildes;
9-
RIA.x = fildes >> 8;
10-
RIA.op = RIA_OP_READ_XRAM;
11-
while (RIA.busy & RIA_BUSY_BIT)
12-
;
13-
return RIA.a | (RIA.x << 8);
4+
ria_push_int(buf);
5+
ria_push_int(count);
6+
ria_set_ax(fildes);
7+
return ria_call_int_errno(RIA_OP_READ_XRAM);
148
}

0 commit comments

Comments
 (0)