Skip to content

Commit 41447d5

Browse files
committed
Rewrite of sioload.
1 parent 1d9752f commit 41447d5

File tree

4 files changed

+241
-145
lines changed

4 files changed

+241
-145
lines changed

src/mips/ps1sdk/include/serialio.h

Lines changed: 33 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ extern "C" {
4343
#define SIO_STAT_TX_EMPTY 0x0004
4444
#define SIO_STAT_RX_RDY 0x0002
4545
#define SIO_STAT_TX_RDY 0x0001
46+
#define SIO_STAT_MASK (0x03FF)
4647

4748
// bits for CONTROL
4849

@@ -56,6 +57,7 @@ extern "C" {
5657
#define SIO_CTRL_BUF4 0x0200
5758
#define SIO_CTRL_BUF2 0x0100
5859
#define SIO_CTRL_BUF1 0x0000
60+
// why is there nothing for bit 7? CTRL_BUFx is bits 9-10
5961
#define SIO_CTRL_RESET_INT 0x0040
6062
// enable RTS driver(inverted)
6163
#define SIO_CTRL_RTS_EN 0x0020
@@ -68,6 +70,7 @@ extern "C" {
6870
#define SIO_CTRL_DTR_EN 0x0002
6971
// enable TXD
7072
#define SIO_CTRL_TX_EN 0x0001
73+
#define SIO_CTRL_MASK (0x1FFF)
7174

7275
/*
7376
* SIO1
@@ -89,34 +92,48 @@ extern "C" {
8992

9093
// Bits for MODE
9194

92-
// MODE: Baud Rate multiplier(??)
93-
// NOTE: supposedly these 2 bits should always be "10"(2)..
94-
#define SIO_MODE_BR_1 0x0001
95-
#define SIO_MODE_BR_16 0x0002
96-
#define SIO_MODE_BR_64 0x0003
95+
// MODE: Stop Bits
96+
// bits 6-7
97+
#define SIO_MODE_SB_1 0x0040
98+
#define SIO_MODE_SB_1_5 0x0080
99+
#define SIO_MODE_SB_2 0x00C0
100+
101+
// MODE: Parity
102+
// bits 4-5
103+
#define SIO_MODE_P_NONE 0x0000
104+
#define SIO_MODE_P_ODD 0x0010
105+
#define SIO_MODE_P_EVEN 0x0030
97106

98107
// MODE: Character Length(Bits Per Character)
108+
// bits 2-3
99109
#define SIO_MODE_CHLEN_5 0x0000
100110
#define SIO_MODE_CHLEN_6 0x0004
101111
#define SIO_MODE_CHLEN_7 0x0008
102112
#define SIO_MODE_CHLEN_8 0x000C
103113

104-
// MODE: Parity
105-
#define SIO_MODE_P_NONE 0x0000
106-
#define SIO_MODE_P_ODD 0x0010
107-
#define SIO_MODE_P_EVEN 0x0030
114+
// MODE: Baud Rate multiplier(??)
115+
// NOTE: supposedly these 2 bits should always be "10"(2)..
116+
// bits 0-1
117+
#define SIO_MODE_BR_1 0x0001
118+
#define SIO_MODE_BR_16 0x0002
119+
#define SIO_MODE_BR_64 0x0003
108120

109-
// MODE: Stop Bits
110-
#define SIO_MODE_SB_1 0x0040
111-
#define SIO_MODE_SB_1_5 0x0080
112-
#define SIO_MODE_SB_2 0x00C0
121+
#define SIO_MODE_MASK 0x00FF
113122

114123
/* prototypes */
115124

116-
uint8_t read_sio(void);
117-
void write_sio(uint8_t d);
125+
int sio_peek8(uint32_t timeout);
126+
uint32_t sio_peek32(uint32_t timeout);
127+
uint16_t sio_peek16(uint32_t timeout);
128+
129+
int sio_poke8(uint8_t data, uint32_t timeout);
130+
int sio_poke16(uint16_t data, uint32_t timeout);
131+
int sio_poke32(uint32_t data, uint32_t timeout);
132+
133+
void sio_reset(void);
134+
void sio_clear_error(void);
135+
void sio_reset_driver(void);
118136
void init_sio(uint32_t baud);
119-
uint32_t sio_read32(void);
120137

121138
//~ void sio_init(int port_no, int baud);
122139

src/mips/sioload/Makefile

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ SRCS = \
44
../common/hardware/cop0.s \
55
crt0/crt0.S \
66
src/main.c \
7+
src/serialio.c \
78

89
LIBS = ../ps1sdk/libps1sdk.a
910

src/mips/sioload/src/main.c

Lines changed: 16 additions & 129 deletions
Original file line numberDiff line numberDiff line change
@@ -25,152 +25,38 @@
2525

2626
#include "common/hardware/cop0.h"
2727

28-
typedef struct {
29-
uint32_t inited, mode, ctrl, baud;
30-
} port_config_t;
31-
32-
static port_config_t config;
33-
34-
#define SIO1_BAUD_DIV (2073600)
35-
// I don't understand this... PsyQ says "bps must be in the range 9600 - 2073600 and evenly divisible into 2073600"
36-
// but reversing libsio shows 2116800 being divided by baud, not 2073600??
37-
//#define SIO1_BAUD_DIV (2116800)
38-
39-
#define SIO_RESET() (*R_PS1_SIO1_CTRL = SIO_CTRL_RESET_INT | SIO_CTRL_RESET_ERR)
40-
41-
static inline void sio_put_baud(uint32_t baud) { *R_PS1_SIO1_BAUD = SIO1_BAUD_DIV / baud; }
42-
static inline void sio_put_mode(uint16_t mode) { *R_PS1_SIO1_MODE = (mode & (~3)) | SIO_MODE_BR_16; }
43-
static inline void sio_put_ctrl(uint16_t mask, uint16_t ctrl) { *R_PS1_SIO1_CTRL = ((*R_PS1_SIO1_CTRL & mask) | ctrl); }
44-
45-
/* the sio_set_xxx functions not only write the value to the register but also update the config value for that register
46-
*/
47-
static inline void sio_set_baud(uint32_t baud) {
48-
config.baud = baud;
49-
sio_put_baud(config.baud);
50-
}
51-
52-
static inline void sio_set_ctrl(uint16_t mask, uint16_t ctrl) {
53-
config.ctrl = ctrl;
54-
sio_put_ctrl(mask, config.ctrl);
55-
}
56-
57-
static inline void sio_set_mode(uint16_t mode) {
58-
// bits 0 and 1 should always be 0 and 1, respectively
59-
// this apparently corresponds to "baud rate multiplier 16"
60-
config.mode = mode;
61-
sio_put_mode(config.mode);
62-
}
63-
64-
static inline uint16_t sio_get_status(void) { return *R_PS1_SIO1_STAT; }
65-
66-
static inline uint8_t sio_get_data(void) { return *R_PS1_SIO1_DATA; }
67-
68-
static inline void sio_put_data(uint8_t d) { *R_PS1_SIO1_DATA = d; }
69-
70-
// this should probably check STAT for errors.
71-
uint8_t sio_get_byte(void) {
72-
uint8_t d;
73-
74-
// this may not be necessary. Some UARTs won't transfer if yout don't though.
75-
76-
// assert RTR(Ready To Receive akia "RTS"/Request to Send)
77-
sio_put_ctrl(~(SIO_CTRL_RTR_EN), SIO_CTRL_RTR_EN);
78-
79-
// wait for data in the RX FIFO
80-
while (!(sio_get_status() & SIO_STAT_RX_RDY))
81-
;
82-
83-
// pop a byte from the RX FIFO
84-
d = *R_PS1_SIO1_DATA;
85-
86-
// deassert RTR
87-
sio_put_ctrl(~(SIO_CTRL_RTR_EN), 0);
88-
89-
return d;
90-
}
91-
92-
int sio_put_byte(uint8_t data, uint32_t timeout) {
93-
volatile uint8_t d;
94-
95-
if (sio_get_status() & (SIO_STAT_RX_OVRN_ERR | SIO_STAT_FRAME_ERR | SIO_STAT_PARITY_ERR)) {
96-
// I guess this is to preserve the data that's currently in the TX FIFO?
97-
d = *R_PS1_SIO1_DATA;
98-
99-
while (sio_get_status() & (SIO_STAT_RX_OVRN_ERR | SIO_STAT_FRAME_ERR | SIO_STAT_PARITY_ERR)) {
100-
// RX Overrun, Frame Error or Parity Error
101-
102-
// reset the interrupt and error
103-
SIO_RESET();
104-
105-
delay_ms(5);
106-
107-
// restore the TX FIFO?
108-
*R_PS1_SIO1_DATA = d;
109-
110-
// restore mode and ctrl
111-
sio_put_mode(config.mode);
112-
sio_put_ctrl(0, config.ctrl);
113-
}
114-
}
115-
116-
// FIXME: what happens if the CTRL SIO_CTRL_TX_EN isn't set??
117-
118-
if (timeout == 0)
119-
while (!(sio_get_status() & SIO_STAT_TX_RDY))
120-
;
121-
else {
122-
uint32_t tries = 0;
123-
while (!(sio_get_status() & SIO_STAT_TX_RDY)) {
124-
if (++tries >= timeout) return -2;
125-
}
126-
}
127-
128-
// push the byte into the TX FIFO
129-
*R_PS1_SIO1_DATA = data;
130-
return data;
131-
}
132-
133-
void init_sio(uint32_t baud) {
134-
/* 8bit, no-parity, 1 stop-bit */
135-
sio_set_mode(SIO_MODE_CHLEN_8 | SIO_MODE_P_NONE | SIO_MODE_SB_1);
136-
sio_set_baud(baud);
137-
sio_set_ctrl(0, SIO_CTRL_RX_EN | SIO_CTRL_TX_EN);
138-
}
139-
140-
uint32_t sio_read32(void) {
141-
uint32_t d;
142-
143-
d = sio_get_byte() | (sio_get_byte() << 8) | (sio_get_byte() << 16) | (sio_get_byte() << 24);
144-
return d;
145-
}
146-
147-
void sioload() {
28+
void sioload(void) {
14829
int i;
149-
uint8_t sync;
30+
int sync;
15031
uint8_t* p;
15132
uint8_t header_buf[2048];
15233
EXE_Header* header = (EXE_Header*)header_buf;
15334
uint32_t x_addr, // ignored
15435
write_addr, n_load;
15536

156-
while (1) sio_put_byte('X', 0); // sends an X to pc
37+
while (1) {
38+
sio_poke8('X', 0); // sends an X to pc
39+
}
15740

15841
do {
159-
sync = sio_get_byte();
42+
sync = sio_peek8(10000);
16043
} while (sync != 99);
16144

16245
for (i = 0; i < sizeof(header_buf); i++) {
163-
header_buf[i] = sio_get_byte();
46+
header_buf[i] = sio_peek8(0);
16447
}
16548

166-
x_addr = sio_read32();
167-
write_addr = sio_read32();
168-
n_load = sio_read32();
49+
// ignored
50+
x_addr = sio_peek32(0);
51+
write_addr = sio_peek32(0);
52+
n_load = sio_peek32(0);
16953

17054
for (i = 0; i < n_load; i++) {
171-
((uint8_t*)write_addr)[i] = sio_get_byte();
55+
((uint8_t*)write_addr)[i] = sio_peek8(0);
17256
}
17357

58+
// could at least send back a kiss goodbye...
59+
17460
header->exec.stack_addr = 0x801FFF00;
17561
header->exec.stack_size = 0;
17662
EnterCriticalSection();
@@ -190,7 +76,8 @@ int DelSIO(void) {
19076
close(stdin);
19177
close(stdout);
19278
DelDevice("tty");
193-
SIO_RESET();
79+
sio_reset();
80+
19481
AddDummyConsoleDevice();
19582
if (open("tty00:", O_RDONLY) != stdin) return 1;
19683
if (open("tty00:", O_WRONLY) != stdout) return 1;

0 commit comments

Comments
 (0)