Subversion Repositories HelenOS

Rev

Rev 4615 | Go to most recent revision | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 4615 Rev 4628
Line 48... Line 48...
48
#include <genarch/fb/visuals.h>
48
#include <genarch/fb/visuals.h>
49
 
49
 
50
/* Addresses of devices. */
50
/* Addresses of devices. */
51
#define QEMU_ICP_VIDEORAM            0x16000000
51
#define QEMU_ICP_VIDEORAM            0x16000000
52
#define QEMU_ICP_KBD                 0x18000000
52
#define QEMU_ICP_KBD                 0x18000000
-
 
53
#define ICP_KBD_STAT             0x04
-
 
54
#define ICP_KBD_DATA             0x08
-
 
55
#define ICP_KBD_INTR_STAT        0x10
53
#define QEMU_ICP_HALT_OFFSET         0x10
56
#define QEMU_ICP_HALT_OFFSET         0x10
54
#define QEMU_ICP_RTC                 0x13000000
57
#define QEMU_ICP_RTC                 0x13000000
55
#define QEMU_ICP_RTC1_LOAD_OFFSET    0x100
58
#define QEMU_ICP_RTC1_LOAD_OFFSET    0x100
56
#define QEMU_ICP_RTC1_READ_OFFSET    0x104
59
#define QEMU_ICP_RTC1_READ_OFFSET    0x104
57
#define QEMU_ICP_RTC1_CTL_OFFSET     0x108
60
#define QEMU_ICP_RTC1_CTL_OFFSET     0x108
Line 61... Line 64...
61
#define QEMU_ICP_IRQC                0x14000000
64
#define QEMU_ICP_IRQC                0x14000000
62
#define QEMU_ICP_IRQC_MASK_OFFSET    0xC
65
#define QEMU_ICP_IRQC_MASK_OFFSET    0xC
63
#define QEMU_ICP_IRQC_UNMASK_OFFSET  0x8
66
#define QEMU_ICP_IRQC_UNMASK_OFFSET  0x8
64
#define QEMU_ICP_MP                  0x11000000
67
#define QEMU_ICP_MP                  0x11000000
65
#define QEMU_ICP_MP_MEMSIZE_OFFSET   0x0090
68
#define QEMU_ICP_MP_MEMSIZE_OFFSET   0x0090
66
#define QEMU_ICP_FB                  0x94000
69
#define QEMU_ICP_FB                  0x01000000
67
 
70
 
68
#define ICP_VGA              0xC0000000
71
#define ICP_VGA              0xC0000000
69
#define ICP_CMCR             0x10000000
72
#define ICP_CMCR             0x10000000
70
 
73
 
71
/* IRQs */
74
/* IRQs */
Line 143... Line 146...
143
 
146
 
