Statistics
| Branch: | Revision:

root / hw / slavio_serial.c @ 977d5710

History | View | Annotate | Download (8.8 kB)

1
/*
2
 * QEMU Sparc SLAVIO serial port emulation
3
 * 
4
 * Copyright (c) 2003-2004 Fabrice Bellard
5
 * 
6
 * Permission is hereby granted, free of charge, to any person obtaining a copy
7
 * of this software and associated documentation files (the "Software"), to deal
8
 * in the Software without restriction, including without limitation the rights
9
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10
 * copies of the Software, and to permit persons to whom the Software is
11
 * furnished to do so, subject to the following conditions:
12
 *
13
 * The above copyright notice and this permission notice shall be included in
14
 * all copies or substantial portions of the Software.
15
 *
16
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22
 * THE SOFTWARE.
23
 */
24
#include "vl.h"
25

    
26
//#define DEBUG_SERIAL
27

    
28
/* debug keyboard */
29
//#define DEBUG_KBD
30

    
31
/* debug keyboard : only mouse */
32
//#define DEBUG_MOUSE
33

    
34
/*
35
 * This is the serial port, mouse and keyboard part of chip STP2001
36
 * (Slave I/O), also produced as NCR89C105. See
37
 * http://www.ibiblio.org/pub/historic-linux/early-ports/Sparc/NCR/NCR89C105.txt
38
 * 
39
 * The serial ports implement full AMD AM8530 or Zilog Z8530 chips,
40
 * mouse and keyboard ports don't implement all functions and they are
41
 * only asynchronous. There is no DMA.
42
 *
43
 */
