Statistics
| Branch: | Revision:

root / hw / slavio_serial.c @ 5fafdf24

History | View | Annotate | Download (17.9 kB)

1
/*
2
 * QEMU Sparc SLAVIO serial port emulation
3
 *
4
 * Copyright (c) 2003-2005 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
/* debug serial */
26
//#define DEBUG_SERIAL
27

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

    
31
/* debug 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
/*
46
 * Modifications:
47
 *  2006-Aug-10  Igor Kovalenko :   Renamed KBDQueue to SERIOQueue, implemented
48
 *                                  serial mouse queue.
49
 *                                  Implemented serial mouse protocol.
50
 */
51

    
52
#ifdef DEBUG_SERIAL
53
#define SER_DPRINTF(fmt, args...) \
54
do { printf("SER: " fmt , ##args); } while (0)
55
#else
56
#define SER_DPRINTF(fmt, args...)
57
#endif
58
#ifdef DEBUG_KBD
59
#define KBD_DPRINTF(fmt, args...) \
60
do { printf("KBD: " fmt , ##args); } while (0)
61
#else
62
#define KBD_DPRINTF(fmt, args...)
63
#endif
64
#ifdef DEBUG_MOUSE
65
#define MS_DPRINTF(fmt, args...) \
66
do { printf("MSC: " fmt , ##args); } while (0)
67
#else
68
#define MS_DPRINTF(fmt, args...)
69
#endif
70

    
71
typedef enum {
72
    chn_a, chn_b,
73
} chn_id_t;
74

    
75
#define CHN_C(s) ((s)->chn == chn_b? 'b' : 'a')
76

    
77
typedef enum {
78
    ser, kbd, mouse,
79
} chn_type_t;
80

    
81
#define SERIO_QUEUE_SIZE 256
82

    
83
typedef struct {
84
    uint8_t data[SERIO_QUEUE_SIZE];
85
    int rptr, wptr, count;
86
} SERIOQueue;
87

    
88
typedef struct ChannelState {
89
    qemu_irq irq;
90
    int reg;
91
    int rxint, txint, rxint_under_svc, txint_under_svc;
92
    chn_id_t chn; // this channel, A (base+4) or B (base+0)
93
    chn_type_t type;
94
    struct ChannelState *otherchn;
95
    uint8_t rx, tx, wregs[16], rregs[16];
96
    SERIOQueue queue;
97
    CharDriverState *chr;
98
} ChannelState;
99

    
100
struct SerialState {
101
    struct ChannelState chn[2];
102
};
103

    
104
#define SERIAL_MAXADDR 7
105
#define SERIAL_SIZE (SERIAL_MAXADDR + 1)
106

    
107
static void handle_kbd_command(ChannelState *s, int val);
108
static int serial_can_receive(void *opaque);
109
static void serial_receive_byte(ChannelState *s, int ch);
110
static inline void set_txint(ChannelState *s);
111

    
112
static void clear_queue(void *opaque)
113
{
114
    ChannelState *s = opaque;
115
    SERIOQueue *q = &s->queue;
116
    q->rptr = q->wptr = q->count = 0;
117
}
118

    
119
static void put_queue(void *opaque, int b)
120
{
121
    ChannelState *s = opaque;
122
    SERIOQueue *q = &s->queue;
123

    
124
    SER_DPRINTF("channel %c put: 0x%02x\n", CHN_C(s), b);
125
    if (q->count >= SERIO_QUEUE_SIZE)
126
        return;
127
    q->data[q->wptr] = b;
128
    if (++q->wptr == SERIO_QUEUE_SIZE)
129
        q->wptr = 0;
130
    q->count++;
131
    serial_receive_byte(s, 0);
132
}
133

    
134
static uint32_t get_queue(void *opaque)
135
{
136
    ChannelState *s = opaque;
137
    SERIOQueue *q = &s->queue;
138
    int val;
139
   
140
    if (q->count == 0) {
141
        return 0;
142
    } else {
143
        val = q->data[q->rptr];
144
        if (++q->rptr == SERIO_QUEUE_SIZE)
145
            q->rptr = 0;
146
        q->count--;
147
    }
148
    SER_DPRINTF("channel %c get 0x%02x\n", CHN_C(s), val);
149
    if (q->count > 0)
150
        serial_receive_byte(s, 0);
151
    return val;
152
}
153

    
154
static int slavio_serial_update_irq_chn(ChannelState *s)
155
{
156
    if ((s->wregs[1] & 1) && // interrupts enabled
157
        (((s->wregs[1] & 2) && s->txint == 1) || // tx ints enabled, pending
158
         ((((s->wregs[1] & 0x18) == 8) || ((s->wregs[1] & 0x18) == 0x10)) &&
159
          s->rxint == 1) || // rx ints enabled, pending
160
         ((s->wregs[15] & 0x80) && (s->rregs[0] & 0x80)))) { // break int e&p
161
        return 1;
162
    }
163
    return 0;
164
}
165

    
166
static void slavio_serial_update_irq(ChannelState *s)
167
{
168
    int irq;
169

    
170
    irq = slavio_serial_update_irq_chn(s);
171
    irq |= slavio_serial_update_irq_chn(s->otherchn);
172

    
173
    SER_DPRINTF("IRQ = %d\n", irq);
174
    qemu_set_irq(s->irq, irq);
175
}
176

    
177
static void slavio_serial_reset_chn(ChannelState *s)
178
{
179
    int i;
180

    
181
    s->reg = 0;
182
    for (i = 0; i < SERIAL_SIZE; i++) {
183
        s->rregs[i] = 0;
184
        s->wregs[i] = 0;
185
    }
186
    s->wregs[4] = 4;
187
    s->wregs[9] = 0xc0;
188
    s->wregs[11] = 8;
189
    s->wregs[14] = 0x30;
190
    s->wregs[15] = 0xf8;
191
    s->rregs[0] = 0x44;
192
    s->rregs[1] = 6;
193

    
194
    s->rx = s->tx = 0;
195
    s->rxint = s->txint = 0;
196
    s->rxint_under_svc = s->txint_under_svc = 0;
197
    clear_queue(s);
198
}
199

    
200
static void slavio_serial_reset(void *opaque)
201
{
202
    SerialState *s = opaque;
203
    slavio_serial_reset_chn(&s->chn[0]);
204
    slavio_serial_reset_chn(&s->chn[1]);
205
}
206

    
207
static inline void clr_rxint(ChannelState *s)
208
{
209
    s->rxint = 0;
210
    s->rxint_under_svc = 0;
211
    if (s->chn == chn_a) {
212
        if (s->wregs[9] & 0x10)
213
            s->otherchn->rregs[2] = 0x60;
214
        else
215
            s->otherchn->rregs[2] = 0x06;
216
        s->rregs[3] &= ~0x20;
217
    } else {
218
        if (s->wregs[9] & 0x10)
219
            s->rregs[2] = 0x60;
220
        else
221
            s->rregs[2] = 0x06;
222
        s->otherchn->rregs[3] &= ~4;
223
    }
224
    if (s->txint)
225
        set_txint(s);
226
    slavio_serial_update_irq(s);
227
}
228

    
229
static inline void set_rxint(ChannelState *s)
230
{
231
    s->rxint = 1;
232
    if (!s->txint_under_svc) {
233
        s->rxint_under_svc = 1;
234
        if (s->chn == chn_a) {
235
            if (s->wregs[9] & 0x10)
236
                s->otherchn->rregs[2] = 0x30;
237
            else
238
                s->otherchn->rregs[2] = 0x0c;
239
        } else {
240
            if (s->wregs[9] & 0x10)
241
                s->rregs[2] = 0x20;
242
            else
243
                s->rregs[2] = 0x04;
244
        }
245
    }
246
    if (s->chn == chn_a)
247
        s->rregs[3] |= 0x20;
248
    else
249
        s->otherchn->rregs[3] |= 4;
250
    slavio_serial_update_irq(s);
251
}
252

    
253
static inline void clr_txint(ChannelState *s)
254
{
255
    s->txint = 0;
256
    s->txint_under_svc = 0;
257
    if (s->chn == chn_a) {
258
        if (s->wregs[9] & 0x10)
259
            s->otherchn->rregs[2] = 0x60;
260
        else
261
            s->otherchn->rregs[2] = 0x06;
262
        s->rregs[3] &= ~0x10;
263
    } else {
264
        if (s->wregs[9] & 0x10)
265
            s->rregs[2] = 0x60;
266
        else
267
            s->rregs[2] = 0x06;
268
        s->otherchn->rregs[3] &= ~2;
269
    }
270
    if (s->rxint)
271
        set_rxint(s);
272
    slavio_serial_update_irq(s);
273
}
274

    
275
static inline void set_txint(ChannelState *s)
276
{
277
    s->txint = 1;
278
    if (!s->rxint_under_svc) {
279
        s->txint_under_svc = 1;
280
        if (s->chn == chn_a) {
281
            if (s->wregs[9] & 0x10)
282
                s->otherchn->rregs[2] = 0x10;
283
            else
284
                s->otherchn->rregs[2] = 0x08;
285
        } else {
286
            s->rregs[2] = 0;
287
        }
288
    }
289
    if (s->chn == chn_a)
290
        s->rregs[3] |= 0x10;
291
    else
292
        s->otherchn->rregs[3] |= 2;
293
    slavio_serial_update_irq(s);
294
}
295

    
296
static void slavio_serial_update_parameters(ChannelState *s)
297
{
298
    int speed, parity, data_bits, stop_bits;
299
    QEMUSerialSetParams ssp;
300

    
301
    if (!s->chr || s->type != ser)
302
        return;
303

    
304
    if (s->wregs[4] & 1) {
305
        if (s->wregs[4] & 2)
306
            parity = 'E';
307
        else
308
            parity = 'O';
309
    } else {
310
        parity = 'N';
311
    }
312
    if ((s->wregs[4] & 0x0c) == 0x0c)
313
        stop_bits = 2;
314
    else
315
        stop_bits = 1;
316
    switch (s->wregs[5] & 0x60) {
317
    case 0x00:
318
        data_bits = 5;
319
        break;
320
    case 0x20:
321
        data_bits = 7;
322
        break;
323
    case 0x40:
324
        data_bits = 6;
325
        break;
326
    default:
327
    case 0x60:
328
        data_bits = 8;
329
        break;
330
    }
331
    speed = 2457600 / ((s->wregs[12] | (s->wregs[13] << 8)) + 2);
332
    switch (s->wregs[4] & 0xc0) {
333
    case 0x00:
334
        break;
335
    case 0x40:
336
        speed /= 16;
337
        break;
338
    case 0x80:
339
        speed /= 32;
340
        break;
341
    default:
342
    case 0xc0:
343
        speed /= 64;
344
        break;
345
    }
346
    ssp.speed = speed;
347
    ssp.parity = parity;
348
    ssp.data_bits = data_bits;
349
    ssp.stop_bits = stop_bits;
350
    SER_DPRINTF("channel %c: speed=%d parity=%c data=%d stop=%d\n", CHN_C(s),
351
                speed, parity, data_bits, stop_bits);
352
    qemu_chr_ioctl(s->chr, CHR_IOCTL_SERIAL_SET_PARAMS, &ssp);
353
}
354

    
355
static void slavio_serial_mem_writeb(void *opaque, target_phys_addr_t addr, uint32_t val)
356
{
357
    SerialState *serial = opaque;
358
    ChannelState *s;
359
    uint32_t saddr;
360
    int newreg, channel;
361

    
362
    val &= 0xff;
363
    saddr = (addr & 3) >> 1;
364
    channel = (addr & SERIAL_MAXADDR) >> 2;
365
    s = &serial->chn[channel];
366
    switch (saddr) {
367
    case 0:
368
        SER_DPRINTF("Write channel %c, reg[%d] = %2.2x\n", CHN_C(s), s->reg, val & 0xff);
369
        newreg = 0;
370
        switch (s->reg) {
371
        case 0:
372
            newreg = val & 7;
373
            val &= 0x38;
374
            switch (val) {
375
            case 8:
376
                newreg |= 0x8;
377
                break;
378
            case 0x28:
379
                clr_txint(s);
380
                break;
381
            case 0x38:
382
                if (s->rxint_under_svc)
383
                    clr_rxint(s);
384
                else if (s->txint_under_svc)
385
                    clr_txint(s);
386
                break;
387
            default:
388
                break;
389
            }
390
            break;
391
        case 1 ... 3:
392
        case 6 ... 8:
393
        case 10 ... 11:
394
        case 14 ... 15:
395
            s->wregs[s->reg] = val;
396
            break;
397
        case 4:
398
        case 5:
399
        case 12:
400
        case 13:
401
            s->wregs[s->reg] = val;
402
            slavio_serial_update_parameters(s);
403
            break;
404
        case 9:
405
            switch (val & 0xc0) {
406
            case 0:
407
            default:
408
                break;
409
            case 0x40:
410
                slavio_serial_reset_chn(&serial->chn[1]);
411
                return;
412
            case 0x80:
413
                slavio_serial_reset_chn(&serial->chn[0]);
414
                return;
415
            case 0xc0:
416
                slavio_serial_reset(serial);
417
                return;
418
            }
419
            break;
420
        default:
421
            break;
422
        }
423
        if (s->reg == 0)
424
            s->reg = newreg;
425
        else
426
            s->reg = 0;
427
        break;
428
    case 1:
429
        SER_DPRINTF("Write channel %c, ch %d\n", CHN_C(s), val);
430
        s->tx = val;
431
        if (s->wregs[5] & 8) { // tx enabled
432
            if (s->chr)
433
                qemu_chr_write(s->chr, &s->tx, 1);
434
            else if (s->type == kbd) {
435
                handle_kbd_command(s, val);
436
            }
437
        }
438
        s->rregs[0] |= 4; // Tx buffer empty
439
        s->rregs[1] |= 1; // All sent
440
        set_txint(s);
441
        break;
442
    default:
443
        break;
444
    }
445
}
446

    
447
static uint32_t slavio_serial_mem_readb(void *opaque, target_phys_addr_t addr)
448
{
449
    SerialState *serial = opaque;
450
    ChannelState *s;
451
    uint32_t saddr;
452
    uint32_t ret;
453
    int channel;
454

    
455
    saddr = (addr & 3) >> 1;
456
    channel = (addr & SERIAL_MAXADDR) >> 2;
457
    s = &serial->chn[channel];
458
    switch (saddr) {
459
    case 0:
460
        SER_DPRINTF("Read channel %c, reg[%d] = %2.2x\n", CHN_C(s), s->reg, s->rregs[s->reg]);
461
        ret = s->rregs[s->reg];
462
        s->reg = 0;
463
        return ret;
464
    case 1:
465
        s->rregs[0] &= ~1;
466
        clr_rxint(s);
467
        if (s->type == kbd || s->type == mouse)
468
            ret = get_queue(s);
469
        else
470
            ret = s->rx;
471
        SER_DPRINTF("Read channel %c, ch %d\n", CHN_C(s), ret);
472
        return ret;
473
    default:
474
        break;
475
    }
476
    return 0;
477
}
478

    
479
static int serial_can_receive(void *opaque)
480
{
481
    ChannelState *s = opaque;
482
    int ret;
483

    
484
    if (((s->wregs[3] & 1) == 0) // Rx not enabled
485
        || ((s->rregs[0] & 1) == 1)) // char already available
486
        ret = 0;
487
    else
488
        ret = 1;
489
    //SER_DPRINTF("channel %c can receive %d\n", CHN_C(s), ret);
490
    return ret;
491
}
492

    
493
static void serial_receive_byte(ChannelState *s, int ch)
494
{
495
    SER_DPRINTF("channel %c put ch %d\n", CHN_C(s), ch);
496
    s->rregs[0] |= 1;
497
    s->rx = ch;
498
    set_rxint(s);
499
}
500

    
501
static void serial_receive_break(ChannelState *s)
502
{
503
    s->rregs[0] |= 0x80;
504
    slavio_serial_update_irq(s);
505
}
506

    
507
static void serial_receive1(void *opaque, const uint8_t *buf, int size)
508
{
509
    ChannelState *s = opaque;
510
    serial_receive_byte(s, buf[0]);
511
}
512

    
513
static void serial_event(void *opaque, int event)
514
{
515
    ChannelState *s = opaque;
516
    if (event == CHR_EVENT_BREAK)
517
        serial_receive_break(s);
518
}
519

    
520
static CPUReadMemoryFunc *slavio_serial_mem_read[3] = {
521
    slavio_serial_mem_readb,
522
    slavio_serial_mem_readb,
523
    slavio_serial_mem_readb,
524
};
525

    
526
static CPUWriteMemoryFunc *slavio_serial_mem_write[3] = {
527
    slavio_serial_mem_writeb,
528
    slavio_serial_mem_writeb,
529
    slavio_serial_mem_writeb,
530
};
531

    
532
static void slavio_serial_save_chn(QEMUFile *f, ChannelState *s)
533
{
534
    int tmp;
535
    tmp = 0;
536
    qemu_put_be32s(f, &tmp); /* unused, was IRQ.  */
537
    qemu_put_be32s(f, &s->reg);
538
    qemu_put_be32s(f, &s->rxint);
539
    qemu_put_be32s(f, &s->txint);
540
    qemu_put_be32s(f, &s->rxint_under_svc);
541
    qemu_put_be32s(f, &s->txint_under_svc);
542
    qemu_put_8s(f, &s->rx);
543
    qemu_put_8s(f, &s->tx);
544
    qemu_put_buffer(f, s->wregs, 16);
545
    qemu_put_buffer(f, s->rregs, 16);
546
}
547

    
548
static void slavio_serial_save(QEMUFile *f, void *opaque)
549
{
550
    SerialState *s = opaque;
551

    
552
    slavio_serial_save_chn(f, &s->chn[0]);
553
    slavio_serial_save_chn(f, &s->chn[1]);
554
}
555

    
556
static int slavio_serial_load_chn(QEMUFile *f, ChannelState *s, int version_id)
557
{
558
    int tmp;
559

    
560
    if (version_id > 2)
561
        return -EINVAL;
562

    
563
    qemu_get_be32s(f, &tmp); /* unused */
564
    qemu_get_be32s(f, &s->reg);
565
    qemu_get_be32s(f, &s->rxint);
566
    qemu_get_be32s(f, &s->txint);
567
    if (version_id >= 2) {
568
        qemu_get_be32s(f, &s->rxint_under_svc);
569
        qemu_get_be32s(f, &s->txint_under_svc);
570
    }
571
    qemu_get_8s(f, &s->rx);
572
    qemu_get_8s(f, &s->tx);
573
    qemu_get_buffer(f, s->wregs, 16);
574
    qemu_get_buffer(f, s->rregs, 16);
575
    return 0;
576
}
577

    
578
static int slavio_serial_load(QEMUFile *f, void *opaque, int version_id)
579
{
580
    SerialState *s = opaque;
581
    int ret;
582

    
583
    ret = slavio_serial_load_chn(f, &s->chn[0], version_id);
584
    if (ret != 0)
585
        return ret;
586
    ret = slavio_serial_load_chn(f, &s->chn[1], version_id);
587
    return ret;
588

    
589
}
590

    
591
SerialState *slavio_serial_init(target_phys_addr_t base, qemu_irq irq,
592
                                CharDriverState *chr1, CharDriverState *chr2)
593
{
594
    int slavio_serial_io_memory, i;
595
    SerialState *s;
596

    
597
    s = qemu_mallocz(sizeof(SerialState));
598
    if (!s)
599
        return NULL;
600

    
601
    slavio_serial_io_memory = cpu_register_io_memory(0, slavio_serial_mem_read, slavio_serial_mem_write, s);
602
    cpu_register_physical_memory(base, SERIAL_SIZE, slavio_serial_io_memory);
603

    
604
    s->chn[0].chr = chr1;
605
    s->chn[1].chr = chr2;
606

    
607
    for (i = 0; i < 2; i++) {
608
        s->chn[i].irq = irq;
609
        s->chn[i].chn = 1 - i;
610
        s->chn[i].type = ser;
611
        if (s->chn[i].chr) {
612
            qemu_chr_add_handlers(s->chn[i].chr, serial_can_receive,
613
                                  serial_receive1, serial_event, &s->chn[i]);
614
        }
615
    }
616
    s->chn[0].otherchn = &s->chn[1];
617
    s->chn[1].otherchn = &s->chn[0];
618
    register_savevm("slavio_serial", base, 2, slavio_serial_save, slavio_serial_load, s);
619
    qemu_register_reset(slavio_serial_reset, s);
620
    slavio_serial_reset(s);
621
    return s;
622
}
623

    
624
static const uint8_t keycodes[128] = {
625
    127, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 43, 53,
626
    54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 89, 76, 77, 78,
627
    79, 80, 81, 82, 83, 84, 85, 86, 87, 42, 99, 88, 100, 101, 102, 103,
628
    104, 105, 106, 107, 108, 109, 110, 47, 19, 121, 119, 5, 6, 8, 10, 12,
629
    14, 16, 17, 18, 7, 98, 23, 68, 69, 70, 71, 91, 92, 93, 125, 112,
630
    113, 114, 94, 50, 0, 0, 124, 9, 11, 0, 0, 0, 0, 0, 0, 0,
631
    90, 0, 46, 22, 13, 111, 52, 20, 96, 24, 28, 74, 27, 123, 44, 66,
632
    0, 45, 2, 4, 48, 0, 0, 21, 0, 0, 0, 0, 0, 120, 122, 67,
633
};
634

    
635
static void sunkbd_event(void *opaque, int ch)
636
{
637
    ChannelState *s = opaque;
638
    int release = ch & 0x80;
639

    
640
    ch = keycodes[ch & 0x7f];
641
    KBD_DPRINTF("Keycode %d (%s)\n", ch, release? "release" : "press");
642
    put_queue(s, ch | release);
643
}
644

    
645
static void handle_kbd_command(ChannelState *s, int val)
646
{
647
    KBD_DPRINTF("Command %d\n", val);
648
    switch (val) {
649
    case 1: // Reset, return type code
650
        clear_queue(s);
651
        put_queue(s, 0xff);
652
        put_queue(s, 4); // Type 4
653
        break;
654
    case 7: // Query layout
655
    case 0xf:
656
        clear_queue(s);
657
        put_queue(s, 0xfe);
658
        put_queue(s, 19); // XXX, layout?
659
        break;
660
    default:
661
        break;
662
    }
663
}
664

    
665
static void sunmouse_event(void *opaque,
666
                               int dx, int dy, int dz, int buttons_state)
667
{
668
    ChannelState *s = opaque;
669
    int ch;
670

    
671
    MS_DPRINTF("dx=%d dy=%d buttons=%01x\n", dx, dy, buttons_state);
672

    
673
    ch = 0x80 | 0x7; /* protocol start byte, no buttons pressed */
674

    
675
    if (buttons_state & MOUSE_EVENT_LBUTTON)
676
        ch ^= 0x4;
677
    if (buttons_state & MOUSE_EVENT_MBUTTON)
678
        ch ^= 0x2;
679
    if (buttons_state & MOUSE_EVENT_RBUTTON)
680
        ch ^= 0x1;
681

    
682
    put_queue(s, ch);
683

    
684
    ch = dx;
685

    
686
    if (ch > 127)
687
        ch=127;
688
    else if (ch < -127)
689
        ch=-127;
690

    
691
    put_queue(s, ch & 0xff);
692

    
693
    ch = -dy;
694

    
695
    if (ch > 127)
696
        ch=127;
697
    else if (ch < -127)
698
        ch=-127;
699

    
700
    put_queue(s, ch & 0xff);
701

    
702
    // MSC protocol specify two extra motion bytes
703

    
704
    put_queue(s, 0);
705
    put_queue(s, 0);
706
}
707

    
708
void slavio_serial_ms_kbd_init(target_phys_addr_t base, qemu_irq irq)
709
{
710
    int slavio_serial_io_memory, i;
711
    SerialState *s;
712

    
713
    s = qemu_mallocz(sizeof(SerialState));
714
    if (!s)
715
        return;
716
    for (i = 0; i < 2; i++) {
717
        s->chn[i].irq = irq;
718
        s->chn[i].chn = 1 - i;
719
        s->chn[i].chr = NULL;
720
    }
721
    s->chn[0].otherchn = &s->chn[1];
722
    s->chn[1].otherchn = &s->chn[0];
723
    s->chn[0].type = mouse;
724
    s->chn[1].type = kbd;
725

    
726
    slavio_serial_io_memory = cpu_register_io_memory(0, slavio_serial_mem_read, slavio_serial_mem_write, s);
727
    cpu_register_physical_memory(base, SERIAL_SIZE, slavio_serial_io_memory);
728

    
729
    qemu_add_mouse_event_handler(sunmouse_event, &s->chn[0], 0, "QEMU Sun Mouse");
730
    qemu_add_kbd_event_handler(sunkbd_event, &s->chn[1]);
731
    register_savevm("slavio_serial_mouse", base, 2, slavio_serial_save, slavio_serial_load, s);
732
    qemu_register_reset(slavio_serial_reset, s);
733
    slavio_serial_reset(s);
734
}