144
/** Initializes #qemu_icp_hw_map. */
147
/** Initializes #qemu_icp_hw_map. */
145
void qemu_icp_hw_map_init(void)
148
void qemu_icp_hw_map_init(void)
146
{
149
{
147
    qemu_icp_hw_map.videoram = hw_map(QEMU_ICP_VIDEORAM, PAGE_SIZE);
150
    qemu_icp_hw_map.videoram = hw_map(QEMU_ICP_VIDEORAM, PAGE_SIZE);
148
    qemu_icp_hw_map.kbd = hw_map(QEMU_ICP_KBD, PAGE_SIZE);
151
    qemu_icp_hw_map.kbd_ctrl = hw_map(QEMU_ICP_KBD, PAGE_SIZE);
-
 
152
    qemu_icp_hw_map.kbd_stat = qemu_icp_hw_map.kbd_ctrl + ICP_KBD_STAT;
-
 
153
    qemu_icp_hw_map.kbd_data = qemu_icp_hw_map.kbd_ctrl + ICP_KBD_DATA;
-
 
154
    qemu_icp_hw_map.kbd_intstat = qemu_icp_hw_map.kbd_ctrl + ICP_KBD_INTR_STAT;
149
    qemu_icp_hw_map.rtc = hw_map(QEMU_ICP_RTC, PAGE_SIZE);
155
    qemu_icp_hw_map.rtc = hw_map(QEMU_ICP_RTC, PAGE_SIZE);
150
    qemu_icp_hw_map.rtc1_load = qemu_icp_hw_map.rtc + QEMU_ICP_RTC1_LOAD_OFFSET;
156
    qemu_icp_hw_map.rtc1_load = qemu_icp_hw_map.rtc + QEMU_ICP_RTC1_LOAD_OFFSET;
151
    qemu_icp_hw_map.rtc1_read = qemu_icp_hw_map.rtc + QEMU_ICP_RTC1_READ_OFFSET;
157
    qemu_icp_hw_map.rtc1_read = qemu_icp_hw_map.rtc + QEMU_ICP_RTC1_READ_OFFSET;
152
    qemu_icp_hw_map.rtc1_ctl = qemu_icp_hw_map.rtc + QEMU_ICP_RTC1_CTL_OFFSET;
158
    qemu_icp_hw_map.rtc1_ctl = qemu_icp_hw_map.rtc + QEMU_ICP_RTC1_CTL_OFFSET;
153
    qemu_icp_hw_map.rtc1_intrclr = qemu_icp_hw_map.rtc + QEMU_ICP_RTC1_INTRCLR_OFFSET;
159
    qemu_icp_hw_map.rtc1_intrclr = qemu_icp_hw_map.rtc + QEMU_ICP_RTC1_INTRCLR_OFFSET;
Line 205... Line 211...
205
static char qemu_icp_do_read(chardev_t *dev)
211
static char qemu_icp_do_read(chardev_t *dev)
206
{
212
{
207
    char ch;
213
    char ch;
208
 
214
 
209
    while (1) {
215
    while (1) {
210
        ch = *((volatile char *) qemu_icp_hw_map.kbd);
216
        ch = *((volatile char *) qemu_icp_hw_map.kbd_data);
211
        if (ch) {
217
        if (ch) {
212
            if (ch == '\r')
218
            if (ch == '\r')
213
                return '\n';
219
                return '\n';
214
            if (ch == 0x7f)
220
            if (ch == 0x7f)
215
                return '\b';
221
                return '\b';
Line 228... Line 234...
228
    if ((irq->notif_cfg.notify) && (irq->notif_cfg.answerbox)) {
234
    if ((irq->notif_cfg.notify) && (irq->notif_cfg.answerbox)) {
229
        ipc_irq_send_notif(irq);
235
        ipc_irq_send_notif(irq);
230
    } else {
236
    } else {
231
        char ch = 0;
237
        char ch = 0;
232
       
238
       
233
        ch = *((char *) qemu_icp_hw_map.kbd);
239
        ch = *((char *) qemu_icp_hw_map.kbd_data);
234
        if (ch == '\r') {
240
        if (ch == '\r') {
235
            ch = '\n';
241
            ch = '\n';
236
        }
242
        }
237
        if (ch == 0x7f) {
243
        if (ch == 0x7f) {
238
            ch = '\b';
244
            ch = '\b';
Line 273... Line 279...
273
 *
279
 *
274
 *  @param devno device number.
280
 *  @param devno device number.
275
 */
281
 */
276
void qemu_icp_console_init(devno_t devno)
282
void qemu_icp_console_init(devno_t devno)
277
{
283
{
278
    qemu_icp_irqc_mask(QEMU_ICP_KBD_IRQ);
-
 
279
    chardev_initialize("qemu_icp_console", &console, &qemu_icp_ops);
284
    chardev_initialize("qemu_icp_console", &console, &qemu_icp_ops);
280
    stdin = &console;
285
    stdin = &console;
281
    stdout = &console;
286
    stdout = &console;
282
   
287
   
-
 
288
    qemu_icp_irqc_mask(QEMU_ICP_KBD_IRQ);
283
    irq_initialize(&qemu_icp_console_irq);
289
    irq_initialize(&qemu_icp_console_irq);
284
    qemu_icp_console_irq.devno = devno;
290
    qemu_icp_console_irq.devno = devno;
285
    qemu_icp_console_irq.inr = QEMU_ICP_KBD_IRQ;
291
    qemu_icp_console_irq.inr = QEMU_ICP_KBD_IRQ;
286
    qemu_icp_console_irq.claim = qemu_icp_claim;
292
    qemu_icp_console_irq.claim = qemu_icp_claim;
287
    qemu_icp_console_irq.handler = qemu_icp_irq_handler;
293
    qemu_icp_console_irq.handler = qemu_icp_irq_handler;
288
    irq_register(&qemu_icp_console_irq);
294
    irq_register(&qemu_icp_console_irq);
-
 
295
 
-
 
296
    *(char *)qemu_icp_hw_map.kbd_ctrl = 0x17;
289
   
297
   
290
    qemu_icp_irqc_unmask(QEMU_ICP_KBD_IRQ);
298
    qemu_icp_irqc_unmask(QEMU_ICP_KBD_IRQ);
291
   
299
   
292
    sysinfo_set_item_val("kbd", NULL, true);
300
    sysinfo_set_item_val("kbd", NULL, true);
293
    sysinfo_set_item_val("kbd.devno", NULL, devno);
301
    sysinfo_set_item_val("kbd.devno", NULL, devno);
294
    sysinfo_set_item_val("kbd.inr", NULL, QEMU_ICP_KBD_IRQ);
302
    sysinfo_set_item_val("kbd.inr", NULL, QEMU_ICP_KBD_IRQ);
295
    sysinfo_set_item_val("kbd.address.virtual", NULL, qemu_icp_hw_map.kbd);
303
    sysinfo_set_item_val("kbd.address.virtual", NULL, qemu_icp_hw_map.kbd_data);
296
}
304
}
297
 
305
 
298
/** Starts qemu_icp Real Time Clock device, which asserts regular interrupts.
306
/** Starts qemu_icp Real Time Clock device, which asserts regular interrupts.
299
 *
307
 *
300
 * @param frequency Interrupts frequency (0 disables RTC).
308
 * @param frequency Interrupts frequency (0 disables RTC).
Line 308... Line 316...
308
    qemu_icp_irqc_unmask(QEMU_ICP_TIMER_IRQ);
316
    qemu_icp_irqc_unmask(QEMU_ICP_TIMER_IRQ);
309
}
317
}
310
 
318
 
311
static irq_ownership_t qemu_icp_timer_claim(void)
319
static irq_ownership_t qemu_icp_timer_claim(void)
312
{
320
{
313
    *((uint32_t*) qemu_icp_hw_map.rtc1_intrclr) = 1;
-
 
314
    return IRQ_ACCEPT;
321
    return IRQ_ACCEPT;
315
}
322
}
316
 
323
 
317
/** Timer interrupt handler.
324
/** Timer interrupt handler.
318
 *
325
 *
Line 323... Line 330...
323
{
330
{
324
    /*
331
    /*
325
    * We are holding a lock which prevents preemption.
332
    * We are holding a lock which prevents preemption.
326
    * Release the lock, call clock() and reacquire the lock again.
333
    * Release the lock, call clock() and reacquire the lock again.
327
    */
334
    */
-
 
335
    *((uint32_t*) qemu_icp_hw_map.rtc1_intrclr) = 1;
328
    spinlock_unlock(&irq->lock);
336
    spinlock_unlock(&irq->lock);
329
    clock();
337
    clock();
330
    spinlock_lock(&irq->lock);
338
    spinlock_lock(&irq->lock);
331
 
339
 
332
}
340
}
Line 384... Line 392...
384
}
392
}
385
 
393
 
386
/** Stops qemu_icp. */
394
/** Stops qemu_icp. */
387
void qemu_icp_cpu_halt(void)
395
void qemu_icp_cpu_halt(void)
388
{
396
{
389
    char * addr = 0;
-
 
390
    if (!hw_map_init_called) {
-
 
391
        addr = (char *) QEMU_ICP_KBD;
-
 
392
    } else {
397
    while (1);
393
        addr = (char *) qemu_icp_hw_map.videoram;
-
 
394
    }
-
 
395
   
-
 
396
    *(addr + QEMU_ICP_HALT_OFFSET) = '\0';
-
 
397
}
398
}
398
 
399
 
399
/** Gxemul specific interrupt exception handler.
400
/** Gxemul specific interrupt exception handler.
400
 *
401
 *
401
 * Determines sources of the interrupt from interrupt controller and
402
 * Determines sources of the interrupt from interrupt controller and