Subject: Re: port-alpha/36628: cdhdtape image panics with memory management
To: None <tsutsui@NetBSD.org, gnats-admin@netbsd.org,>
From: Izumi Tsutsui <tsutsui@ceres.dti.ne.jp>
List: netbsd-bugs
Date: 07/27/2007 15:00:05
The following reply was made to PR port-alpha/36628; it has been noted by GNATS.

From: Izumi Tsutsui <tsutsui@ceres.dti.ne.jp>
To: ChristophFranzen@gmx.net
Cc: gnats-bugs@NetBSD.org, tsutsui@ceres.dti.ne.jp
Subject: Re: port-alpha/36628: cdhdtape image panics with memory management
	 trap on Jensen
Date: Fri, 27 Jul 2007 23:58:07 +0900

 ChristophFranzen@gmx.net wrote:
 
 > the ahb0 interrupt seems OK (the INTDEF and ECU values are both 12), 
 > but it still hangs at "enabling interrupts", the "evcnt" number is 
 > still large.
 
 Okay, I've checked mailing list archives and notice there is
 no report that ahb(4) worked on Jensen but there is the similar hang:
 http://mail-index.netbsd.org/port-alpha/2000/10/29/0000.html
 
 Looks interrupts on Jensen PICs are not ack'ed properly.
 I don't know what is the right way to handle this, but
 anyway could you try this one (which includes some PIC fixes)?
 http://www.ceres.dti.ne.jp/~tsutsui/netbsd/cdhdtape-GENERIC-20070727.gz
 
 ---
 Index: jensenio_intr.c
 ===================================================================
 RCS file: /cvsroot/src/sys/arch/alpha/jensenio/jensenio_intr.c,v
 retrieving revision 1.6
 diff -u -r1.6 jensenio_intr.c
 --- jensenio_intr.c	27 Jul 2007 13:37:07 -0000	1.6
 +++ jensenio_intr.c	27 Jul 2007 14:27:50 -0000
 @@ -56,6 +56,8 @@
  #include <dev/isa/isareg.h>
  #include <dev/isa/isavar.h>
  
 +#include <dev/ic/i8259reg.h>
 +
  #include <alpha/jensenio/jenseniovar.h>
  
  static bus_space_tag_t pic_iot;
 @@ -71,6 +73,11 @@
  int	jensenio_eisa_intr_alloc(void *, int, int, int *);
  
  #define	JENSEN_MAX_IRQ		16
 +#define	IRQ_SLAVE		2
 +
 +#ifndef STRAY_MAX
 +#define	STRAY_MAX		10
 +#endif
  
  struct alpha_shared_intr *jensenio_eisa_intr;
  
 @@ -103,11 +110,13 @@
  jensenio_specific_eoi(int irq)
  {
  
 -	if (irq > 7)
 -		bus_space_write_1(pic_iot, pic_ioh[1],
 -		    0, 0x20 | (irq & 0x07));
 -	bus_space_write_1(pic_iot, pic_ioh[0],
 -	    0, 0x20 | (irq > 7 ? 2 : irq));
 +	if (irq >= 8) {
 +		bus_space_write_1(pic_iot, pic_ioh[1], PIC_OCW2,
 +		    OCW2_SELECT | OCW2_SL | OCW2_EOI | OCW2_ILS(irq - 8));
 +		irq = IRQ_SLAVE;
 +	}
 +	bus_space_write_1(pic_iot, pic_ioh[0], PIC_OCW2,
 +	    OCW2_SELECT | OCW2_SL | OCW2_EOI | OCW2_ILS(irq));
  }
  
  void
 @@ -128,7 +137,7 @@
  		    i, jensenio_intr_deftype[i]);
  		/* Don't bother with stray interrupts. */
  		alpha_shared_intr_set_maxstrays(jensenio_eisa_intr,
 -		    i, 0);
 +		    i, STRAY_MAX);
  
  		cp = alpha_shared_intr_string(jensenio_eisa_intr, i);
  		sprintf(cp, "irq %d", i);
 @@ -140,8 +149,8 @@
  	/*
  	 * The cascasde interrupt must be edge triggered and always enabled.
  	 */
 -	jensenio_setlevel(2, 0);
 -	jensenio_enable_intr(2, 1);
 +	jensenio_setlevel(IRQ_SLAVE, 0);
 +	jensenio_enable_intr(IRQ_SLAVE, 1);
  
  	/*
  	 * Initialize the EISA chipset.
 @@ -289,12 +298,12 @@
  	pic = irq >> 3;
  	bit = 1 << (irq & 0x7);
  
 -	mask = bus_space_read_1(pic_iot, pic_ioh[pic], 1);
 +	mask = bus_space_read_1(pic_iot, pic_ioh[pic], PIC_OCW1);
  	if (onoff)
  		mask &= ~bit;
  	else
  		mask |= bit;
 -	bus_space_write_1(pic_iot, pic_ioh[pic], 1, mask);
 +	bus_space_write_1(pic_iot, pic_ioh[pic], PIC_OCW1, mask);
  }
  
  void
 @@ -334,4 +343,58 @@
  	 */
  	if (bus_space_map(pic_iot, 0x4d0, 2, 0, &pic_elcr_ioh))
  		panic("jensenio_init_intr: unable to map ELCR registers");
 +
 +	/*
 +	 * Initialize master PIC.
 +	 */
 +
 +	/* reset; program device, four bytes */
 +	bus_space_write_1(pic_iot, picaddr[0],
 +	    PIC_ICW1, ICW1_SELECT | ICW1_IC4);
 +	/* starting at this vector index */
 +	bus_space_write_1(pic_iot, picaddr[0],
 +	    PIC_ICW2, 0);				/* XXX */
 +	/* slave on line 2 */
 +	bus_space_write_1(pic_iot, picaddr[0],
 +	    PIC_ICW3, ICW3_CASCADE(IRQ_SLAVE));
 +	/* special fully nested mode, 8086 mode */
 +	bus_space_write_1(pic_iot, picaddr[0],
 +	    PIC_ICW4, ICW4_SFNM | ICW4_8086);
 +	/* special mask mode */
 +	bus_space_write_1(pic_iot, picaddr[0],
 +	    PIC_OCW3, OCW3_SELECT | OCW3_SSMM | OCW3_SMM);
 +	/* read IRR by default */
 +	bus_space_write_1(pic_iot, picaddr[0],
 +	    PIC_OCW3, OCW3_SELECT | OCW3_RR);
 +
 +	/*
 +	 * Initialize slave PIC.
 +	 */
 +
 +	/* reset; program device, four bytes */
 +	bus_space_write_1(pic_iot, picaddr[1],
 +	    PIC_ICW1, ICW1_SELECT | ICW1_IC4);
 +	/* starting at this vector index */
 +	bus_space_write_1(pic_iot, picaddr[1],
 +	    PIC_ICW2, 8);				/* XXX */
 +	/* slave connected to line 2 of master */
 +	bus_space_write_1(pic_iot, picaddr[1],
 +	    PIC_ICW3, ICW3_SIC(IRQ_SLAVE));
 +	/* special fully nested mode, 8086 mode */
 +	bus_space_write_1(pic_iot, picaddr[1],
 +	    PIC_ICW4, ICW4_SFNM | ICW4_8086);
 +	/* special mask mode */
 +	bus_space_write_1(pic_iot, picaddr[1],
 +	    PIC_OCW3, OCW3_SELECT | OCW3_SSMM | OCW3_SMM);
 +	/* read IRR by default */
 +	bus_space_write_1(pic_iot, picaddr[1],
 +	    PIC_OCW3, OCW3_SELECT | OCW3_RR);
 +
 +	/* mask all interrupts */
 +	bus_space_write_1(pic_iot, picaddr[0], PIC_OCW1, 0xff);
 +	bus_space_write_1(pic_iot, picaddr[1], PIC_OCW1, 0xff);
 +
 +	/* default to edge-triggered */
 +	bus_space_write_1(pic_iot, pic_elcr_ioh, 0, 0);
 +	bus_space_write_1(pic_iot, pic_elcr_ioh, 1, 0);
  }
 
 ---
 Izumi Tsutsui