Generate intrnames[] dynamically. This should be new-bus friendly.

Old version reviewed by: se
This commit is contained in:
Bruce Evans 1999-04-14 14:26:36 +00:00
parent 4b056ee860
commit 6a9df7a421
15 changed files with 373 additions and 550 deletions

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: apic_vector.s,v 1.34 1998/09/06 22:41:41 tegge Exp $
* $Id: apic_vector.s,v 1.35 1999/04/10 19:19:02 tegge Exp $
*/
@ -997,46 +997,4 @@ CNAME(cpustop_restartfunc):
_apic_pin_trigger:
.long 0
/*
* Interrupt counters and names. The format of these and the label names
* must agree with what vmstat expects. The tables are indexed by device
* ids so that we don't have to move the names around as devices are
* attached.
*/
#include "vector.h"
.globl _intrcnt, _eintrcnt
_intrcnt:
.space (NR_DEVICES + ICU_LEN) * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.ascii DEVICE_NAMES
.asciz "stray irq0"
.asciz "stray irq1"
.asciz "stray irq2"
.asciz "stray irq3"
.asciz "stray irq4"
.asciz "stray irq5"
.asciz "stray irq6"
.asciz "stray irq7"
.asciz "stray irq8"
.asciz "stray irq9"
.asciz "stray irq10"
.asciz "stray irq11"
.asciz "stray irq12"
.asciz "stray irq13"
.asciz "stray irq14"
.asciz "stray irq15"
.asciz "stray irq16"
.asciz "stray irq17"
.asciz "stray irq18"
.asciz "stray irq19"
.asciz "stray irq20"
.asciz "stray irq21"
.asciz "stray irq22"
.asciz "stray irq23"
_eintrnames:
.text

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: icu_vector.s,v 1.8 1998/08/11 15:08:12 bde Exp $
* $Id: icu_vector.s,v 1.9 1998/08/11 17:01:32 bde Exp $
*/
/*
@ -214,37 +214,4 @@ imasks: /* masks for interrupt handlers */
.long 0, 0, 0, 0
.long 0, 0, SWI_CLOCK_MASK, SWI_AST_MASK
/*
* Interrupt counters and names. The format of these and the label names
* must agree with what vmstat expects. The tables are indexed by device
* ids so that we don't have to move the names around as devices are
* attached.
*/
#include "vector.h"
.globl _intrcnt, _eintrcnt
_intrcnt:
.space (NR_DEVICES + ICU_LEN) * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.ascii DEVICE_NAMES
.asciz "stray irq0"
.asciz "stray irq1"
.asciz "stray irq2"
.asciz "stray irq3"
.asciz "stray irq4"
.asciz "stray irq5"
.asciz "stray irq6"
.asciz "stray irq7"
.asciz "stray irq8"
.asciz "stray irq9"
.asciz "stray irq10"
.asciz "stray irq11"
.asciz "stray irq12"
.asciz "stray irq13"
.asciz "stray irq14"
.asciz "stray irq15"
_eintrnames:
.text

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: icu_vector.s,v 1.8 1998/08/11 15:08:12 bde Exp $
* $Id: icu_vector.s,v 1.9 1998/08/11 17:01:32 bde Exp $
*/
/*
@ -214,37 +214,4 @@ imasks: /* masks for interrupt handlers */
.long 0, 0, 0, 0
.long 0, 0, SWI_CLOCK_MASK, SWI_AST_MASK
/*
* Interrupt counters and names. The format of these and the label names
* must agree with what vmstat expects. The tables are indexed by device
* ids so that we don't have to move the names around as devices are
* attached.
*/
#include "vector.h"
.globl _intrcnt, _eintrcnt
_intrcnt:
.space (NR_DEVICES + ICU_LEN) * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.ascii DEVICE_NAMES
.asciz "stray irq0"
.asciz "stray irq1"
.asciz "stray irq2"
.asciz "stray irq3"
.asciz "stray irq4"
.asciz "stray irq5"
.asciz "stray irq6"
.asciz "stray irq7"
.asciz "stray irq8"
.asciz "stray irq9"
.asciz "stray irq10"
.asciz "stray irq11"
.asciz "stray irq12"
.asciz "stray irq13"
.asciz "stray irq14"
.asciz "stray irq15"
_eintrnames:
.text

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: icu_vector.s,v 1.8 1998/08/11 15:08:12 bde Exp $
* $Id: icu_vector.s,v 1.9 1998/08/11 17:01:32 bde Exp $
*/
/*
@ -214,37 +214,4 @@ imasks: /* masks for interrupt handlers */
.long 0, 0, 0, 0
.long 0, 0, SWI_CLOCK_MASK, SWI_AST_MASK
/*
* Interrupt counters and names. The format of these and the label names
* must agree with what vmstat expects. The tables are indexed by device
* ids so that we don't have to move the names around as devices are
* attached.
*/
#include "vector.h"
.globl _intrcnt, _eintrcnt
_intrcnt:
.space (NR_DEVICES + ICU_LEN) * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.ascii DEVICE_NAMES
.asciz "stray irq0"
.asciz "stray irq1"
.asciz "stray irq2"
.asciz "stray irq3"
.asciz "stray irq4"
.asciz "stray irq5"
.asciz "stray irq6"
.asciz "stray irq7"
.asciz "stray irq8"
.asciz "stray irq9"
.asciz "stray irq10"
.asciz "stray irq11"
.asciz "stray irq12"
.asciz "stray irq13"
.asciz "stray irq14"
.asciz "stray irq15"
_eintrnames:
.text

