Subversion Repositories HelenOS

Rev

Rev 4343 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
982 decky 1
/*
2071 jermar 2
 * Copyright (c) 2006 Martin Decky
982 decky 3
 * All rights reserved.
4
 *
5
 * Redistribution and use in source and binary forms, with or without
6
 * modification, are permitted provided that the following conditions
7
 * are met:
8
 *
9
 * - Redistributions of source code must retain the above copyright
10
 *   notice, this list of conditions and the following disclaimer.
11
 * - Redistributions in binary form must reproduce the above copyright
12
 *   notice, this list of conditions and the following disclaimer in the
13
 *   documentation and/or other materials provided with the distribution.
14
 * - The name of the author may not be used to endorse or promote products
15
 *   derived from this software without specific prior written permission.
16
 *
17
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19
 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20
 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26
 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27
 */
28
 
1734 decky 29
/** @addtogroup ppc32  
1702 cejka 30
 * @{
31
 */
32
/** @file
33
 */
34
 
982 decky 35
#include <arch/drivers/cuda.h>
36
#include <arch/asm.h>
987 decky 37
#include <console/console.h>
1628 decky 38
#include <console/chardev.h>
1480 palkovsky 39
#include <arch/drivers/pic.h>
1625 decky 40
#include <sysinfo/sysinfo.h>
1480 palkovsky 41
#include <interrupt.h>
1619 decky 42
#include <stdarg.h>
982 decky 43
 
1928 decky 44
#define CUDA_IRQ 10
1633 decky 45
#define SPECIAL     '?'
46
 
1619 decky 47
#define PACKET_ADB  0x00
48
#define PACKET_CUDA 0x01
49
 
2227 decky 50
#define CUDA_POWERDOWN  0x0a
51
#define CUDA_RESET      0x11
982 decky 52
 
53
#define RS 0x200
54
#define B (0 * RS)
55
#define A (1 * RS)
56
#define SR (10 * RS)
57
#define ACR (11 * RS)
58
 
59
#define SR_OUT 0x10
60
#define TACK 0x10
61
#define TIP 0x20
62
 
63
 
1780 jermar 64
static volatile uint8_t *cuda = NULL;
1928 decky 65
static irq_t cuda_irq;      /**< Cuda's IRQ. */
982 decky 66
 
1619 decky 67
static char lchars[0x80] = {
1633 decky 68
    'a',
69
    's',
70
    'd',
71
    'f',
72
    'h',
73
    'g',
74
    'z',
75
    'x',
76
    'c',
77
    'v',
78
    SPECIAL,
79
    'b',
80
    'q',
81
    'w',
82
    'e',
83
    'r',
84
    'y',
85
    't',
86
    '1',
87
    '2',
88
    '3',
89
    '4',
90
    '6',
91
    '5',
92
    '=',
93
    '9',
94
    '7',
95
    '-',
96
    '8',
97
    '0',
98
    ']',
99
    'o',
100
    'u',
101
    '[',
102
    'i',
103
    'p',
104
    '\n',    /* Enter */
105
    'l',
106
    'j',
107
    '\'',
108
    'k',
109
    ';',
110
    '\\',
111
    ',',
112
    '/',
113
    'n',
114
    'm',
115
    '.',
116
    '\t',    /* Tab */
117
    ' ',
118
    '`',
119
    '\b',    /* Backspace */
120
    SPECIAL,
121
    SPECIAL, /* Escape */
122
    SPECIAL, /* Ctrl */
123
    SPECIAL, /* Alt */
124
    SPECIAL, /* Shift */
125
    SPECIAL, /* Caps-Lock */
126
    SPECIAL, /* RAlt */
127
    SPECIAL, /* Left */
128
    SPECIAL, /* Right */
129
    SPECIAL, /* Down */
130
    SPECIAL, /* Up */
131
    SPECIAL,
132
    SPECIAL,
133
    '.',     /* Keypad . */
134
    SPECIAL,
135
    '*',     /* Keypad * */
136
    SPECIAL,
137
    '+',     /* Keypad + */
138
    SPECIAL,
139
    SPECIAL, /* NumLock */
140
    SPECIAL,
141
    SPECIAL,
142
    SPECIAL,
143
    '/',     /* Keypad / */
144
    '\n',    /* Keypad Enter */
145
    SPECIAL,
146
    '-',     /* Keypad - */
147
    SPECIAL,
148
    SPECIAL,
149
    SPECIAL,
150
    '0',     /* Keypad 0 */
151
    '1',     /* Keypad 1 */
152
    '2',     /* Keypad 2 */
153
    '3',     /* Keypad 3 */
154
    '4',     /* Keypad 4 */
155
    '5',     /* Keypad 5 */
156
    '6',     /* Keypad 6 */
157
    '7',     /* Keypad 7 */
158
    SPECIAL,
159
    '8',     /* Keypad 8 */
160
    '9',     /* Keypad 9 */
161
    SPECIAL,
162
    SPECIAL,
163
    SPECIAL,
164
    SPECIAL, /* F5 */
165
    SPECIAL, /* F6 */
166
    SPECIAL, /* F7 */
167
    SPECIAL, /* F3 */
168
    SPECIAL, /* F8 */
169
    SPECIAL, /* F9 */
170
    SPECIAL,
171
    SPECIAL, /* F11 */
172
    SPECIAL,
173
    SPECIAL, /* F13 */
174
    SPECIAL,
175
    SPECIAL, /* ScrollLock */
176
    SPECIAL,
177
    SPECIAL, /* F10 */
178
    SPECIAL,
179
    SPECIAL, /* F12 */
180
    SPECIAL,
181
    SPECIAL, /* Pause */
182
    SPECIAL, /* Insert */
183
    SPECIAL, /* Home */
184
    SPECIAL, /* PageUp */
185
    SPECIAL, /* Delete */
186
    SPECIAL, /* F4 */
187
    SPECIAL, /* End */
188
    SPECIAL, /* F2 */
189
    SPECIAL, /* PageDown */
190
    SPECIAL  /* F1 */
1619 decky 191
};
192
 
