Subversion Repositories HelenOS

Rev

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

Rev 2412 Rev 2414
Line 44... Line 44...
44
#include <mm/page.h>
44
#include <mm/page.h>
45
#include <arch/machine.h>
45
#include <arch/machine.h>
46
#include <arch/debug/print.h>
46
#include <arch/debug/print.h>
47
 
47
 
48
 
48
 
49
/** Addresses of devices. */
49
/* Addresses of devices. */
50
#define GXEMUL_VIDEORAM            0x10000000
50
#define GXEMUL_VIDEORAM            0x10000000
51
#define GXEMUL_KBD                 0x10000000
51
#define GXEMUL_KBD                 0x10000000
52
#define GXEMUL_HALT_OFFSET         0x10
52
#define GXEMUL_HALT_OFFSET         0x10
53
#define GXEMUL_RTC                 0x15000000
53
#define GXEMUL_RTC                 0x15000000
54
#define GXEMUL_RTC_FREQ_OFFSET     0x100
54
#define GXEMUL_RTC_FREQ_OFFSET     0x100
Line 59... Line 59...
59
#define GXEMUL_MP                  0x11000000
59
#define GXEMUL_MP                  0x11000000
60
#define GXEMUL_MP_MEMSIZE_OFFSET   0x0090
60
#define GXEMUL_MP_MEMSIZE_OFFSET   0x0090
61
#define GXEMUL_FB                  0x12000000
61
#define GXEMUL_FB                  0x12000000
62
 
62
 
63
 
63
 
64
/** IRQs */
64
/* IRQs */
65
#define GXEMUL_KBD_IRQ      2
65
#define GXEMUL_KBD_IRQ      2
66
#define GXEMUL_TIMER_IRQ    4
66
#define GXEMUL_TIMER_IRQ    4
67
 
67
 
68
static gxemul_hw_map_t gxemul_hw_map;
68
static gxemul_hw_map_t gxemul_hw_map;
69
static chardev_t console;
69
static chardev_t console;
70
static irq_t gxemul_irq;
70
static irq_t gxemul_console_irq;
71
static irq_t gxemul_timer_irq;
71
static irq_t gxemul_timer_irq;
72
 
72
 
73
static bool hw_map_init_called = false;
73
static bool hw_map_init_called = false;
74
 
74
 
-
 
75
static void gxemul_kbd_enable(chardev_t *dev);
-
 
76
static void gxemul_kbd_disable(chardev_t *dev);
75
static void gxemul_write(chardev_t *dev, const char ch);
77
static void gxemul_write(chardev_t *dev, const char ch);
76
static void gxemul_enable(chardev_t *dev);
-
 
77
static void gxemul_disable(chardev_t *dev);
-
 
78
static char gxemul_do_read(chardev_t *dev);
78
static char gxemul_do_read(chardev_t *dev);
79
 
79
 
80
static chardev_operations_t gxemul_ops = {
80
static chardev_operations_t gxemul_ops = {
81
    .resume = gxemul_enable,
81
    .resume = gxemul_kbd_enable,
82
    .suspend = gxemul_disable,
82
    .suspend = gxemul_kbd_disable,
83
    .write = gxemul_write,
83
    .write = gxemul_write,
84
    .read = gxemul_do_read,
84
    .read = gxemul_do_read,
85
};
85
};
86
 
86
 
87
 
87
 
Line 127... Line 127...
127
 
127
 
128
    hw_map_init_called = true;
128
    hw_map_init_called = true;
129
}
129
}
130
 
130
 
131
 
131
 
132
/** Putchar that works with gxemul */
132
/** Putchar that works with gxemul.
-
 
133
 *
-
 
134
 * @param dev Not used.
-
 
135
 * @param ch Characted to be printed.
-
 
136
 */
133
static void gxemul_write(chardev_t *dev, const char ch)
137
static void gxemul_write(chardev_t *dev, const char ch)
134
{
138
{
135
    *((char *) gxemul_hw_map.videoram) = ch;
139
    *((char *) gxemul_hw_map.videoram) = ch;
136
}
140
}
137
 