View File

@ -34,7 +34,7 @@
* SUCH DAMAGE.
*
* from: @(#)isa.c 7.2 (Berkeley) 5/13/91
* $Id: intr_machdep.c,v 1.15 1998/12/04 22:54:46 archie Exp $
* $Id: intr_machdep.c,v 1.16 1999/01/08 19:17:48 bde Exp $
*/
#include "opt_auto_eoi.h"
@ -61,7 +61,6 @@
#include <i386/isa/isa.h>
#endif
#include <i386/isa/icu.h>
#include "vector.h"
#include <i386/isa/intr_machdep.h>
#include <sys/interrupt.h>
@ -86,6 +85,8 @@
#define AUTO_EOI_1 1
#endif
#define NR_INTRNAMES (1 + ICU_LEN + 2 * ICU_LEN)
u_long *intr_countp[ICU_LEN];
inthand2_t *intr_handler[ICU_LEN];
u_int intr_mask[ICU_LEN];
@ -264,9 +265,9 @@ isa_strayintr(vcookiep)
* must be done before sending an EOI so it can't be done if
* we are using AUTO_EOI_1.
*/
if (intrcnt[NR_DEVICES + intr] <= 5)
if (intrcnt[1 + intr] <= 5)
log(LOG_ERR, "stray irq %d\n", intr);
if (intrcnt[NR_DEVICES + intr] == 5)
if (intrcnt[1 + intr] == 5)
log(LOG_CRIT,
"too many stray irq %d's; not logging any more\n", intr);
}
@ -315,74 +316,88 @@ update_intr_masks(void)
return (n);
}
/*
* The find_device_id function is only required because of the way the
* device names are currently stored for reporting in systat or vmstat.
* In fact, those programs should be modified to use the sysctl interface
* to obtain a list of driver names by traversing intreclist_head[irq].
*/
static int
find_device_id(int irq)
static const char *
isa_get_nameunit(int id)
{
char buf[16];
char *cp;
int free_id, id;
static char buf[32];
struct isa_device *dp;
snprintf(buf, sizeof(buf), "pci irq%d", irq);
cp = intrnames;
/* default to 0, which corresponds to clk0 */
free_id = 0;
if (id == -1)
return ("pci"); /* XXX may also be eisa */
if (id == 0)
return ("clk0"); /* XXX may also be sloppy driver */
if (id == 1)
return ("rtc0");
for (dp = isa_devtab_bio; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_cam; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_net; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_null; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_tty; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
return "???";
for (id = 0; id < NR_DEVICES; id++) {
if (strcmp(cp, buf) == 0)
return (id);
if (free_id == 0 && strcmp(cp, "pci irqnn") == 0)
free_id = id;
while (*cp++ != '\0');
}
#if 0
if (free_id == 0) {
/*
* All pci irq counters are in use, perhaps because config
* is old so there aren't any. Abuse the clk0 counter.
*/
printf("\tcounting shared irq%d as clk0 irq\n", irq);
}
#endif
return (free_id);
found_device:
snprintf(buf, sizeof(buf), "%s%d", dp->id_driver->name, dp->id_unit);
return (buf);
}
void
update_intrname(int intr, int device_id)
{
char *cp;
int id;
char buf[32];
char *cp;
const char *name;
int name_index, off, strayintr;
if (device_id == -1)
device_id = find_device_id(intr);
if ((u_int)device_id >= NR_DEVICES)
return;
intr_countp[intr] = &intrcnt[device_id];
for (cp = intrnames, id = 0; id <= device_id; id++)
while (*cp++ != '\0')
;
if (cp > eintrnames)
return;
if (intr < 10) {
cp[-3] = intr + '0';
cp[-2] = ' ';
} else if (intr < 20) {
cp[-3] = '1';
cp[-2] = intr - 10 + '0';
} else {
cp[-3] = '2';
cp[-2] = intr - 20 + '0';
/*
* Initialise strings for bitbucket and stray interrupt counters.
* These have statically allocated indices 0 and 1 through ICU_LEN.
*/
if (intrnames[0] == '\0') {
off = sprintf(intrnames, "???") + 1;
for (strayintr = 0; strayintr < ICU_LEN; strayintr++)
off += sprintf(intrnames + off, "stray irq%d",
strayintr) + 1;
}
}
name = isa_get_nameunit(device_id);
if (snprintf(buf, sizeof(buf), "%s irq%d", name, intr) >= sizeof(buf))
goto use_bitbucket;
/*
* Search for `buf' in `intrnames'. In the usual case when it is
* not found, append it to the end if there is enough space (the \0
* terminator for the previous string, if any, becomes a separator).
*/
for (cp = intrnames, name_index = 0;
cp != eintrnames && name_index < NR_INTRNAMES;
cp += strlen(cp) + 1, name_index++) {
if (*cp == '\0') {
if (strlen(buf) >= eintrnames - cp)
break;
strcpy(cp, buf);
goto found;
}
if (strcmp(cp, buf) == 0)
goto found;
}
use_bitbucket:
printf("update_intrname: counting %s irq%d as %s\n", name, intr,
intrnames);
name_index = 0;
found:
intr_countp[intr] = &intrcnt[name_index];
}
int
icu_setup(int intr, inthand2_t *handler, void *arg, u_int *maskptr, int flags)
@ -479,7 +494,7 @@ icu_unset(intr, handler)
INTRDIS(1 << intr);
ef = read_eflags();
disable_intr();
intr_countp[intr] = &intrcnt[NR_DEVICES + intr];
intr_countp[intr] = &intrcnt[1 + intr];
intr_handler[intr] = isa_strayintr;
intr_mptr[intr] = NULL;
intr_mask[intr] = HWI_MASK | SWI_MASK;

View File

@ -34,7 +34,7 @@
* SUCH DAMAGE.
*
* from: @(#)isa.c 7.2 (Berkeley) 5/13/91
* $Id: intr_machdep.c,v 1.15 1998/12/04 22:54:46 archie Exp $
* $Id: intr_machdep.c,v 1.16 1999/01/08 19:17:48 bde Exp $
*/
#include "opt_auto_eoi.h"
@ -61,7 +61,6 @@
#include <i386/isa/isa.h>
#endif
#include <i386/isa/icu.h>
#include "vector.h"
#include <i386/isa/intr_machdep.h>
#include <sys/interrupt.h>
@ -86,6 +85,8 @@
#define AUTO_EOI_1 1
#endif
#define NR_INTRNAMES (1 + ICU_LEN + 2 * ICU_LEN)
u_long *intr_countp[ICU_LEN];
inthand2_t *intr_handler[ICU_LEN];
u_int intr_mask[ICU_LEN];
@ -264,9 +265,9 @@ isa_strayintr(vcookiep)
* must be done before sending an EOI so it can't be done if
* we are using AUTO_EOI_1.
*/
if (intrcnt[NR_DEVICES + intr] <= 5)
if (intrcnt[1 + intr] <= 5)
log(LOG_ERR, "stray irq %d\n", intr);
if (intrcnt[NR_DEVICES + intr] == 5)
if (intrcnt[1 + intr] == 5)
log(LOG_CRIT,
"too many stray irq %d's; not logging any more\n", intr);
}
@ -315,74 +316,88 @@ update_intr_masks(void)
return (n);
}
/*
* The find_device_id function is only required because of the way the
* device names are currently stored for reporting in systat or vmstat.
* In fact, those programs should be modified to use the sysctl interface
* to obtain a list of driver names by traversing intreclist_head[irq].
*/
static int
find_device_id(int irq)
static const char *
isa_get_nameunit(int id)
{
char buf[16];
char *cp;
int free_id, id;
static char buf[32];
struct isa_device *dp;
snprintf(buf, sizeof(buf), "pci irq%d", irq);
cp = intrnames;
/* default to 0, which corresponds to clk0 */
free_id = 0;
if (id == -1)
return ("pci"); /* XXX may also be eisa */
if (id == 0)
return ("clk0"); /* XXX may also be sloppy driver */
if (id == 1)
return ("rtc0");
for (dp = isa_devtab_bio; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_cam; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_net; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_null; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_tty; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
return "???";
for (id = 0; id < NR_DEVICES; id++) {
if (strcmp(cp, buf) == 0)
return (id);
if (free_id == 0 && strcmp(cp, "pci irqnn") == 0)
free_id = id;
while (*cp++ != '\0');
}
#if 0
if (free_id == 0) {
/*
* All pci irq counters are in use, perhaps because config
* is old so there aren't any. Abuse the clk0 counter.
*/
printf("\tcounting shared irq%d as clk0 irq\n", irq);
}
#endif
return (free_id);
found_device:
snprintf(buf, sizeof(buf), "%s%d", dp->id_driver->name, dp->id_unit);
return (buf);
}
void
update_intrname(int intr, int device_id)
{
char *cp;
int id;
char buf[32];
char *cp;
const char *name;
int name_index, off, strayintr;
if (device_id == -1)
device_id = find_device_id(intr);
if ((u_int)device_id >= NR_DEVICES)
return;
intr_countp[intr] = &intrcnt[device_id];
for (cp = intrnames, id = 0; id <= device_id; id++)
while (*cp++ != '\0')
;
if (cp > eintrnames)
return;
if (intr < 10) {
cp[-3] = intr + '0';
cp[-2] = ' ';
} else if (intr < 20) {
cp[-3] = '1';
cp[-2] = intr - 10 + '0';
} else {
cp[-3] = '2';
cp[-2] = intr - 20 + '0';
/*
* Initialise strings for bitbucket and stray interrupt counters.
* These have statically allocated indices 0 and 1 through ICU_LEN.
*/
if (intrnames[0] == '\0') {
off = sprintf(intrnames, "???") + 1;
for (strayintr = 0; strayintr < ICU_LEN; strayintr++)
off += sprintf(intrnames + off, "stray irq%d",
strayintr) + 1;
}
}
name = isa_get_nameunit(device_id);
if (snprintf(buf, sizeof(buf), "%s irq%d", name, intr) >= sizeof(buf))
goto use_bitbucket;
/*
* Search for `buf' in `intrnames'. In the usual case when it is
* not found, append it to the end if there is enough space (the \0
* terminator for the previous string, if any, becomes a separator).
*/
for (cp = intrnames, name_index = 0;
cp != eintrnames && name_index < NR_INTRNAMES;
cp += strlen(cp) + 1, name_index++) {
if (*cp == '\0') {
if (strlen(buf) >= eintrnames - cp)
break;
strcpy(cp, buf);
goto found;
}
if (strcmp(cp, buf) == 0)
goto found;
}
use_bitbucket:
printf("update_intrname: counting %s irq%d as %s\n", name, intr,
intrnames);
name_index = 0;
found:
intr_countp[intr] = &intrcnt[name_index];
}
int
icu_setup(int intr, inthand2_t *handler, void *arg, u_int *maskptr, int flags)
@ -479,7 +494,7 @@ icu_unset(intr, handler)
INTRDIS(1 << intr);
ef = read_eflags();
disable_intr();
intr_countp[intr] = &intrcnt[NR_DEVICES + intr];
intr_countp[intr] = &intrcnt[1 + intr];
intr_handler[intr] = isa_strayintr;
intr_mptr[intr] = NULL;
intr_mask[intr] = HWI_MASK | SWI_MASK;

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: vector.s,v 1.2 1997/05/24 17:05:26 smp Exp smp $
* $Id: vector.s,v 1.30 1997/05/26 17:58:27 fsmp Exp $
*/
/*
@ -41,6 +41,24 @@ _intr_nesting_level:
.byte 0
.space 3
/*
* Interrupt counters and names for export to vmstat(8) and friends.
*
* XXX this doesn't really belong here; everything except the labels
* for the endpointers is almost machine-independent.
*/
#define NR_INTRNAMES (1 + ICU_LEN + 2 * ICU_LEN)
.globl _intrcnt, _eintrcnt
_intrcnt:
.space NR_INTRNAMES * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.space NR_INTRNAMES * 16
_eintrnames:
.text
/*

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: vector.s,v 1.2 1997/05/24 17:05:26 smp Exp smp $
* $Id: vector.s,v 1.30 1997/05/26 17:58:27 fsmp Exp $
*/
/*
@ -41,6 +41,24 @@ _intr_nesting_level:
.byte 0
.space 3
/*
* Interrupt counters and names for export to vmstat(8) and friends.
*
* XXX this doesn't really belong here; everything except the labels
* for the endpointers is almost machine-independent.
*/
#define NR_INTRNAMES (1 + ICU_LEN + 2 * ICU_LEN)
.globl _intrcnt, _eintrcnt
_intrcnt:
.space NR_INTRNAMES * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.space NR_INTRNAMES * 16
_eintrnames:
.text
/*

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: apic_vector.s,v 1.34 1998/09/06 22:41:41 tegge Exp $
* $Id: apic_vector.s,v 1.35 1999/04/10 19:19:02 tegge Exp $
*/
@ -997,46 +997,4 @@ CNAME(cpustop_restartfunc):
_apic_pin_trigger:
.long 0
/*
* Interrupt counters and names. The format of these and the label names
* must agree with what vmstat expects. The tables are indexed by device
* ids so that we don't have to move the names around as devices are
* attached.
*/
#include "vector.h"
.globl _intrcnt, _eintrcnt
_intrcnt:
.space (NR_DEVICES + ICU_LEN) * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.ascii DEVICE_NAMES
.asciz "stray irq0"
.asciz "stray irq1"
.asciz "stray irq2"
.asciz "stray irq3"
.asciz "stray irq4"
.asciz "stray irq5"
.asciz "stray irq6"
.asciz "stray irq7"
.asciz "stray irq8"
.asciz "stray irq9"
.asciz "stray irq10"
.asciz "stray irq11"
.asciz "stray irq12"
.asciz "stray irq13"
.asciz "stray irq14"
.asciz "stray irq15"
.asciz "stray irq16"
.asciz "stray irq17"
.asciz "stray irq18"
.asciz "stray irq19"
.asciz "stray irq20"
.asciz "stray irq21"
.asciz "stray irq22"
.asciz "stray irq23"
_eintrnames:
.text

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: apic_vector.s,v 1.34 1998/09/06 22:41:41 tegge Exp $
* $Id: apic_vector.s,v 1.35 1999/04/10 19:19:02 tegge Exp $
*/
@ -997,46 +997,4 @@ CNAME(cpustop_restartfunc):
_apic_pin_trigger:
.long 0
/*
* Interrupt counters and names. The format of these and the label names
* must agree with what vmstat expects. The tables are indexed by device
* ids so that we don't have to move the names around as devices are
* attached.
*/
#include "vector.h"
.globl _intrcnt, _eintrcnt
_intrcnt:
.space (NR_DEVICES + ICU_LEN) * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.ascii DEVICE_NAMES
.asciz "stray irq0"
.asciz "stray irq1"
.asciz "stray irq2"
.asciz "stray irq3"
.asciz "stray irq4"
.asciz "stray irq5"
.asciz "stray irq6"
.asciz "stray irq7"
.asciz "stray irq8"
.asciz "stray irq9"
.asciz "stray irq10"
.asciz "stray irq11"
.asciz "stray irq12"
.asciz "stray irq13"
.asciz "stray irq14"
.asciz "stray irq15"
.asciz "stray irq16"
.asciz "stray irq17"
.asciz "stray irq18"
.asciz "stray irq19"
.asciz "stray irq20"
.asciz "stray irq21"
.asciz "stray irq22"
.asciz "stray irq23"
_eintrnames:
.text

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: icu_vector.s,v 1.8 1998/08/11 15:08:12 bde Exp $
* $Id: icu_vector.s,v 1.9 1998/08/11 17:01:32 bde Exp $
*/
/*
@ -214,37 +214,4 @@ imasks: /* masks for interrupt handlers */
.long 0, 0, 0, 0
.long 0, 0, SWI_CLOCK_MASK, SWI_AST_MASK
/*
* Interrupt counters and names. The format of these and the label names
* must agree with what vmstat expects. The tables are indexed by device
* ids so that we don't have to move the names around as devices are
* attached.
*/
#include "vector.h"
.globl _intrcnt, _eintrcnt
_intrcnt:
.space (NR_DEVICES + ICU_LEN) * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.ascii DEVICE_NAMES
.asciz "stray irq0"
.asciz "stray irq1"
.asciz "stray irq2"
.asciz "stray irq3"
.asciz "stray irq4"
.asciz "stray irq5"
.asciz "stray irq6"
.asciz "stray irq7"
.asciz "stray irq8"
.asciz "stray irq9"
.asciz "stray irq10"
.asciz "stray irq11"
.asciz "stray irq12"
.asciz "stray irq13"
.asciz "stray irq14"
.asciz "stray irq15"
_eintrnames:
.text

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: icu_vector.s,v 1.8 1998/08/11 15:08:12 bde Exp $
* $Id: icu_vector.s,v 1.9 1998/08/11 17:01:32 bde Exp $
*/
/*
@ -214,37 +214,4 @@ imasks: /* masks for interrupt handlers */
.long 0, 0, 0, 0
.long 0, 0, SWI_CLOCK_MASK, SWI_AST_MASK
/*
* Interrupt counters and names. The format of these and the label names
* must agree with what vmstat expects. The tables are indexed by device
* ids so that we don't have to move the names around as devices are
* attached.
*/
#include "vector.h"
.globl _intrcnt, _eintrcnt
_intrcnt:
.space (NR_DEVICES + ICU_LEN) * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.ascii DEVICE_NAMES
.asciz "stray irq0"
.asciz "stray irq1"
.asciz "stray irq2"
.asciz "stray irq3"
.asciz "stray irq4"
.asciz "stray irq5"
.asciz "stray irq6"
.asciz "stray irq7"
.asciz "stray irq8"
.asciz "stray irq9"
.asciz "stray irq10"
.asciz "stray irq11"
.asciz "stray irq12"
.asciz "stray irq13"
.asciz "stray irq14"
.asciz "stray irq15"
_eintrnames:
.text

View File

@ -34,7 +34,7 @@
* SUCH DAMAGE.
*
* from: @(#)isa.c 7.2 (Berkeley) 5/13/91
* $Id: intr_machdep.c,v 1.15 1998/12/04 22:54:46 archie Exp $
* $Id: intr_machdep.c,v 1.16 1999/01/08 19:17:48 bde Exp $
*/
#include "opt_auto_eoi.h"
@ -61,7 +61,6 @@
#include <i386/isa/isa.h>
#endif
#include <i386/isa/icu.h>
#include "vector.h"
#include <i386/isa/intr_machdep.h>
#include <sys/interrupt.h>
@ -86,6 +85,8 @@
#define AUTO_EOI_1 1
#endif
#define NR_INTRNAMES (1 + ICU_LEN + 2 * ICU_LEN)
u_long *intr_countp[ICU_LEN];
inthand2_t *intr_handler[ICU_LEN];
u_int intr_mask[ICU_LEN];
@ -264,9 +265,9 @@ isa_strayintr(vcookiep)
* must be done before sending an EOI so it can't be done if
* we are using AUTO_EOI_1.
*/
if (intrcnt[NR_DEVICES + intr] <= 5)
if (intrcnt[1 + intr] <= 5)
log(LOG_ERR, "stray irq %d\n", intr);
if (intrcnt[NR_DEVICES + intr] == 5)
if (intrcnt[1 + intr] == 5)
log(LOG_CRIT,
"too many stray irq %d's; not logging any more\n", intr);
}
@ -315,74 +316,88 @@ update_intr_masks(void)
return (n);
}
/*
* The find_device_id function is only required because of the way the
* device names are currently stored for reporting in systat or vmstat.
* In fact, those programs should be modified to use the sysctl interface
* to obtain a list of driver names by traversing intreclist_head[irq].
*/
static int
find_device_id(int irq)
static const char *
isa_get_nameunit(int id)
{
char buf[16];
char *cp;
int free_id, id;
static char buf[32];
struct isa_device *dp;
snprintf(buf, sizeof(buf), "pci irq%d", irq);
cp = intrnames;
/* default to 0, which corresponds to clk0 */
free_id = 0;
if (id == -1)
return ("pci"); /* XXX may also be eisa */
if (id == 0)
return ("clk0"); /* XXX may also be sloppy driver */
if (id == 1)
return ("rtc0");
for (dp = isa_devtab_bio; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_cam; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_net; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_null; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_tty; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
return "???";
for (id = 0; id < NR_DEVICES; id++) {
if (strcmp(cp, buf) == 0)
return (id);
if (free_id == 0 && strcmp(cp, "pci irqnn") == 0)
free_id = id;
while (*cp++ != '\0');
}
#if 0
if (free_id == 0) {
/*
* All pci irq counters are in use, perhaps because config
* is old so there aren't any. Abuse the clk0 counter.
*/
printf("\tcounting shared irq%d as clk0 irq\n", irq);
}
#endif
return (free_id);
found_device:
snprintf(buf, sizeof(buf), "%s%d", dp->id_driver->name, dp->id_unit);
return (buf);
}
void
update_intrname(int intr, int device_id)
{
char *cp;
int id;
char buf[32];
char *cp;
const char *name;
int name_index, off, strayintr;
if (device_id == -1)
device_id = find_device_id(intr);
if ((u_int)device_id >= NR_DEVICES)
return;
intr_countp[intr] = &intrcnt[device_id];
for (cp = intrnames, id = 0; id <= device_id; id++)
while (*cp++ != '\0')
;
if (cp > eintrnames)
return;
if (intr < 10) {
cp[-3] = intr + '0';
cp[-2] = ' ';
} else if (intr < 20) {
cp[-3] = '1';
cp[-2] = intr - 10 + '0';
} else {
cp[-3] = '2';
cp[-2] = intr - 20 + '0';
/*
* Initialise strings for bitbucket and stray interrupt counters.
* These have statically allocated indices 0 and 1 through ICU_LEN.
*/
if (intrnames[0] == '\0') {
off = sprintf(intrnames, "???") + 1;
for (strayintr = 0; strayintr < ICU_LEN; strayintr++)
off += sprintf(intrnames + off, "stray irq%d",
strayintr) + 1;
}
}
name = isa_get_nameunit(device_id);
if (snprintf(buf, sizeof(buf), "%s irq%d", name, intr) >= sizeof(buf))
goto use_bitbucket;
/*
* Search for `buf' in `intrnames'. In the usual case when it is
* not found, append it to the end if there is enough space (the \0
* terminator for the previous string, if any, becomes a separator).
*/
for (cp = intrnames, name_index = 0;
cp != eintrnames && name_index < NR_INTRNAMES;
cp += strlen(cp) + 1, name_index++) {
if (*cp == '\0') {
if (strlen(buf) >= eintrnames - cp)
break;
strcpy(cp, buf);
goto found;
}
if (strcmp(cp, buf) == 0)
goto found;
}
use_bitbucket:
printf("update_intrname: counting %s irq%d as %s\n", name, intr,
intrnames);
name_index = 0;
found:
intr_countp[intr] = &intrcnt[name_index];
}
int
icu_setup(int intr, inthand2_t *handler, void *arg, u_int *maskptr, int flags)
@ -479,7 +494,7 @@ icu_unset(intr, handler)
INTRDIS(1 << intr);
ef = read_eflags();
disable_intr();
intr_countp[intr] = &intrcnt[NR_DEVICES + intr];
intr_countp[intr] = &intrcnt[1 + intr];
intr_handler[intr] = isa_strayintr;
intr_mptr[intr] = NULL;
intr_mask[intr] = HWI_MASK | SWI_MASK;

View File

@ -34,7 +34,7 @@
* SUCH DAMAGE.
*
* from: @(#)isa.c 7.2 (Berkeley) 5/13/91
* $Id: intr_machdep.c,v 1.15 1998/12/04 22:54:46 archie Exp $
* $Id: intr_machdep.c,v 1.16 1999/01/08 19:17:48 bde Exp $
*/
#include "opt_auto_eoi.h"
@ -61,7 +61,6 @@
#include <i386/isa/isa.h>
#endif
#include <i386/isa/icu.h>
#include "vector.h"
#include <i386/isa/intr_machdep.h>
#include <sys/interrupt.h>
@ -86,6 +85,8 @@
#define AUTO_EOI_1 1
#endif
#define NR_INTRNAMES (1 + ICU_LEN + 2 * ICU_LEN)
u_long *intr_countp[ICU_LEN];
inthand2_t *intr_handler[ICU_LEN];
u_int intr_mask[ICU_LEN];
@ -264,9 +265,9 @@ isa_strayintr(vcookiep)
* must be done before sending an EOI so it can't be done if
* we are using AUTO_EOI_1.
*/
if (intrcnt[NR_DEVICES + intr] <= 5)
if (intrcnt[1 + intr] <= 5)
log(LOG_ERR, "stray irq %d\n", intr);
if (intrcnt[NR_DEVICES + intr] == 5)
if (intrcnt[1 + intr] == 5)
log(LOG_CRIT,
"too many stray irq %d's; not logging any more\n", intr);
}
@ -315,74 +316,88 @@ update_intr_masks(void)
return (n);
}
/*
* The find_device_id function is only required because of the way the
* device names are currently stored for reporting in systat or vmstat.
* In fact, those programs should be modified to use the sysctl interface
* to obtain a list of driver names by traversing intreclist_head[irq].
*/
static int
find_device_id(int irq)
static const char *
isa_get_nameunit(int id)
{
char buf[16];
char *cp;
int free_id, id;
static char buf[32];
struct isa_device *dp;
snprintf(buf, sizeof(buf), "pci irq%d", irq);
cp = intrnames;
/* default to 0, which corresponds to clk0 */
free_id = 0;
if (id == -1)
return ("pci"); /* XXX may also be eisa */
if (id == 0)
return ("clk0"); /* XXX may also be sloppy driver */
if (id == 1)
return ("rtc0");
for (dp = isa_devtab_bio; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_cam; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_net; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_null; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
for (dp = isa_devtab_tty; dp->id_driver != NULL; dp++)
if (dp->id_id == id)
goto found_device;
return "???";
for (id = 0; id < NR_DEVICES; id++) {
if (strcmp(cp, buf) == 0)
return (id);
if (free_id == 0 && strcmp(cp, "pci irqnn") == 0)
free_id = id;
while (*cp++ != '\0');
}
#if 0
if (free_id == 0) {
/*
* All pci irq counters are in use, perhaps because config
* is old so there aren't any. Abuse the clk0 counter.
*/
printf("\tcounting shared irq%d as clk0 irq\n", irq);
}
#endif
return (free_id);
found_device:
snprintf(buf, sizeof(buf), "%s%d", dp->id_driver->name, dp->id_unit);
return (buf);
}
void
update_intrname(int intr, int device_id)
{
char *cp;
int id;
char buf[32];
char *cp;
const char *name;
int name_index, off, strayintr;
if (device_id == -1)
device_id = find_device_id(intr);
if ((u_int)device_id >= NR_DEVICES)
return;
intr_countp[intr] = &intrcnt[device_id];
for (cp = intrnames, id = 0; id <= device_id; id++)
while (*cp++ != '\0')
;
if (cp > eintrnames)
return;
if (intr < 10) {
cp[-3] = intr + '0';
cp[-2] = ' ';
} else if (intr < 20) {
cp[-3] = '1';
cp[-2] = intr - 10 + '0';
} else {
cp[-3] = '2';
cp[-2] = intr - 20 + '0';
/*
* Initialise strings for bitbucket and stray interrupt counters.
* These have statically allocated indices 0 and 1 through ICU_LEN.
*/
if (intrnames[0] == '\0') {
off = sprintf(intrnames, "???") + 1;
for (strayintr = 0; strayintr < ICU_LEN; strayintr++)
off += sprintf(intrnames + off, "stray irq%d",
strayintr) + 1;
}
}
name = isa_get_nameunit(device_id);
if (snprintf(buf, sizeof(buf), "%s irq%d", name, intr) >= sizeof(buf))
goto use_bitbucket;
/*
* Search for `buf' in `intrnames'. In the usual case when it is
* not found, append it to the end if there is enough space (the \0
* terminator for the previous string, if any, becomes a separator).
*/
for (cp = intrnames, name_index = 0;
cp != eintrnames && name_index < NR_INTRNAMES;
cp += strlen(cp) + 1, name_index++) {
if (*cp == '\0') {
if (strlen(buf) >= eintrnames - cp)
break;
strcpy(cp, buf);
goto found;
}
if (strcmp(cp, buf) == 0)
goto found;
}
use_bitbucket:
printf("update_intrname: counting %s irq%d as %s\n", name, intr,
intrnames);
name_index = 0;
found:
intr_countp[intr] = &intrcnt[name_index];
}
int
icu_setup(int intr, inthand2_t *handler, void *arg, u_int *maskptr, int flags)
@ -479,7 +494,7 @@ icu_unset(intr, handler)
INTRDIS(1 << intr);
ef = read_eflags();
disable_intr();
intr_countp[intr] = &intrcnt[NR_DEVICES + intr];
intr_countp[intr] = &intrcnt[1 + intr];
intr_handler[intr] = isa_strayintr;
intr_mptr[intr] = NULL;
intr_mask[intr] = HWI_MASK | SWI_MASK;

View File

@ -1,6 +1,6 @@
/*
* from: vector.s, 386BSD 0.1 unknown origin
* $Id: vector.s,v 1.2 1997/05/24 17:05:26 smp Exp smp $
* $Id: vector.s,v 1.30 1997/05/26 17:58:27 fsmp Exp $
*/
/*
@ -41,6 +41,24 @@ _intr_nesting_level:
.byte 0
.space 3
/*
* Interrupt counters and names for export to vmstat(8) and friends.
*
* XXX this doesn't really belong here; everything except the labels
* for the endpointers is almost machine-independent.
*/
#define NR_INTRNAMES (1 + ICU_LEN + 2 * ICU_LEN)
.globl _intrcnt, _eintrcnt
_intrcnt:
.space NR_INTRNAMES * 4
_eintrcnt:
.globl _intrnames, _eintrnames
_intrnames:
.space NR_INTRNAMES * 16
_eintrnames:
.text
/*