193
 
1780 jermar 194
static void receive_packet(uint8_t *kind, index_t count, uint8_t data[])
1619 decky 195
{
196
    cuda[B] = cuda[B] & ~TIP;
197
    *kind = cuda[SR];
198
 
199
    index_t i;
200
    for (i = 0; i < count; i++)
201
        data[i] = cuda[SR];
202
 
203
    cuda[B] = cuda[B] | TIP;
204
}
205
 
206
 
1606 decky 207
/* Called from getc(). */
208
static void cuda_resume(chardev_t *d)
209
{
210
}
211
 
212
 
213
/* Called from getc(). */
214
static void cuda_suspend(chardev_t *d)
215
{
216
}
217
 
218
 
219
static char key_read(chardev_t *d)
220
{
221
    char ch;
222
 
223
    ch = 0;
224
    return ch;
225
}
226
 
227
 
1628 decky 228
static chardev_t kbrd;
1606 decky 229
static chardev_operations_t ops = {
230
    .suspend = cuda_suspend,
231
    .resume = cuda_resume,
232
    .read = key_read
233
};
234
 
1619 decky 235
 
1633 decky 236
int cuda_get_scancode(void)
1480 palkovsky 237
{
4341 svoboda 238
    if (cuda) {
239
        uint8_t kind;
240
        uint8_t data[4];
241
 
242
        receive_packet(&kind, 4, data);
243
 
244
        if ((kind == PACKET_ADB) && (data[0] == 0x40) && (data[1] == 0x2c))
245
            return data[2];
246
    }
1619 decky 247
 
1633 decky 248
    return -1;
1480 palkovsky 249
}
982 decky 250
 
4343 svoboda 251
static void cuda_irq_handler(irq_t *irq)
1628 decky 252
{
4344 svoboda 253
    int scan_code = cuda_get_scancode();
1928 decky 254
 
4344 svoboda 255
    if (scan_code != -1) {
256
        uint8_t scancode = (uint8_t) scan_code;
257
        if ((scancode & 0x80) != 0x80)
258
            chardev_push_character(&kbrd, lchars[scancode & 0x7f]);
1633 decky 259
    }
1628 decky 260
}
261
 
4344 svoboda 262
static irq_ownership_t cuda_claim(irq_t *irq)
1928 decky 263
{
264
    return IRQ_ACCEPT;
265
}
1628 decky 266
 
1928 decky 267
void cuda_init(devno_t devno, uintptr_t base, size_t size)
990 decky 268
{
4341 svoboda 269
    cuda = (uint8_t *) hw_map(base, size);
1619 decky 270
 
1606 decky 271
    chardev_initialize("cuda_kbd", &kbrd, &ops);
272
    stdin = &kbrd;
1625 decky 273
 
1928 decky 274
    irq_initialize(&cuda_irq);
275
    cuda_irq.devno = devno;
276
    cuda_irq.inr = CUDA_IRQ;
277
    cuda_irq.claim = cuda_claim;
278
    cuda_irq.handler = cuda_irq_handler;
279
    irq_register(&cuda_irq);
280
 
281
    pic_enable_interrupt(CUDA_IRQ);
4341 svoboda 282
 
1928 decky 283
    sysinfo_set_item_val("kbd", NULL, true);
284
    sysinfo_set_item_val("kbd.devno", NULL, devno);
285
    sysinfo_set_item_val("kbd.inr", NULL, CUDA_IRQ);
286
    sysinfo_set_item_val("kbd.address.virtual", NULL, base);
990 decky 287
}
288
 
289
 
2227 decky 290
static void send_packet(const uint8_t kind, count_t count, ...)
1628 decky 291
{
292
    index_t i;
293
    va_list va;
294
 
295
    cuda[B] = cuda[B] | TIP;
296
    cuda[ACR] = cuda[ACR] | SR_OUT;
297
    cuda[SR] = kind;
298
    cuda[B] = cuda[B] & ~TIP;
299
 
300
    va_start(va, count);
301
 
302
    for (i = 0; i < count; i++) {
303
        cuda[ACR] = cuda[ACR] | SR_OUT;
304
        cuda[SR] = va_arg(va, int);
305
        cuda[B] = cuda[B] | TACK;
306
    }
307
 
308
    va_end(va);
309
 
310
    cuda[B] = cuda[B] | TIP;
311
}
312
 
313
 
982 decky 314
void cpu_halt(void) {
1269 decky 315
    asm volatile (
316
        "b 0\n"
317
    );
982 decky 318
}
1702 cejka 319
 
2227 decky 320
void arch_reboot(void) {
4341 svoboda 321
    if (cuda)
322
        send_packet(PACKET_CUDA, 1, CUDA_RESET);
323
 
2227 decky 324
    asm volatile (
325
        "b 0\n"
326
    );
327
}
328
 
1734 decky 329
/** @}
1702 cejka 330
 */