141
 
138
 
142
 
-
 
143
/** Enables gxemul keyboard (interrupt unmasked).
-
 
144
 *
-
 
145
 * @param dev Not used.
-
 
146
 *
139
/* Called from getc(). */
147
 * Called from getc().
-
 
148
 */
140
static void gxemul_enable(chardev_t *dev)
149
static void gxemul_kbd_enable(chardev_t *dev)
141
{
150
{
142
    gxemul_irqc_unmask(GXEMUL_KBD_IRQ);
151
    gxemul_irqc_unmask(GXEMUL_KBD_IRQ);
143
}
152
}
144
 
153
 
145
 
154
 
-
 
155
/** Disables gxemul keyboard (interrupt masked).
-
 
156
 *
-
 
157
 * @param dev not used
-
 
158
 *
146
/* Called from getc(). */
159
 * Called from getc().
-
 
160
 */
147
static void gxemul_disable(chardev_t *dev)
161
static void gxemul_kbd_disable(chardev_t *dev)
148
{
162
{
149
    gxemul_irqc_mask(GXEMUL_KBD_IRQ);
163
    gxemul_irqc_mask(GXEMUL_KBD_IRQ);
150
}
164
}
151
 
165
 
152
 
166
 
Line 169... Line 183...
169
        }
183
        }
170
    }
184
    }
171
}
185
}
172
 
186
 
173
 
187
 
174
/** Process keyboard interrupt. */
188
/** Process keyboard interrupt.
-
 
189
 *  
-
 
190
 *  @param irq IRQ information.
-
 
191
 *  @param arg Not used.
-
 
192
 */
