Fix up the mac68k interrupt handlers to work with the new style common

clockframe layout and remove the CLOCK_FORMAT0 work-around.  As a nice
side-effect, this also eliminates the super-sketchy stack unwinding used
by rtclock_intr to get at the interrupt stack frame.
This commit is contained in:
thorpej 2024-02-28 13:05:39 +00:00
parent a75f9c4ba3
commit 3ced769fe7
7 changed files with 65 additions and 77 deletions

View File

@ -1,4 +1,4 @@
/* $NetBSD: cpu.h,v 1.24 2024/02/27 16:07:02 nat Exp $ */
/* $NetBSD: cpu.h,v 1.25 2024/02/28 13:05:39 thorpej Exp $ */
/*
* Copyright (c) 1988 University of Utah.
@ -149,10 +149,8 @@ void cpu_proc_fork(struct proc *, struct proc *);
* what the interrupt stub puts on the stack before calling C code.
*/
struct clockframe {
#ifndef CLOCK_FORMAT0
/* regs saved on the stack by the interrupt stub */
u_int cf_regs[4]; /* d0,d1,a0,a1 */
#endif
/* hardware frame */
u_short cf_sr; /* sr at time of interrupt */
u_long cf_pc; /* pc at time of interrupt */

View File

@ -1,4 +1,4 @@
/* $NetBSD: adb_direct.c,v 1.70 2024/02/09 18:20:00 andvar Exp $ */
/* $NetBSD: adb_direct.c,v 1.71 2024/02/28 13:05:39 thorpej Exp $ */
/* From: adb_direct.c 2.02 4/18/97 jpw */
@ -62,7 +62,7 @@
#ifdef __NetBSD__
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: adb_direct.c,v 1.70 2024/02/09 18:20:00 andvar Exp $");
__KERNEL_RCSID(0, "$NetBSD: adb_direct.c,v 1.71 2024/02/28 13:05:39 thorpej Exp $");
#include "opt_adb.h"
@ -78,6 +78,8 @@ __KERNEL_RCSID(0, "$NetBSD: adb_direct.c,v 1.70 2024/02/09 18:20:00 andvar Exp $
#include <machine/adbsys.h> /* required for adbvar.h */
#include <machine/iopreg.h> /* required for IOP support */
#include <m68k/vectors.h>
#include <mac68k/mac68k/macrom.h>
#include <mac68k/dev/adbvar.h>
#define printf_intr printf
@ -353,6 +355,17 @@ print_single(u_char *str)
}
#endif
static inline void
adb_process_serial_intrs(void)
{
/* grab any serial interrupts (autovector IPL 4) */
struct clockframe dummy_frame = {
.cf_sr = PSL_S,
.cf_vo = VECI_TO_VECO(VECI_INTRAV4),
};
(void)intr_dispatch(dummy_frame);
}
void
adb_cuda_tickle(void)
{
@ -720,7 +733,7 @@ adb_intr_II(void *arg)
delay(ADB_DELAY); /* yuck (don't remove) */
(void)intr_dispatch(0x70); /* grab any serial interrupts */
adb_process_serial_intrs();
if (ADB_INTR_IS_ON)
intr_on = 1; /* save for later */
@ -768,7 +781,7 @@ switch_start:
adbActionState = ADB_ACTION_IN;
}
delay(ADB_DELAY);
(void)intr_dispatch(0x70); /* grab any serial interrupts */
adb_process_serial_intrs();
goto switch_start;
break;
case ADB_ACTION_IDLE:
@ -1262,7 +1275,7 @@ switch_start:
ADB_SET_STATE_ACKON(); /* start ACK to ADB chip */
delay(ADB_DELAY); /* delay */
ADB_SET_STATE_ACKOFF(); /* end ACK to ADB chip */
(void)intr_dispatch(0x70); /* grab any serial interrupts */
adb_process_serial_intrs();
break;
case ADB_ACTION_IN:
@ -1276,7 +1289,7 @@ switch_start:
ADB_SET_STATE_ACKON(); /* start ACK to ADB chip */
delay(ADB_DELAY); /* delay */
ADB_SET_STATE_ACKOFF(); /* end ACK to ADB chip */
(void)intr_dispatch(0x70); /* grab any serial interrupts */
adb_process_serial_intrs();
if (1 == ending) { /* end of message? */
ADB_SET_STATE_INACTIVE(); /* signal end of frame */
@ -1323,7 +1336,7 @@ switch_start:
adbActionState = ADB_ACTION_OUT; /* set next state */
delay(ADB_DELAY); /* delay */
(void)intr_dispatch(0x70); /* grab any serial interrupts */
adb_process_serial_intrs();
if (ADB_INTR_IS_ON) { /* ADB intr low during
* write */
@ -1364,13 +1377,13 @@ switch_start:
adbWriteDelay = 1; /* must retry when done with
* read */
delay(ADB_DELAY); /* delay */
(void)intr_dispatch(0x70); /* grab any serial interrupts */
adb_process_serial_intrs();
goto switch_start; /* process next state right
* now */
break;
}
delay(ADB_DELAY); /* required delay */
(void)intr_dispatch(0x70); /* grab any serial interrupts */
adb_process_serial_intrs();
if (adbOutputBuffer[0] == adbSentChars) { /* check for done */
if (0 == adb_cmd_result(adbOutputBuffer)) { /* do we expect data

View File

@ -1,4 +1,4 @@
/* $NetBSD: cpu.h,v 1.106 2024/02/27 16:07:02 nat Exp $ */
/* $NetBSD: cpu.h,v 1.107 2024/02/28 13:05:40 thorpej Exp $ */
/*
* Copyright (c) 1988 University of Utah.
@ -60,10 +60,6 @@
#ifndef _CPU_MACHINE_
#define _CPU_MACHINE_
#ifndef CLOCK_FORMAT0
#define CLOCK_FORMAT0
#endif
#if defined(_KERNEL_OPT)
#include "opt_lockdebug.h"
#endif

View File

@ -1,4 +1,4 @@
/* $NetBSD: intr.h,v 1.32 2023/07/11 17:55:04 riastradh Exp $ */
/* $NetBSD: intr.h,v 1.33 2024/02/28 13:05:40 thorpej Exp $ */
/*
* Copyright (C) 1997 Scott Reynolds
@ -90,10 +90,11 @@ splraiseipl(ipl_cookie_t icookie)
#include <sys/spl.h>
/* intr.c */
struct clockframe;
void intr_init(void);
void intr_establish(int (*)(void *), void *, int);
void intr_disestablish(int);
void intr_dispatch(int);
void intr_dispatch(struct clockframe);
/* locore.s */
int spl0(void);

View File

@ -1,4 +1,4 @@
/* $NetBSD: intr.c,v 1.35 2024/01/19 20:55:42 thorpej Exp $ */
/* $NetBSD: intr.c,v 1.36 2024/02/28 13:05:40 thorpej Exp $ */
/*-
* Copyright (c) 1996, 1997 The NetBSD Foundation, Inc.
@ -34,7 +34,7 @@
*/
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: intr.c,v 1.35 2024/01/19 20:55:42 thorpej Exp $");
__KERNEL_RCSID(0, "$NetBSD: intr.c,v 1.36 2024/02/28 13:05:40 thorpej Exp $");
#include <sys/param.h>
#include <sys/systm.h>
@ -42,6 +42,8 @@ __KERNEL_RCSID(0, "$NetBSD: intr.c,v 1.35 2024/01/19 20:55:42 thorpej Exp $");
#include <sys/cpu.h>
#include <sys/intr.h>
#include <m68k/vectors.h>
#include <machine/psc.h>
#include <machine/viareg.h>
@ -61,14 +63,14 @@ static int ((*intr_func[NISR])(void *)) = {
intr_noint
};
static void *intr_arg[NISR] = {
(void *)0,
(void *)1,
(void *)2,
(void *)3,
(void *)4,
(void *)5,
(void *)6,
(void *)7
NULL,
NULL,
NULL,
NULL,
NULL,
NULL,
NULL,
NULL
};
#ifdef DEBUG
@ -196,7 +198,7 @@ intr_disestablish(int ipl)
panic("intr_disestablish: bad ipl %d", ipl);
intr_func[ipl] = intr_noint;
intr_arg[ipl] = (void *)ipl;
intr_arg[ipl] = NULL;
}
/*
@ -205,35 +207,19 @@ intr_disestablish(int ipl)
*
* XXX Note: see the warning in intr_establish()
*/
#if __GNUC_PREREQ__(8, 0)
/*
* XXX rtclock_intr() requires this for unwinding stack frame.
*/
#pragma GCC push_options
#pragma GCC optimize "-fno-omit-frame-pointer"
#endif
void
intr_dispatch(int evec) /* format | vector offset */
intr_dispatch(struct clockframe frame)
{
int ipl, vec;
const int ipl = VECO_TO_VECI(frame.cf_vo) - VECI_INTRAV0;
intr_depth++;
vec = (evec & 0xfff) >> 2;
#ifdef DIAGNOSTIC
if ((vec < ISRLOC) || (vec >= (ISRLOC + NISR)))
panic("intr_dispatch: bad vec 0x%x", vec);
#endif
ipl = vec - ISRLOC;
intrcnt[ipl]++;
curcpu()->ci_data.cpu_nintr++;
(void)(*intr_func[ipl])(intr_arg[ipl]);
(void)(*intr_func[ipl])(intr_arg[ipl] ? intr_arg[ipl] : &frame);
intr_depth--;
}
#if __GNUC_PREREQ__(8, 0)
#pragma GCC pop_options
#endif
/*
* Default interrupt handler: do nothing.
@ -243,8 +229,11 @@ intr_noint(void *arg)
{
#ifdef DEBUG
intr_depth++;
if (intr_debug)
printf("intr_noint: ipl %d\n", (int)arg);
if (intr_debug) {
const struct clockframe *frame = arg;
const int ipl = VECO_TO_VECI(frame->cf_vo) - VECI_INTRAV0;
printf("intr_noint: ipl %d\n", ipl);
}
intr_depth--;
#endif
return 0;

View File

@ -1,4 +1,4 @@
/* $NetBSD: locore.s,v 1.183 2024/01/17 12:33:50 thorpej Exp $ */
/* $NetBSD: locore.s,v 1.184 2024/02/28 13:05:40 thorpej Exp $ */
/*
* Copyright (c) 1988 University of Utah.
@ -751,10 +751,7 @@ ENTRY_NOPROFILE(spurintr)
ENTRY_NOPROFILE(intrhand)
INTERRUPT_SAVEREG
movw %sp@(22),%sp@- | push exception vector info
clrw %sp@-
jbsr _C_LABEL(intr_dispatch) | call dispatch routine
addql #4,%sp
INTERRUPT_RESTOREREG
jra _ASM_LABEL(rei) | all done
@ -776,19 +773,17 @@ ENTRY_NOPROFILE(lev7intr)
* saving the status register directly to the stack, but this would lose
* badly on the 040. Aligning the stack takes 10 more cycles than this
* code does, so it's a good compromise.
*
* A pointer to the clockframe is passed as an argument in the usual
* fashion.
*/
ENTRY_NOPROFILE(rtclock_intr)
movl %sp@(4),%a1 | stash pointer to clockframe
movl %d2,%sp@- | save %d2
movw %sr,%d2 | save SPL
movw _C_LABEL(ipl2psl_table)+IPL_CLOCK*2,%sr
| raise SPL to splclock()
movl %a6@,%a1 | unwind to frame in intr_dispatch
| XXX FIXME
lea %a1@(28),%a1 | push pointer to interrupt frame
movl %a1,%sp@- | 28 = 16 for regs in intrhand,
| + 4 for args to intr_dispatch
| + 4 for return address to intrhand
| + 4 for value of %A6
movw _C_LABEL(ipl2psl_table)+IPL_CLOCK*2,%sr
movl %a1,%sp@- | push pointer to clockframe
jbsr _C_LABEL(hardclock) | call generic clock int routine
addql #4,%sp | pop param
jbsr _C_LABEL(mrg_VBLQueue) | give programs in the VBLqueue a chance

View File

@ -1,4 +1,4 @@
/* $NetBSD: via.c,v 1.76 2020/07/21 06:10:26 rin Exp $ */
/* $NetBSD: via.c,v 1.77 2024/02/28 13:05:40 thorpej Exp $ */
/*-
* Copyright (C) 1993 Allen K. Briggs, Chris P. Caputo,
@ -39,7 +39,7 @@
*/
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: via.c,v 1.76 2020/07/21 06:10:26 rin Exp $");
__KERNEL_RCSID(0, "$NetBSD: via.c,v 1.77 2024/02/28 13:05:40 thorpej Exp $");
#include "opt_mac68k.h"
@ -239,15 +239,8 @@ via_set_modem(int onoff)
via_reg(VIA1, vBufA) &= ~DA1O_vSync;
}
#if __GNUC_PREREQ__(8, 0)
/*
* XXX rtclock_intr() requires this for unwinding stack frame.
*/
#pragma GCC push_options
#pragma GCC optimize "-fno-omit-frame-pointer"
#endif
void
via1_intr(void *intr_arg)
via1_intr(void *intr_arg /* struct clockframe * */)
{
u_int8_t intbits, bitnum;
u_int mask;
@ -269,16 +262,19 @@ via1_intr(void *intr_arg)
bitnum = 0;
do {
if (intbits & mask) {
via1itab[bitnum](via1iarg[bitnum]);
/*
* We want to pass the clockframe on to
* rtclock_intr().
*/
void *arg = via1itab[bitnum] == rtclock_intr
? intr_arg : via1iarg[bitnum];
via1itab[bitnum](arg);
/* via_reg(VIA1, vIFR) = mask; */
}
mask <<= 1;
++bitnum;
} while (intbits >= mask);
}
#if __GNUC_PREREQ__(8, 0)
#pragma GCC pop_options
#endif
void
via2_intr(void *intr_arg)