46
57
if (env->pending_interrupts == 0)
47
58
cpu_reset_interrupt(env, CPU_INTERRUPT_HARD);
49
#if defined(PPC_DEBUG_IRQ)
50
if (loglevel & CPU_LOG_INT) {
51
fprintf(logfile, "%s: %p n_IRQ %d level %d => pending %08" PRIx32
60
LOG_IRQ("%s: %p n_IRQ %d level %d => pending %08" PRIx32
52
61
"req %08x\n", __func__, env, n_IRQ, level,
53
62
env->pending_interrupts, env->interrupt_request);
58
65
/* PowerPC 6xx / 7xx internal IRQ controller */
61
68
CPUState *env = opaque;
64
#if defined(PPC_DEBUG_IRQ)
65
if (loglevel & CPU_LOG_INT) {
66
fprintf(logfile, "%s: env %p pin %d level %d\n", __func__,
71
LOG_IRQ("%s: env %p pin %d level %d\n", __func__,
70
73
cur_level = (env->irq_input_state >> pin) & 1;
71
74
/* Don't generate spurious events */
72
75
if ((cur_level == 1 && level == 0) || (cur_level == 0 && level != 0)) {
74
77
case PPC6xx_INPUT_TBEN:
75
78
/* Level sensitive - active high */
76
#if defined(PPC_DEBUG_IRQ)
77
if (loglevel & CPU_LOG_INT) {
78
fprintf(logfile, "%s: %s the time base\n",
79
LOG_IRQ("%s: %s the time base\n",
79
80
__func__, level ? "start" : "stop");
83
82
cpu_ppc_tb_start(env);
87
86
case PPC6xx_INPUT_INT:
88
87
/* Level sensitive - active high */
89
#if defined(PPC_DEBUG_IRQ)
90
if (loglevel & CPU_LOG_INT) {
91
fprintf(logfile, "%s: set the external IRQ state to %d\n",
88
LOG_IRQ("%s: set the external IRQ state to %d\n",
95
90
ppc_set_irq(env, PPC_INTERRUPT_EXT, level);
97
92
case PPC6xx_INPUT_SMI:
98
93
/* Level sensitive - active high */
99
#if defined(PPC_DEBUG_IRQ)
100
if (loglevel & CPU_LOG_INT) {
101
fprintf(logfile, "%s: set the SMI IRQ state to %d\n",
94
LOG_IRQ("%s: set the SMI IRQ state to %d\n",
105
96
ppc_set_irq(env, PPC_INTERRUPT_SMI, level);
107
98
case PPC6xx_INPUT_MCP:
124
111
/* XXX: TODO: relay the signal to CKSTP_OUT pin */
125
112
/* XXX: Note that the only way to restart the CPU is to reset it */
127
#if defined(PPC_DEBUG_IRQ)
128
if (loglevel & CPU_LOG_INT) {
129
fprintf(logfile, "%s: stop the CPU\n", __func__);
114
LOG_IRQ("%s: stop the CPU\n", __func__);
135
118
case PPC6xx_INPUT_HRESET:
136
119
/* Level sensitive - active low */
138
#if defined(PPC_DEBUG_IRQ)
139
if (loglevel & CPU_LOG_INT) {
140
fprintf(logfile, "%s: reset the CPU\n", __func__);
121
LOG_IRQ("%s: reset the CPU\n", __func__);
143
122
env->interrupt_request |= CPU_INTERRUPT_EXITTB;
152
131
case PPC6xx_INPUT_SRESET:
153
#if defined(PPC_DEBUG_IRQ)
154
if (loglevel & CPU_LOG_INT) {
155
fprintf(logfile, "%s: set the RESET IRQ state to %d\n",
132
LOG_IRQ("%s: set the RESET IRQ state to %d\n",
156
133
__func__, level);
159
134
ppc_set_irq(env, PPC_INTERRUPT_RESET, level);
162
137
/* Unknown pin - do nothing */
163
#if defined(PPC_DEBUG_IRQ)
164
if (loglevel & CPU_LOG_INT) {
165
fprintf(logfile, "%s: unknown IRQ pin %d\n", __func__, pin);
138
LOG_IRQ("%s: unknown IRQ pin %d\n", __func__, pin);
187
158
CPUState *env = opaque;
190
#if defined(PPC_DEBUG_IRQ)
191
if (loglevel & CPU_LOG_INT) {
192
fprintf(logfile, "%s: env %p pin %d level %d\n", __func__,
161
LOG_IRQ("%s: env %p pin %d level %d\n", __func__,
193
162
env, pin, level);
196
163
cur_level = (env->irq_input_state >> pin) & 1;
197
164
/* Don't generate spurious events */
198
165
if ((cur_level == 1 && level == 0) || (cur_level == 0 && level != 0)) {
200
167
case PPC970_INPUT_INT:
201
168
/* Level sensitive - active high */
202
#if defined(PPC_DEBUG_IRQ)
203
if (loglevel & CPU_LOG_INT) {
204
fprintf(logfile, "%s: set the external IRQ state to %d\n",
169
LOG_IRQ("%s: set the external IRQ state to %d\n",
205
170
__func__, level);
208
171
ppc_set_irq(env, PPC_INTERRUPT_EXT, level);
210
173
case PPC970_INPUT_THINT:
211
174
/* Level sensitive - active high */
212
#if defined(PPC_DEBUG_IRQ)
213
if (loglevel & CPU_LOG_INT) {
214
fprintf(logfile, "%s: set the SMI IRQ state to %d\n", __func__,
175
LOG_IRQ("%s: set the SMI IRQ state to %d\n", __func__,
218
177
ppc_set_irq(env, PPC_INTERRUPT_THERM, level);
220
179
case PPC970_INPUT_MCP:
236
191
/* Level sensitive - active low */
237
192
/* XXX: TODO: relay the signal to CKSTP_OUT pin */
239
#if defined(PPC_DEBUG_IRQ)
240
if (loglevel & CPU_LOG_INT) {
241
fprintf(logfile, "%s: stop the CPU\n", __func__);
194
LOG_IRQ("%s: stop the CPU\n", __func__);
246
#if defined(PPC_DEBUG_IRQ)
247
if (loglevel & CPU_LOG_INT) {
248
fprintf(logfile, "%s: restart the CPU\n", __func__);
197
LOG_IRQ("%s: restart the CPU\n", __func__);
255
202
/* Level sensitive - active low */
257
204
#if 0 // XXX: TOFIX
258
#if defined(PPC_DEBUG_IRQ)
259
if (loglevel & CPU_LOG_INT) {
260
fprintf(logfile, "%s: reset the CPU\n", __func__);
205
LOG_IRQ("%s: reset the CPU\n", __func__);
267
210
case PPC970_INPUT_SRESET:
268
#if defined(PPC_DEBUG_IRQ)
269
if (loglevel & CPU_LOG_INT) {
270
fprintf(logfile, "%s: set the RESET IRQ state to %d\n",
211
LOG_IRQ("%s: set the RESET IRQ state to %d\n",
271
212
__func__, level);
274
213
ppc_set_irq(env, PPC_INTERRUPT_RESET, level);
276
215
case PPC970_INPUT_TBEN:
277
#if defined(PPC_DEBUG_IRQ)
278
if (loglevel & CPU_LOG_INT) {
279
fprintf(logfile, "%s: set the TBEN state to %d\n", __func__,
216
LOG_IRQ("%s: set the TBEN state to %d\n", __func__,
286
221
/* Unknown pin - do nothing */
287
#if defined(PPC_DEBUG_IRQ)
288
if (loglevel & CPU_LOG_INT) {
289
fprintf(logfile, "%s: unknown IRQ pin %d\n", __func__, pin);
222
LOG_IRQ("%s: unknown IRQ pin %d\n", __func__, pin);
311
242
CPUState *env = opaque;
314
#if defined(PPC_DEBUG_IRQ)
315
if (loglevel & CPU_LOG_INT) {
316
fprintf(logfile, "%s: env %p pin %d level %d\n", __func__,
245
LOG_IRQ("%s: env %p pin %d level %d\n", __func__,
317
246
env, pin, level);
320
247
cur_level = (env->irq_input_state >> pin) & 1;
321
248
/* Don't generate spurious events */
322
249
if ((cur_level == 1 && level == 0) || (cur_level == 0 && level != 0)) {
324
251
case PPC40x_INPUT_RESET_SYS:
326
#if defined(PPC_DEBUG_IRQ)
327
if (loglevel & CPU_LOG_INT) {
328
fprintf(logfile, "%s: reset the PowerPC system\n",
253
LOG_IRQ("%s: reset the PowerPC system\n",
332
255
ppc40x_system_reset(env);
335
258
case PPC40x_INPUT_RESET_CHIP:
337
#if defined(PPC_DEBUG_IRQ)
338
if (loglevel & CPU_LOG_INT) {
339
fprintf(logfile, "%s: reset the PowerPC chip\n", __func__);
260
LOG_IRQ("%s: reset the PowerPC chip\n", __func__);
342
261
ppc40x_chip_reset(env);
345
264
case PPC40x_INPUT_RESET_CORE:
346
265
/* XXX: TODO: update DBSR[MRR] */
348
#if defined(PPC_DEBUG_IRQ)
349
if (loglevel & CPU_LOG_INT) {
350
fprintf(logfile, "%s: reset the PowerPC core\n", __func__);
267
LOG_IRQ("%s: reset the PowerPC core\n", __func__);
353
268
ppc40x_core_reset(env);
356
271
case PPC40x_INPUT_CINT:
357
272
/* Level sensitive - active high */
358
#if defined(PPC_DEBUG_IRQ)
359
if (loglevel & CPU_LOG_INT) {
360
fprintf(logfile, "%s: set the critical IRQ state to %d\n",
273
LOG_IRQ("%s: set the critical IRQ state to %d\n",
361
274
__func__, level);
364
275
ppc_set_irq(env, PPC_INTERRUPT_CEXT, level);
366
277
case PPC40x_INPUT_INT:
367
278
/* Level sensitive - active high */
368
#if defined(PPC_DEBUG_IRQ)
369
if (loglevel & CPU_LOG_INT) {
370
fprintf(logfile, "%s: set the external IRQ state to %d\n",
279
LOG_IRQ("%s: set the external IRQ state to %d\n",
371
280
__func__, level);
374
281
ppc_set_irq(env, PPC_INTERRUPT_EXT, level);
376
283
case PPC40x_INPUT_HALT:
377
284
/* Level sensitive - active low */
379
#if defined(PPC_DEBUG_IRQ)
380
if (loglevel & CPU_LOG_INT) {
381
fprintf(logfile, "%s: stop the CPU\n", __func__);
286
LOG_IRQ("%s: stop the CPU\n", __func__);
386
#if defined(PPC_DEBUG_IRQ)
387
if (loglevel & CPU_LOG_INT) {
388
fprintf(logfile, "%s: restart the CPU\n", __func__);
289
LOG_IRQ("%s: restart the CPU\n", __func__);
394
293
case PPC40x_INPUT_DEBUG:
395
294
/* Level sensitive - active high */
396
#if defined(PPC_DEBUG_IRQ)
397
if (loglevel & CPU_LOG_INT) {
398
fprintf(logfile, "%s: set the debug pin state to %d\n",
295
LOG_IRQ("%s: set the debug pin state to %d\n",
399
296
__func__, level);
402
297
ppc_set_irq(env, PPC_INTERRUPT_DEBUG, level);
405
300
/* Unknown pin - do nothing */
406
#if defined(PPC_DEBUG_IRQ)
407
if (loglevel & CPU_LOG_INT) {
408
fprintf(logfile, "%s: unknown IRQ pin %d\n", __func__, pin);
301
LOG_IRQ("%s: unknown IRQ pin %d\n", __func__, pin);
423
314
env, PPC40x_INPUT_NB);
317
/* PowerPC E500 internal IRQ controller */
318
static void ppce500_set_irq (void *opaque, int pin, int level)
320
CPUState *env = opaque;
323
LOG_IRQ("%s: env %p pin %d level %d\n", __func__,
325
cur_level = (env->irq_input_state >> pin) & 1;
326
/* Don't generate spurious events */
327
if ((cur_level == 1 && level == 0) || (cur_level == 0 && level != 0)) {
329
case PPCE500_INPUT_MCK:
331
LOG_IRQ("%s: reset the PowerPC system\n",
333
qemu_system_reset_request();
336
case PPCE500_INPUT_RESET_CORE:
338
LOG_IRQ("%s: reset the PowerPC core\n", __func__);
339
ppc_set_irq(env, PPC_INTERRUPT_MCK, level);
342
case PPCE500_INPUT_CINT:
343
/* Level sensitive - active high */
344
LOG_IRQ("%s: set the critical IRQ state to %d\n",
346
ppc_set_irq(env, PPC_INTERRUPT_CEXT, level);
348
case PPCE500_INPUT_INT:
349
/* Level sensitive - active high */
350
LOG_IRQ("%s: set the core IRQ state to %d\n",
352
ppc_set_irq(env, PPC_INTERRUPT_EXT, level);
354
case PPCE500_INPUT_DEBUG:
355
/* Level sensitive - active high */
356
LOG_IRQ("%s: set the debug pin state to %d\n",
358
ppc_set_irq(env, PPC_INTERRUPT_DEBUG, level);
361
/* Unknown pin - do nothing */
362
LOG_IRQ("%s: unknown IRQ pin %d\n", __func__, pin);
366
env->irq_input_state |= 1 << pin;
368
env->irq_input_state &= ~(1 << pin);
372
void ppce500_irq_init (CPUState *env)
374
env->irq_inputs = (void **)qemu_allocate_irqs(&ppce500_set_irq,
375
env, PPCE500_INPUT_NB);
426
377
/*****************************************************************************/
427
378
/* PowerPC time base and decrementer emulation */
428
379
struct ppc_tb_t {
882
797
env->spr[SPR_40x_TSR] |= 1 << 26;
883
798
if ((env->spr[SPR_40x_TCR] >> 23) & 0x1)
884
799
ppc_set_irq(env, PPC_INTERRUPT_FIT, 1);
887
fprintf(logfile, "%s: ir %d TCR " ADDRX " TSR " ADDRX "\n", __func__,
800
LOG_TB("%s: ir %d TCR " ADDRX " TSR " ADDRX "\n", __func__,
888
801
(int)((env->spr[SPR_40x_TCR] >> 23) & 0x1),
889
802
env->spr[SPR_40x_TCR], env->spr[SPR_40x_TSR]);
894
805
/* Programmable interval timer */
902
813
!((env->spr[SPR_40x_TCR] >> 26) & 0x1) ||
903
814
(is_excp && !((env->spr[SPR_40x_TCR] >> 22) & 0x1))) {
907
fprintf(logfile, "%s: stop PIT\n", __func__);
816
LOG_TB("%s: stop PIT\n", __func__);
910
817
qemu_del_timer(tb_env->decr_timer);
914
fprintf(logfile, "%s: start PIT %016" PRIx64 "\n",
819
LOG_TB("%s: start PIT %016" PRIx64 "\n",
915
820
__func__, ppcemb_timer->pit_reload);
918
821
now = qemu_get_clock(vm_clock);
919
822
next = now + muldiv64(ppcemb_timer->pit_reload,
920
823
ticks_per_sec, tb_env->decr_freq);
940
843
if ((env->spr[SPR_40x_TCR] >> 26) & 0x1)
941
844
ppc_set_irq(env, PPC_INTERRUPT_PIT, 1);
942
845
start_stop_pit(env, tb_env, 1);
945
fprintf(logfile, "%s: ar %d ir %d TCR " ADDRX " TSR " ADDRX " "
846
LOG_TB("%s: ar %d ir %d TCR " ADDRX " TSR " ADDRX " "
946
847
"%016" PRIx64 "\n", __func__,
947
848
(int)((env->spr[SPR_40x_TCR] >> 22) & 0x1),
948
849
(int)((env->spr[SPR_40x_TCR] >> 26) & 0x1),
949
850
env->spr[SPR_40x_TCR], env->spr[SPR_40x_TSR],
950
851
ppcemb_timer->pit_reload);
955
854
/* Watchdog timer */
1094
973
ppcemb_timer_t *ppcemb_timer;
1096
975
tb_env = qemu_mallocz(sizeof(ppc_tb_t));
1097
if (tb_env == NULL) {
1100
976
env->tb_env = tb_env;
1101
977
ppcemb_timer = qemu_mallocz(sizeof(ppcemb_timer_t));
1102
978
tb_env->tb_freq = freq;
1103
979
tb_env->decr_freq = freq;
1104
980
tb_env->opaque = ppcemb_timer;
1106
if (loglevel != 0) {
1107
fprintf(logfile, "%s freq %" PRIu32 "\n", __func__, freq);
981
LOG_TB("%s freq %" PRIu32 "\n", __func__, freq);
1110
982
if (ppcemb_timer != NULL) {
1111
983
/* We use decr timer for PIT */
1112
984
tb_env->decr_timer = qemu_new_timer(vm_clock, &cpu_4xx_pit_cb, env);