175
static void gxemul_irq_handler(irq_t *irq, void *arg, ...)
193
static void gxemul_irq_handler(irq_t *irq, void *arg, ...)
176
{
194
{
177
    if ((irq->notif_cfg.notify) && (irq->notif_cfg.answerbox)) {
195
    if ((irq->notif_cfg.notify) && (irq->notif_cfg.answerbox)) {
178
        ipc_irq_send_notif(irq);
196
        ipc_irq_send_notif(irq);
179
    } else {
197
    } else {
Line 199... Line 217...
199
 
217
 
200
/** Acquire console back for kernel. */
218
/** Acquire console back for kernel. */
201
void gxemul_grab_console(void)
219
void gxemul_grab_console(void)
202
{
220
{
203
    ipl_t ipl = interrupts_disable();
221
    ipl_t ipl = interrupts_disable();
204
    spinlock_lock(&gxemul_irq.lock);
222
    spinlock_lock(&gxemul_console_irq.lock);
205
    gxemul_irq.notif_cfg.notify = false;
223
    gxemul_console_irq.notif_cfg.notify = false;
206
    spinlock_unlock(&gxemul_irq.lock);
224
    spinlock_unlock(&gxemul_console_irq.lock);
207
    interrupts_restore(ipl);
225
    interrupts_restore(ipl);
208
}
226
}
209
 
227
 
210
 
228
 
211
/** Return console to userspace. */
229
/** Return console to userspace. */
212
void gxemul_release_console(void)
230
void gxemul_release_console(void)
213
{
231
{
214
    ipl_t ipl = interrupts_disable();
232
    ipl_t ipl = interrupts_disable();
215
    spinlock_lock(&gxemul_irq.lock);
233
    spinlock_lock(&gxemul_console_irq.lock);
216
    if (gxemul_irq.notif_cfg.answerbox) {
234
    if (gxemul_console_irq.notif_cfg.answerbox) {
217
        gxemul_irq.notif_cfg.notify = true;
235
        gxemul_console_irq.notif_cfg.notify = true;
218
    }
236
    }
219
    spinlock_unlock(&gxemul_irq.lock);
237
    spinlock_unlock(&gxemul_console_irq.lock);
220
    interrupts_restore(ipl);
238
    interrupts_restore(ipl);
221
}
239
}
222
 
240
 
223
 
241
 
224
/** Initializes console object representing gxemul console.
242
/** Initializes console object representing gxemul console.
Line 229... Line 247...
229
{
247
{
230
    chardev_initialize("gxemul_console", &console, &gxemul_ops);
248
    chardev_initialize("gxemul_console", &console, &gxemul_ops);
231
    stdin = &console;
249
    stdin = &console;
232
    stdout = &console;
250
    stdout = &console;
233
   
251
   
234
    irq_initialize(&gxemul_irq);
252
    irq_initialize(&gxemul_console_irq);
235
    gxemul_irq.devno = devno;
253
    gxemul_console_irq.devno = devno;
236
    gxemul_irq.inr = GXEMUL_KBD_IRQ;
254
    gxemul_console_irq.inr = GXEMUL_KBD_IRQ;
237
    gxemul_irq.claim = gxemul_claim;
255
    gxemul_console_irq.claim = gxemul_claim;
238
    gxemul_irq.handler = gxemul_irq_handler;
256
    gxemul_console_irq.handler = gxemul_irq_handler;
239
    irq_register(&gxemul_irq);
257
    irq_register(&gxemul_console_irq);
240
   
258
   
241
    gxemul_irqc_unmask(GXEMUL_KBD_IRQ);
259
    gxemul_irqc_unmask(GXEMUL_KBD_IRQ);
242
   
260
   
243
    sysinfo_set_item_val("kbd", NULL, true);
261
    sysinfo_set_item_val("kbd", NULL, true);
244
    sysinfo_set_item_val("kbd.devno", NULL, devno);
262
    sysinfo_set_item_val("kbd.devno", NULL, devno);
Line 269... Line 287...
269
 * @param irq Interrupt information.
287
 * @param irq Interrupt information.
270
 * @param arg Not used.
288
 * @param arg Not used.
271
 */
289
 */
272
static void gxemul_timer_irq_handler(irq_t *irq, void *arg, ...)
290
static void gxemul_timer_irq_handler(irq_t *irq, void *arg, ...)
273
{
291
{
274
    /* TODO time drifts ??
-
 
275
    unsigned long drift;
-
 
276
 
-
 
277
    drift = cp0_count_read() - nextcount;
-
 
278
    while (drift > cp0_compare_value) {
-
 
279
        drift -= cp0_compare_value;
-
 
280
        CPU->missed_clock_ticks++;
-
 
281
    }
-
 
282
    nextcount = cp0_count_read() + cp0_compare_value - drift;
-
 
283
    cp0_compare_write(nextcount);
-
 
284
    */
-
 
285
 
-
 
286
    /*
292
    /*
287
    * We are holding a lock which prevents preemption.
293
    * We are holding a lock which prevents preemption.
288
    * Release the lock, call clock() and reacquire the lock again.
294
    * Release the lock, call clock() and reacquire the lock again.
289
    */
295
    */
290
    spinlock_unlock(&irq->lock);
296
    spinlock_unlock(&irq->lock);
291
    clock();
297
    clock();
292
    spinlock_lock(&irq->lock);
298
    spinlock_lock(&irq->lock);
293
 
299
 
294
    /* acknowledge tick */
300
    /* acknowledge tick */
295
    *(uint32_t*) gxemul_hw_map.rtc_ack = 0;
301
    *(uint32_t*) gxemul_hw_map.rtc_ack = 0;
296
   
-
 
297
    /* TODO what's that? *
-
 
298
    if (virtual_timer_fnc != NULL)
-
 
299
        virtual_timer_fnc();
-
 
300
    */
-
 
301
}
302
}
302
 
303
 
303
 
304
 
304
/** Initializes and registers timer interrupt handler. */
305
/** Initializes and registers timer interrupt handler. */
305
static void gxemul_timer_irq_init()
306
static void gxemul_timer_irq_init()