44

    
45
typedef struct ChannelState {
46
    int irq;
47
    int reg;
48
    int rxint, txint;
49
    uint8_t rx, tx, wregs[16], rregs[16];
50
    CharDriverState *chr;
51
} ChannelState;
52

    
53
struct SerialState {
54
    struct ChannelState chn[2];
55
};
56

    
57
#define SERIAL_MAXADDR 7
58

    
59
static void slavio_serial_update_irq(ChannelState *s)
60
{
61
    if ((s->wregs[1] & 1) && // interrupts enabled
62
        (((s->wregs[1] & 2) && s->txint == 1) || // tx ints enabled, pending
63
         ((((s->wregs[1] & 0x18) == 8) || ((s->wregs[1] & 0x18) == 0x10)) &&
64
          s->rxint == 1) || // rx ints enabled, pending
65
         ((s->wregs[15] & 0x80) && (s->rregs[0] & 0x80)))) { // break int e&p
66
        pic_set_irq(s->irq, 1);
67
    } else {
68
        pic_set_irq(s->irq, 0);
69
    }
70
}
71

    
72
static void slavio_serial_reset_chn(ChannelState *s)
73
{
74
    int i;
75

    
76
    s->reg = 0;
77
    for (i = 0; i < SERIAL_MAXADDR; i++) {
78
        s->rregs[i] = 0;
79
        s->wregs[i] = 0;
80
    }
81
    s->wregs[4] = 4;
82
    s->wregs[9] = 0xc0;
83
    s->wregs[11] = 8;
84
    s->wregs[14] = 0x30;
85
    s->wregs[15] = 0xf8;
86
    s->rregs[0] = 0x44;
87
    s->rregs[1] = 6;
88

    
89
    s->rx = s->tx = 0;
90
    s->rxint = s->txint = 0;
91
}
92

    
93
static void slavio_serial_reset(void *opaque)
94
{
95
    SerialState *s = opaque;
96
    slavio_serial_reset_chn(&s->chn[0]);
97
    slavio_serial_reset_chn(&s->chn[1]);
98
}
99

    
100
static void slavio_serial_mem_writeb(void *opaque, uint32_t addr, uint32_t val)
101
{
102
    SerialState *ser = opaque;
103
    ChannelState *s;
104
    uint32_t saddr;
105
    int newreg, channel;
106

    
107
    val &= 0xff;
108
    saddr = (addr & 3) >> 1;
109
    channel = (addr & SERIAL_MAXADDR) >> 2;
110
    s = &ser->chn[channel];
111
    switch (saddr) {
112
    case 0:
113
        newreg = 0;
114
        switch (s->reg) {
115
        case 0:
116
            newreg = val & 7;
117
            val &= 0x38;
118
            switch (val) {
119
            case 8:
120
                s->reg |= 0x8;
121
                break;
122
            case 0x20:
123
                s->rxint = 0;
124
                break;
125
            case 0x28:
126
                s->txint = 0;
127
                break;
128
            default:
129
                break;
130
            }
131
            break;
132
        case 1 ... 8:
133
        case 10 ... 15:
134
            s->wregs[s->reg] = val;
135
            break;
136
        case 9:
137
            switch (val & 0xc0) {
138
            case 0:
139
            default:
140
                break;
141
            case 0x40:
142
                slavio_serial_reset_chn(&ser->chn[1]);
143
                return;
144
            case 0x80:
145
                slavio_serial_reset_chn(&ser->chn[0]);
146
                return;
147
            case 0xc0:
148
                slavio_serial_reset(ser);
149
                return;
150
            }
151
            break;
152
        default:
153
            break;
154
        }
155
        if (s->reg == 0)
156
            s->reg = newreg;
157
        else
158
            s->reg = 0;
159
        break;
160
    case 1:
161
        if (s->wregs[5] & 8) { // tx enabled
162
            s->tx = val;
163
            if (s->chr)
164
                qemu_chr_write(s->chr, &s->tx, 1);
165
            s->txint = 1;
166
        }
167
        break;
168
    default:
169
        break;
170
    }
171
}
172

    
173
static uint32_t slavio_serial_mem_readb(void *opaque, uint32_t addr)
174
{
175
    SerialState *ser = opaque;
176
    ChannelState *s;
177
    uint32_t saddr;
178
    uint32_t ret;
179
    int channel;
180

    
181
    saddr = (addr & 3) >> 1;
182
    channel = (addr & SERIAL_MAXADDR) >> 2;
183
    s = &ser->chn[channel];
184
    switch (saddr) {
185
    case 0:
186
        ret = s->rregs[s->reg];
187
        s->reg = 0;
188
        return ret;
189
    case 1:
190
        s->rregs[0] &= ~1;
191
        return s->rx;
192
    default:
193
        break;
194
    }
195
    return 0;
196
}
197

    
198
static int serial_can_receive(void *opaque)
199
{
200
    ChannelState *s = opaque;
201
    if (((s->wregs[3] & 1) == 0) // Rx not enabled
202
        || ((s->rregs[0] & 1) == 1)) // char already available
203
        return 0;
204
    else
205
        return 1;
206
}
207

    
208
static void serial_receive_byte(ChannelState *s, int ch)
209
{
210
    s->rregs[0] |= 1;
211
    s->rx = ch;
212
    s->rxint = 1;
213
    slavio_serial_update_irq(s);
214
}
215

    
216
static void serial_receive_break(ChannelState *s)
217
{
218
    s->rregs[0] |= 0x80;
219
    slavio_serial_update_irq(s);
220
}
221

    
222
static void serial_receive1(void *opaque, const uint8_t *buf, int size)
223
{
224
    ChannelState *s = opaque;
225
    serial_receive_byte(s, buf[0]);
226
}
227

    
228
static void serial_event(void *opaque, int event)
229
{
230
    ChannelState *s = opaque;
231
    if (event == CHR_EVENT_BREAK)
232
        serial_receive_break(s);
233
}
234

    
235
static CPUReadMemoryFunc *slavio_serial_mem_read[3] = {
236
    slavio_serial_mem_readb,
237
    slavio_serial_mem_readb,
238
    slavio_serial_mem_readb,
239
};
240

    
241
static CPUWriteMemoryFunc *slavio_serial_mem_write[3] = {
242
    slavio_serial_mem_writeb,
243
    slavio_serial_mem_writeb,
244
    slavio_serial_mem_writeb,
245
};
246

    
247
static void slavio_serial_save_chn(QEMUFile *f, ChannelState *s)
248
{
249
    qemu_put_be32s(f, &s->irq);
250
    qemu_put_be32s(f, &s->reg);
251
    qemu_put_be32s(f, &s->rxint);
252
    qemu_put_be32s(f, &s->txint);
253
    qemu_put_8s(f, &s->rx);
254
    qemu_put_8s(f, &s->tx);
255
    qemu_put_buffer(f, s->wregs, 16);
256
    qemu_put_buffer(f, s->rregs, 16);
257
}
258

    
259
static void slavio_serial_save(QEMUFile *f, void *opaque)
260
{
261
    SerialState *s = opaque;
262

    
263
    slavio_serial_save_chn(f, &s->chn[0]);
264
    slavio_serial_save_chn(f, &s->chn[1]);
265
}
266

    
267
static int slavio_serial_load_chn(QEMUFile *f, ChannelState *s, int version_id)
268
{
269
    if (version_id != 1)
270
        return -EINVAL;
271

    
272
    qemu_get_be32s(f, &s->irq);
273
    qemu_get_be32s(f, &s->reg);
274
    qemu_get_be32s(f, &s->rxint);
275
    qemu_get_be32s(f, &s->txint);
276
    qemu_get_8s(f, &s->rx);
277
    qemu_get_8s(f, &s->tx);
278
    qemu_get_buffer(f, s->wregs, 16);
279
    qemu_get_buffer(f, s->rregs, 16);
280
    return 0;
281
}
282

    
283
static int slavio_serial_load(QEMUFile *f, void *opaque, int version_id)
284
{
285
    SerialState *s = opaque;
286
    int ret;
287

    
288
    ret = slavio_serial_load_chn(f, &s->chn[0], version_id);
289
    if (ret != 0)
290
        return ret;
291
    ret = slavio_serial_load_chn(f, &s->chn[1], version_id);
292
    return ret;
293

    
294
}
295

    
296
SerialState *slavio_serial_init(int base, int irq, CharDriverState *chr1, CharDriverState *chr2)
297
{
298
    int slavio_serial_io_memory;
299
    SerialState *s;
300

    
301
    s = qemu_mallocz(sizeof(SerialState));
302
    if (!s)
303
        return NULL;
304
    s->chn[0].irq = irq;
305
    s->chn[1].irq = irq;
306
    s->chn[0].chr = chr1;
307
    s->chn[1].chr = chr2;
308

    
309
    slavio_serial_io_memory = cpu_register_io_memory(0, slavio_serial_mem_read, slavio_serial_mem_write, s);
310
    cpu_register_physical_memory(base, SERIAL_MAXADDR, slavio_serial_io_memory);
311

    
312
    if (chr1) {
313
        qemu_chr_add_read_handler(chr1, serial_can_receive, serial_receive1, &s->chn[0]);
314
        qemu_chr_add_event_handler(chr1, serial_event);
315
    }
316
    if (chr2) {
317
        qemu_chr_add_read_handler(chr2, serial_can_receive, serial_receive1, &s->chn[1]);
318
        qemu_chr_add_event_handler(chr2, serial_event);
319
    }
320
    register_savevm("slavio_serial", base, 1, slavio_serial_save, slavio_serial_load, s);
321
    qemu_register_reset(slavio_serial_reset, s);
322
    slavio_serial_reset(s);
323
    return s;
324
}
325

    
326
static void sunkbd_event(void *opaque, int ch)
327
{
328
    ChannelState *s = opaque;
329
    // XXX: PC -> Sun Type 5 translation?
330
    serial_receive_byte(s, ch);
331
}
332

    
333
static void sunmouse_event(void *opaque, 
334
                               int dx, int dy, int dz, int buttons_state)
335
{
336
    ChannelState *s = opaque;
337
    int ch;
338

    
339
    // XXX
340
    ch = 0x42;
341
    serial_receive_byte(s, ch);
342
}
343

    
344
void slavio_serial_ms_kbd_init(int base, int irq)
345
{
346
    int slavio_serial_io_memory;
347
    SerialState *s;
348

    
349
    s = qemu_mallocz(sizeof(SerialState));
350
    if (!s)
351
        return;
352
    s->chn[0].irq = irq;
353
    s->chn[1].irq = irq;
354
    s->chn[0].chr = NULL;
355
    s->chn[1].chr = NULL;
356

    
357
    slavio_serial_io_memory = cpu_register_io_memory(0, slavio_serial_mem_read, slavio_serial_mem_write, s);
358
    cpu_register_physical_memory(base, SERIAL_MAXADDR, slavio_serial_io_memory);
359

    
360
    qemu_add_kbd_event_handler(sunkbd_event, &s->chn[0]);
361
    qemu_add_mouse_event_handler(sunmouse_event, &s->chn[1]);
362
    qemu_register_reset(slavio_serial_reset, s);
363
    slavio_serial_reset(s);
364
}