All of lore.kernel.org
 help / color / mirror / Atom feed
* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
@ 2008-07-11 11:35 Ricardo Ribalda Delgado
  2008-07-11 12:09 ` Michal Simek
  2008-07-11 12:22 ` Stefan Roese
  0 siblings, 2 replies; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-11 11:35 UTC (permalink / raw)
  To: u-boot

This patchs gives support for the embbedded ppc440
on the Virtex5 FPGAs
---
 cpu/ppc4xx/4xx_enet.c       |    3 +-
 cpu/ppc4xx/4xx_uart.c       |    3 +
 cpu/ppc4xx/cpu.c            |    4 +
 cpu/ppc4xx/gpio.c           |    5 +
 cpu/ppc4xx/interrupts.c     |  238 ++++++++++++++++++++++++++++++++++++-------
 cpu/ppc4xx/miiphy.c         |    5 +
 cpu/ppc4xx/speed.c          |    6 +-
 include/asm-ppc/processor.h |    3 +-
 net/eth.c                   |    3 +-
 9 files changed, 228 insertions(+), 42 deletions(-)

diff --git a/cpu/ppc4xx/4xx_enet.c b/cpu/ppc4xx/4xx_enet.c
index 4e863dc..cf26237 100644
--- a/cpu/ppc4xx/4xx_enet.c
+++ b/cpu/ppc4xx/4xx_enet.c
@@ -97,7 +97,8 @@
  * network support enabled.
  * Remark: CONFIG_405 describes Xilinx PPC405 FPGA without EMAC controller!
  */
-#if defined(CONFIG_CMD_NET) && !defined(CONFIG_405) && !defined(CONFIG_IOP480)
+#if defined(CONFIG_CMD_NET) && !defined(CONFIG_405) && !defined(CONFIG_IOP480) \
+	&& !defined(CONFIG_440_VIRTEX5)
 
 #if !(defined(CONFIG_MII) || defined(CONFIG_CMD_MII))
 #error "CONFIG_MII has to be defined!"
diff --git a/cpu/ppc4xx/4xx_uart.c b/cpu/ppc4xx/4xx_uart.c
index a7587d4..37d3dbc 100644
--- a/cpu/ppc4xx/4xx_uart.c
+++ b/cpu/ppc4xx/4xx_uart.c
@@ -48,6 +48,7 @@
 #include <watchdog.h>
 #include <asm/ppc4xx-intvec.h>
 
+#if !defined(CONFIG_440_VIRTEX5)
 #ifdef CONFIG_SERIAL_MULTI
 #include <serial.h>
 #endif
@@ -873,3 +874,5 @@ int serial_tstc(void)
 #endif /* CONFIG_SERIAL_MULTI */
 
 #endif	/* CONFIG_405GP || CONFIG_405CR */
+
+#endif
diff --git a/cpu/ppc4xx/cpu.c b/cpu/ppc4xx/cpu.c
index 39f439d..f510cdd 100644
--- a/cpu/ppc4xx/cpu.c
+++ b/cpu/ppc4xx/cpu.c
@@ -508,6 +508,10 @@ int checkcpu (void)
 		puts("GT Rev. A");
 		strcpy(addstr, "Security/Kasumi support");
 		break;
+	
+	case PVR_VIRTEX5:
+		printf(" VIRTEX5");
+		break;
 
 	default:
 		printf (" UNKNOWN (PVR=%08x)", pvr);
diff --git a/cpu/ppc4xx/gpio.c b/cpu/ppc4xx/gpio.c
index df99f53..59159ee 100644
--- a/cpu/ppc4xx/gpio.c
+++ b/cpu/ppc4xx/gpio.c
@@ -26,6 +26,9 @@
 #include <asm/io.h>
 #include <asm/gpio.h>
 
+
+#if !defined(CONFIG_440_VIRTEX5)
+
 #if defined(CFG_4xx_GPIO_TABLE)
 gpio_param_s const gpio_tab[GPIO_GROUP_MAX][GPIO_MAX] = CFG_4xx_GPIO_TABLE;
 #endif
@@ -253,3 +256,5 @@ void gpio_set_chip_configuration(void)
 	}
 }
 #endif /* CFG_4xx_GPIO_TABLE */
+
+#endif
diff --git a/cpu/ppc4xx/interrupts.c b/cpu/ppc4xx/interrupts.c
index 8620e2b..4648f52 100644
--- a/cpu/ppc4xx/interrupts.c
+++ b/cpu/ppc4xx/interrupts.c
@@ -8,6 +8,10 @@
  * (C) Copyright 2003 (440GX port)
  * Travis B. Sawyer, Sandburst Corporation, tsawyer at sandburst.com
  *
+ * (C) Copyright 2008 (PPC440X05 port for Virtex 5 FX)
+ * Ricardo Ribalda, Universidad Autonoma de Madrid, ricardo.ribalda at uam.es
+ * Work supported by Qtechnology (htpp://qtec.com)
+ *
  * See file CREDITS for list of people who contributed to this
  * project.
  *
@@ -41,6 +45,7 @@ DECLARE_GLOBAL_DATA_PTR;
 /*
  * Define the number of UIC's
  */
+#if !defined(CONFIG_440_VIRTEX5)
 #if defined(CONFIG_440SPE) || \
     defined(CONFIG_460EX) || defined(CONFIG_460GT)
 #define UIC_MAX		4
@@ -54,17 +59,23 @@ DECLARE_GLOBAL_DATA_PTR;
 #else
 #define UIC_MAX		1
 #endif
-
+#else
+void xilinx_pic_enable(void);
+#endif
 /*
  * CPM interrupt vector functions.
  */
-struct	irq_action {
+struct irq_action {
 	interrupt_handler_t *handler;
 	void *arg;
 	int count;
 };
 
+#if !defined(CONFIG_440_VIRTEX5)
 static struct irq_action irq_vecs[UIC_MAX * 32];
+#else
+static struct irq_action irq_vecs[XPAR_INTC_MAX_NUM_INTR_INPUTS];
+#endif
 
 u32 get_dcr(u16);
 void set_dcr(u16, u32);
@@ -81,27 +92,25 @@ static __inline__ void set_evpr(unsigned long val)
 	asm volatile("mtspr 0x03f,%0" : : "r" (val));
 }
 
-#else /* !defined(CONFIG_440) */
+#else				/* !defined(CONFIG_440) */
 
 static __inline__ void set_pit(unsigned long val)
 {
 	asm volatile("mtpit %0" : : "r" (val));
 }
 
-
 static __inline__ void set_tcr(unsigned long val)
 {
 	asm volatile("mttcr %0" : : "r" (val));
 }
 
-
 static __inline__ void set_evpr(unsigned long val)
 {
 	asm volatile("mtevpr %0" : : "r" (val));
 }
-#endif /* defined(CONFIG_440 */
+#endif				/* defined(CONFIG_440 */
 
-int interrupt_init_cpu (unsigned *decrementer_count)
+int interrupt_init_cpu(unsigned *decrementer_count)
 {
 	int vec;
 	unsigned long val;
@@ -112,7 +121,11 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	/*
 	 * Mark all irqs as free
 	 */
+#if !defined (CONFIG_440_VIRTEX5)
 	for (vec = 0; vec < (UIC_MAX * 32); vec++) {
+#else
+	for (vec = 0; vec < XPAR_INTC_MAX_NUM_INTR_INPUTS; vec++) {
+#endif
 		irq_vecs[vec].handler = NULL;
 		irq_vecs[vec].arg = NULL;
 		irq_vecs[vec].count = 0;
@@ -123,19 +136,19 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	 * Init PIT
 	 */
 #if defined(CONFIG_440)
-	val = mfspr( tcr );
-	val &= (~0x04400000);		/* clear DIS & ARE */
-	mtspr( tcr, val );
-	mtspr( dec, 0 );		/* Prevent exception after TSR clear*/
-	mtspr( decar, 0 );		/* clear reload */
-	mtspr( tsr, 0x08000000 );	/* clear DEC status */
-	val = gd->bd->bi_intfreq/1000;	/* 1 msec */
-	mtspr( decar, val );		/* Set auto-reload value */
-	mtspr( dec, val );		/* Set inital val */
+	val = mfspr(tcr);
+	val &= (~0x04400000);	/* clear DIS & ARE */
+	mtspr(tcr, val);
+	mtspr(dec, 0);		/* Prevent exception after TSR clear */
+	mtspr(decar, 0);	/* clear reload */
+	mtspr(tsr, 0x08000000);	/* clear DEC status */
+	val = gd->bd->bi_intfreq / 1000;	/* 1 msec */
+	mtspr(decar, val);	/* Set auto-reload value */
+	mtspr(dec, val);	/* Set inital val */
 #else
 	set_pit(gd->bd->bi_intfreq / 1000);
 #endif
-#endif  /* CONFIG_4xx */
+#endif				/* CONFIG_4xx */
 
 #ifdef CONFIG_ADCIOP
 	/*
@@ -156,6 +169,8 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	 */
 	set_evpr(0x00000000);
 
+#if !defined (CONFIG_440_VIRTEX5)
+
 #if !defined(CONFIG_440GX)
 #if (UIC_MAX > 1)
 	/* Install the UIC1 handlers */
@@ -170,7 +185,7 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	irq_install_handler(VECNUM_UIC3NC, uic_cascade_interrupt, 0);
 	irq_install_handler(VECNUM_UIC3C, uic_cascade_interrupt, 0);
 #endif
-#else /* !defined(CONFIG_440GX) */
+#else				/* !defined(CONFIG_440GX) */
 	/* Take the GX out of compatibility mode
 	 * Travis Sawyer, 9 Mar 2004
 	 * NOTE: 440gx user manual inconsistency here
@@ -179,18 +194,27 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	 */
 	mfsdr(sdr_mfr, val);
 	val &= ~0x10000000;
-	mtsdr(sdr_mfr,val);
+	mtsdr(sdr_mfr, val);
 
 	/* Enable UIC interrupts via UIC Base Enable Register */
 	mtdcr(uicb0sr, UICB0_ALL);
 	mtdcr(uicb0er, 0x54000000);
 	/* None are critical */
 	mtdcr(uicb0cr, 0);
-#endif /* !defined(CONFIG_440GX) */
+#endif				/* !defined(CONFIG_440GX) */
+
+#else
+	/*
+	 * Enable xilinx pic
+	 */
+	xilinx_pic_enable();
+
+#endif
 
 	return (0);
 }
 
+#if !defined(CONFIG_440_VIRTEX5)
 /* Handler for UIC interrupt */
 static void uic_interrupt(u32 uic_base, int vec_base)
 {
@@ -214,7 +238,7 @@ static void uic_interrupt(u32 uic_base, int vec_base)
 
 			if (irq_vecs[vec].handler != NULL) {
 				/* call isr */
-				(*irq_vecs[vec].handler)(irq_vecs[vec].arg);
+				(*irq_vecs[vec].handler) (irq_vecs[vec].arg);
 			} else {
 				set_dcr(uic_base + UIC_ER,
 					get_dcr(uic_base + UIC_ER) &
@@ -227,7 +251,8 @@ static void uic_interrupt(u32 uic_base, int vec_base)
 			 * After servicing the interrupt, we have to remove the
 			 * status indicator
 			 */
-			set_dcr(uic_base + UIC_SR, (0x80000000 >> (vec & 0x1f)));
+			set_dcr(uic_base + UIC_SR,
+				(0x80000000 >> (vec & 0x1f)));
 		}
 
 		/*
@@ -254,10 +279,10 @@ static void uic_cascade_interrupt(void *para)
 #define UIC_BMSR	uic0msr
 #define UIC_BSR		uic0sr
 #endif
-#else /* CONFIG_440 */
+#else				/* CONFIG_440 */
 #define UIC_BMSR	uicmsr
 #define UIC_BSR		uicsr
-#endif /* CONFIG_440 */
+#endif				/* CONFIG_440 */
 
 /*
  * Handle external interrupts
@@ -294,9 +319,9 @@ void external_interrupt(struct pt_regs *regs)
 	if ((UICB0_UIC0CI & uic_msr) || (UICB0_UIC0NCI & uic_msr))
 		uic_interrupt(UIC0_DCR_BASE, 0);
 #endif
-#else /* CONFIG_440 */
+#else				/* CONFIG_440 */
 	uic_interrupt(UIC0_DCR_BASE, 0);
-#endif /* CONFIG_440 */
+#endif				/* CONFIG_440 */
 
 	mtdcr(UIC_BSR, uic_msr);
 
@@ -313,7 +338,8 @@ void irq_install_handler(int vec, interrupt_handler_t * handler, void *arg)
 	/*
 	 * Print warning when replacing with a different irq vector
 	 */
-	if ((irq_vecs[vec].handler != NULL) && (irq_vecs[vec].handler != handler)) {
+	if ((irq_vecs[vec].handler != NULL)
+	    && (irq_vecs[vec].handler != handler)) {
 		printf("Interrupt vector %d: handler 0x%x replacing 0x%x\n",
 		       vec, (uint) handler, (uint) irq_vecs[vec].handler);
 	}
@@ -339,7 +365,7 @@ void irq_install_handler(int vec, interrupt_handler_t * handler, void *arg)
 	debug("Install interrupt for vector %d ==> %p\n", vec, handler);
 }
 
-void irq_free_handler (int vec)
+void irq_free_handler(int vec)
 {
 	int i;
 
@@ -365,28 +391,166 @@ void irq_free_handler (int vec)
 	irq_vecs[vec].handler = NULL;
 	irq_vecs[vec].arg = NULL;
 }
+#else
+
+#define intc    XPAR_INTC_0_BASEADDR
+#define ISR (0*4)		/* Interrupt Status Register */
+#define IPR (1*4)		/* Interrupt Pending Register */
+#define IER (2*4)		/* Interrupt Enable Register */
+#define IAR (3*4)		/* Interrupt Acknowledge Register */
+#define SIE (4*4)		/* Set Interrupt Enable bits */
+#define CIE (5*4)		/* Clear Interrupt Enable bits */
+#define IVR (6*4)		/* Interrupt Vector Register */
+#define MER (7*4)		/* Master Enable Register */
+
+#define intc_out_be32(addr, mask)     out32((addr), (mask))
+#define intc_in_be32(addr)            in32((addr))
+
+void xilinx_pic_enable(void)
+{
+
+	printf("Xilinx PIC at 0x%8x\n", intc);
+
+	/*
+	 * Disable all external interrupts until they are
+	 * explicitly requested.
+	 */
+	intc_out_be32(intc + IER, 0);
+
+	/* Acknowledge any pending interrupts just in case. */
+	intc_out_be32(intc + IAR, ~(u32) 0);
+
+	/* Turn on the Master Enable. */
+	intc_out_be32(intc + MER, 0x3UL);
+
+	return;
+
+}
+
+int xilinx_pic_irq_get(void)
+{
+	u32 irq;
+	irq = intc_in_be32(intc + IVR);
+
+	/* If no interrupt is pending then all bits of the IVR are set to 1. As
+	 * the IVR is as many bits wide as numbers of inputs are available.
+	 * Therefore, if all bits of the IVR are set to one, its content will
+	 * be bigger than XPAR_INTC_MAX_NUM_INTR_INPUTS.
+	 */
+	if (irq >= XPAR_INTC_MAX_NUM_INTR_INPUTS)
+		irq = -1;	/* report no pending interrupt. */
+
+	debug("get_irq: %d\n", irq);
+	return (irq);
+}
+
+static void xilinx_pic_irq_enable(unsigned int irq)
+{
+	unsigned long mask = (0x00000001 << (irq & 31));
+	debug("enable: %d\n", irq);
+	intc_out_be32(intc + SIE, mask);
+}
+
+static void xilinx_pic_irq_disable(unsigned int irq)
+{
+	unsigned long mask = (0x00000001 << (irq & 31));
+	debug("disable: %d\n", irq);
+	intc_out_be32(intc + CIE, mask);
+}
+
+static void xilinx_pic_irq_ack(unsigned int irq)
+{
+	unsigned long mask = (0x00000001 << (irq & 31));
+	debug("ack: %d\n", irq);
+	intc_out_be32(intc + IAR, mask);
+}
+
+static void xilinx_pic_interrupt(void)
+{
+	int irq;
+
+	irq = xilinx_pic_irq_get();
+	if (irq < 0)
+		return;
+
+	irq_vecs[irq].count++;
+
+	if (irq_vecs[irq].handler != NULL) {
+		/* call isr */
+		(*irq_vecs[irq].handler) (irq_vecs[irq].arg);
+
+	} else {
+		xilinx_pic_irq_disable(irq);
+		printf("Masking bogus interrupt %d\n", irq);
+	}
+
+	xilinx_pic_irq_ack(irq);
+	return;
+}
+
+void external_interrupt(struct pt_regs *regs)
+{
+	xilinx_pic_interrupt();
+}
+
+/*
+ * Install and free a interrupt handler.
+ */
+void irq_install_handler(int vec, interrupt_handler_t * handler, void *arg)
+{
+	/*
+	 * Print warning when replacing with a different irq vector
+	 */
+	if ((irq_vecs[vec].handler != NULL)
+	    && (irq_vecs[vec].handler != handler)) {
+		printf("Interrupt vector %d: handler 0x%x replacing 0x%x\n",
+		       vec, (uint) handler, (uint) irq_vecs[vec].handler);
+	}
+	irq_vecs[vec].handler = handler;
+	irq_vecs[vec].arg = arg;
+
+	xilinx_pic_irq_enable(vec);
+
+	debug("Install interrupt for vector %d ==> %p\n", vec, handler);
+}
+
+void irq_free_handler(int vec)
+{
+	debug("Free interrupt for vector %d ==> %p\n",
+	      vec, irq_vecs[vec].handler);
+
+	xilinx_pic_irq_disable(vec);
+
+	irq_vecs[vec].handler = NULL;
+	irq_vecs[vec].arg = NULL;
+}
+
+#endif
 
-void timer_interrupt_cpu (struct pt_regs *regs)
+void timer_interrupt_cpu(struct pt_regs *regs)
 {
 	/* nothing to do here */
 	return;
 }
 
 #if defined(CONFIG_CMD_IRQ)
-int do_irqinfo(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+int do_irqinfo(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 {
 	int vec;
 
-	printf ("Interrupt-Information:\n");
-	printf ("Nr  Routine   Arg       Count\n");
+	printf("Interrupt-Information:\n");
+	printf("Nr  Routine   Arg       Count\n");
 
+#if !defined (CONFIG_440_VIRTEX5)
 	for (vec = 0; vec < (UIC_MAX * 32); vec++) {
+#else
+	for (vec = 0; vec < XPAR_INTC_MAX_NUM_INTR_INPUTS; vec++) {
+#endif
 		if (irq_vecs[vec].handler != NULL) {
-			printf ("%02d  %08lx  %08lx  %d\n",
-				vec,
-				(ulong)irq_vecs[vec].handler,
-				(ulong)irq_vecs[vec].arg,
-				irq_vecs[vec].count);
+			printf("%02d  %08lx  %08lx  %d\n",
+			       vec,
+			       (ulong) irq_vecs[vec].handler,
+			       (ulong) irq_vecs[vec].arg, irq_vecs[vec].count);
 		}
 	}
 
diff --git a/cpu/ppc4xx/miiphy.c b/cpu/ppc4xx/miiphy.c
index c882720..172fbcd 100644
--- a/cpu/ppc4xx/miiphy.c
+++ b/cpu/ppc4xx/miiphy.c
@@ -43,6 +43,9 @@
 #include <405_mal.h>
 #include <miiphy.h>
 
+
+#if !defined(CONFIG_440_VIRTEX5)
+
 #if !defined(CONFIG_PHY_CLK_FREQ)
 #define CONFIG_PHY_CLK_FREQ	0
 #endif
@@ -331,3 +334,5 @@ int emac4xx_miiphy_write (char *devname, unsigned char addr, unsigned char reg,
 {
 	return emac_miiphy_command(addr, reg, EMAC_STACR_WRITE, value);
 }
+
+#endif
diff --git a/cpu/ppc4xx/speed.c b/cpu/ppc4xx/speed.c
index 34bd721..d1681e4 100644
--- a/cpu/ppc4xx/speed.c
+++ b/cpu/ppc4xx/speed.c
@@ -415,7 +415,8 @@ ulong get_PCI_freq (void)
 	return sys_info.freqPCI;
 }
 
-#elif !defined(CONFIG_440GX) && !defined(CONFIG_440SP) && !defined(CONFIG_440SPE)
+#elif !defined(CONFIG_440GX) && !defined(CONFIG_440SP) && !defined(CONFIG_440SPE)\
+	&&!defined(CONFIG_440_VIRTEX5)
 void get_sys_info (sys_info_t * sysInfo)
 {
 	unsigned long strp0;
@@ -448,6 +449,8 @@ void get_sys_info (sys_info_t * sysInfo)
 	sysInfo->freqUART = sysInfo->freqPLB;
 }
 #else
+
+#if !defined(CONFIG_440_VIRTEX5)
 void get_sys_info (sys_info_t * sysInfo)
 {
 	unsigned long strp0;
@@ -534,6 +537,7 @@ void get_sys_info (sys_info_t * sysInfo)
 }
 
 #endif
+#endif
 
 #if defined(CONFIG_YUCCA)
 unsigned long determine_sysper(void)
diff --git a/include/asm-ppc/processor.h b/include/asm-ppc/processor.h
index 10fd478..88f193a 100644
--- a/include/asm-ppc/processor.h
+++ b/include/asm-ppc/processor.h
@@ -827,13 +827,12 @@
 #define PVR_7400	0x000C0000
 #define PVR_7410	0x800C0000
 #define PVR_7450	0x80000000
-
 #define PVR_85xx	0x80200000
 #define PVR_85xx_REV1	(PVR_85xx | 0x0010)
 #define PVR_85xx_REV2	(PVR_85xx | 0x0020)
-
 #define PVR_86xx	0x80040000
 #define PVR_86xx_REV1	(PVR_86xx | 0x0010)
+#define PVR_VIRTEX5     0x7ff21912
 
 /*
  * For the 8xx processors, all of them report the same PVR family for
diff --git a/net/eth.c b/net/eth.c
index 7fc9aee..54b59b8 100644
--- a/net/eth.c
+++ b/net/eth.c
@@ -621,7 +621,8 @@ int eth_initialize(bd_t *bis)
 	at91rm9200_miiphy_initialize(bis);
 #endif
 #if defined(CONFIG_4xx) && !defined(CONFIG_IOP480) \
-	&& !defined(CONFIG_AP1000) && !defined(CONFIG_405)
+	&& !defined(CONFIG_AP1000) && !defined(CONFIG_405) \
+	&& !defined(CONFIG_440_VIRTEX5)
 	emac4xx_miiphy_initialize(bis);
 #endif
 #if defined(CONFIG_MCF52x2)
-- 
1.5.6.2

^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 11:35 [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX Ricardo Ribalda Delgado
@ 2008-07-11 12:09 ` Michal Simek
  2008-07-11 12:30   ` Stefan Roese
  2008-07-11 12:33   ` Ricardo Ribalda Delgado
  2008-07-11 12:22 ` Stefan Roese
  1 sibling, 2 replies; 22+ messages in thread
From: Michal Simek @ 2008-07-11 12:09 UTC (permalink / raw)
  To: u-boot

Some days ago a sent to mailing list patch (currently is in) where I rename 
CONFIG_XILINX_ML300 -> CONFIG_XILINX_405.

I would like to see if you can use the same style for 440 -> CONFIG_XILINX_440.
I have no detail information about ppc440 but IMHO only virtex5 fx (or whatever) support it -> 
make no sense to me use virtex5 in name.

SR: Do you agree with me?

There is big part of code relate with interrupt controller which is the same with microblaze.
This should be handled in the same way. Any suggestion? (Do generic driver?)

M

BTW: some comments in code.



author	


This patchs gives support for the embbedded ppc440
on the Virtex5 FPGAs
---
 cpu/ppc4xx/4xx_enet.c       |    3 +-
 cpu/ppc4xx/4xx_uart.c       |    3 +
 cpu/ppc4xx/cpu.c            |    4 +
 cpu/ppc4xx/gpio.c           |    5 +
 cpu/ppc4xx/interrupts.c     |  238 ++++++++++++++++++++++++++++++++++++-------
 cpu/ppc4xx/miiphy.c         |    5 +
 cpu/ppc4xx/speed.c          |    6 +-
 include/asm-ppc/processor.h |    3 +-
 net/eth.c                   |    3 +-
 9 files changed, 228 insertions(+), 42 deletions(-)

diff --git a/cpu/ppc4xx/4xx_enet.c b/cpu/ppc4xx/4xx_enet.c
index 4e863dc..cf26237 100644
--- a/cpu/ppc4xx/4xx_enet.c
+++ b/cpu/ppc4xx/4xx_enet.c
@@ -97,7 +97,8 @@
  * network support enabled.
  * Remark: CONFIG_405 describes Xilinx PPC405 FPGA without EMAC controller!
  */
-#if defined(CONFIG_CMD_NET) && !defined(CONFIG_405) && !defined(CONFIG_IOP480)
+#if defined(CONFIG_CMD_NET) && !defined(CONFIG_405) && !defined(CONFIG_IOP480)
\
+	&& !defined(CONFIG_440_VIRTEX5)
 
 #if !(defined(CONFIG_MII) || defined(CONFIG_CMD_MII))
 #error "CONFIG_MII has to be defined!"
diff --git a/cpu/ppc4xx/4xx_uart.c b/cpu/ppc4xx/4xx_uart.c
index a7587d4..37d3dbc 100644
--- a/cpu/ppc4xx/4xx_uart.c
+++ b/cpu/ppc4xx/4xx_uart.c
@@ -48,6 +48,7 @@
 #include <watchdog.h>
 #include <asm/ppc4xx-intvec.h>
 
+#if !defined(CONFIG_440_VIRTEX5)
 #ifdef CONFIG_SERIAL_MULTI
 #include <serial.h>
 #endif
@@ -873,3 +874,5 @@ int serial_tstc(void)
 #endif /* CONFIG_SERIAL_MULTI */
 
 #endif	/* CONFIG_405GP || CONFIG_405CR */
+
+#endif
diff --git a/cpu/ppc4xx/cpu.c b/cpu/ppc4xx/cpu.c
index 39f439d..f510cdd 100644
--- a/cpu/ppc4xx/cpu.c
+++ b/cpu/ppc4xx/cpu.c
@@ -508,6 +508,10 @@ int checkcpu (void)
 		puts("GT Rev. A");
 		strcpy(addstr, "Security/Kasumi support");
 		break;
+	
+	case PVR_VIRTEX5:
+		printf(" VIRTEX5");
+		break;
 

why you use printf here? puts is enough.




 	default:
 		printf (" UNKNOWN (PVR=%08x)", pvr);
diff --git a/cpu/ppc4xx/gpio.c b/cpu/ppc4xx/gpio.c
index df99f53..59159ee 100644
--- a/cpu/ppc4xx/gpio.c
+++ b/cpu/ppc4xx/gpio.c
@@ -26,6 +26,9 @@
 #include <asm/io.h>
 #include <asm/gpio.h>
 
+
+#if !defined(CONFIG_440_VIRTEX5)
+
 #if defined(CFG_4xx_GPIO_TABLE)
 gpio_param_s const gpio_tab[GPIO_GROUP_MAX][GPIO_MAX] = CFG_4xx_GPIO_TABLE;
 #endif
@@ -253,3 +256,5 @@ void gpio_set_chip_configuration(void)
 	}
 }
 #endif /* CFG_4xx_GPIO_TABLE */
+
+#endif
diff --git a/cpu/ppc4xx/interrupts.c b/cpu/ppc4xx/interrupts.c
index 8620e2b..4648f52 100644
--- a/cpu/ppc4xx/interrupts.c
+++ b/cpu/ppc4xx/interrupts.c
@@ -8,6 +8,10 @@
  * (C) Copyright 2003 (440GX port)
  * Travis B. Sawyer, Sandburst Corporation, tsawyer at sandburst.com
  *
+ * (C) Copyright 2008 (PPC440X05 port for Virtex 5 FX)
+ * Ricardo Ribalda, Universidad Autonoma de Madrid, ricardo.ribalda at uam.es
+ * Work supported by Qtechnology (htpp://qtec.com)
+ *
  * See file CREDITS for list of people who contributed to this
  * project.
  *
@@ -41,6 +45,7 @@ DECLARE_GLOBAL_DATA_PTR;
 /*
  * Define the number of UIC's
  */
+#if !defined(CONFIG_440_VIRTEX5)
 #if defined(CONFIG_440SPE) || \
     defined(CONFIG_460EX) || defined(CONFIG_460GT)
 #define UIC_MAX		4
@@ -54,17 +59,23 @@ DECLARE_GLOBAL_DATA_PTR;
 #else
 #define UIC_MAX		1
 #endif
-
+#else
+void xilinx_pic_enable(void);
+#endif
 /*
  * CPM interrupt vector functions.
  */
-struct	irq_action {
+struct irq_action {
 	interrupt_handler_t *handler;
 	void *arg;
 	int count;
 };
 
+#if !defined(CONFIG_440_VIRTEX5)
 static struct irq_action irq_vecs[UIC_MAX * 32];
+#else
+static struct irq_action irq_vecs[XPAR_INTC_MAX_NUM_INTR_INPUTS];
+#endif
 
 u32 get_dcr(u16);
 void set_dcr(u16, u32);
@@ -81,27 +92,25 @@ static __inline__ void set_evpr(unsigned long val)
 	asm volatile("mtspr 0x03f,%0" : : "r" (val));
 }
 
-#else /* !defined(CONFIG_440) */
+#else				/* !defined(CONFIG_440) */
 
 static __inline__ void set_pit(unsigned long val)
 {
 	asm volatile("mtpit %0" : : "r" (val));
 }
 
-
 static __inline__ void set_tcr(unsigned long val)
 {
 	asm volatile("mttcr %0" : : "r" (val));
 }
 
-
 static __inline__ void set_evpr(unsigned long val)
 {
 	asm volatile("mtevpr %0" : : "r" (val));
 }
-#endif /* defined(CONFIG_440 */
+#endif				/* defined(CONFIG_440 */
 
-int interrupt_init_cpu (unsigned *decrementer_count)
+int interrupt_init_cpu(unsigned *decrementer_count)
 {
 	int vec;
 	unsigned long val;
@@ -112,7 +121,11 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	/*
 	 * Mark all irqs as free
 	 */
+#if !defined (CONFIG_440_VIRTEX5)
 	for (vec = 0; vec < (UIC_MAX * 32); vec++) {
+#else
+	for (vec = 0; vec < XPAR_INTC_MAX_NUM_INTR_INPUTS; vec++) {
+#endif

:-( no use this loooooooooooooong value which comes from generated xparameters.h.
SR:Am I understand correctly that 405 or 440 use 32 bits (64...) wide interrupt controllers?

 		irq_vecs[vec].handler = NULL;
 		irq_vecs[vec].arg = NULL;
 		irq_vecs[vec].count = 0;
@@ -123,19 +136,19 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	 * Init PIT
 	 */
 #if defined(CONFIG_440)
-	val = mfspr( tcr );
-	val &= (~0x04400000);		/* clear DIS & ARE */
-	mtspr( tcr, val );
-	mtspr( dec, 0 );		/* Prevent exception after TSR clear*/
-	mtspr( decar, 0 );		/* clear reload */
-	mtspr( tsr, 0x08000000 );	/* clear DEC status */
-	val = gd->bd->bi_intfreq/1000;	/* 1 msec */
-	mtspr( decar, val );		/* Set auto-reload value */
-	mtspr( dec, val );		/* Set inital val */
+	val = mfspr(tcr);
+	val &= (~0x04400000);	/* clear DIS & ARE */
+	mtspr(tcr, val);
+	mtspr(dec, 0);		/* Prevent exception after TSR clear */
+	mtspr(decar, 0);	/* clear reload */
+	mtspr(tsr, 0x08000000);	/* clear DEC status */
+	val = gd->bd->bi_intfreq / 1000;	/* 1 msec */
+	mtspr(decar, val);	/* Set auto-reload value */
+	mtspr(dec, val);	/* Set inital val */
 #else
 	set_pit(gd->bd->bi_intfreq / 1000);
 #endif
-#endif  /* CONFIG_4xx */
+#endif				/* CONFIG_4xx */
 
IMHO coding style issue

 #ifdef CONFIG_ADCIOP
 	/*
@@ -156,6 +169,8 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	 */
 	set_evpr(0x00000000);
 
+#if !defined (CONFIG_440_VIRTEX5)
+
 #if !defined(CONFIG_440GX)
 #if (UIC_MAX > 1)
 	/* Install the UIC1 handlers */
@@ -170,7 +185,7 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	irq_install_handler(VECNUM_UIC3NC, uic_cascade_interrupt, 0);
 	irq_install_handler(VECNUM_UIC3C, uic_cascade_interrupt, 0);
 #endif
-#else /* !defined(CONFIG_440GX) */
+#else				/* !defined(CONFIG_440GX) */

coding style

 	/* Take the GX out of compatibility mode
 	 * Travis Sawyer, 9 Mar 2004
 	 * NOTE: 440gx user manual inconsistency here
@@ -179,18 +194,27 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	 */
 	mfsdr(sdr_mfr, val);
 	val &= ~0x10000000;
-	mtsdr(sdr_mfr,val);
+	mtsdr(sdr_mfr, val);
 
 	/* Enable UIC interrupts via UIC Base Enable Register */
 	mtdcr(uicb0sr, UICB0_ALL);
 	mtdcr(uicb0er, 0x54000000);
 	/* None are critical */
 	mtdcr(uicb0cr, 0);
-#endif /* !defined(CONFIG_440GX) */
+#endif				/* !defined(CONFIG_440GX) */

coding style

+
+#else
+	/*
+	 * Enable xilinx pic
+	 */
+	xilinx_pic_enable();

so big comment


+#endif
 
 	return (0);
 }
 
+#if !defined(CONFIG_440_VIRTEX5)
 /* Handler for UIC interrupt */
 static void uic_interrupt(u32 uic_base, int vec_base)
 {
@@ -214,7 +238,7 @@ static void uic_interrupt(u32 uic_base, int vec_base)
 
 			if (irq_vecs[vec].handler != NULL) {
 				/* call isr */
-				(*irq_vecs[vec].handler)(irq_vecs[vec].arg);
+				(*irq_vecs[vec].handler) (irq_vecs[vec].arg);
 			} else {
 				set_dcr(uic_base + UIC_ER,
 					get_dcr(uic_base + UIC_ER) &
@@ -227,7 +251,8 @@ static void uic_interrupt(u32 uic_base, int vec_base)
 			 * After servicing the interrupt, we have to remove the
 			 * status indicator
 			 */
-			set_dcr(uic_base + UIC_SR, (0x80000000 >> (vec & 0x1f)));
+			set_dcr(uic_base + UIC_SR,
+				(0x80000000 >> (vec & 0x1f)));
 		}
 
 		/*
@@ -254,10 +279,10 @@ static void uic_cascade_interrupt(void *para)
 #define UIC_BMSR	uic0msr
 #define UIC_BSR		uic0sr
 #endif
-#else /* CONFIG_440 */
+#else				/* CONFIG_440 */

CS

 #define UIC_BMSR	uicmsr
 #define UIC_BSR		uicsr
-#endif /* CONFIG_440 */
+#endif				/* CONFIG_440 */
 
CS

 /*
  * Handle external interrupts
@@ -294,9 +319,9 @@ void external_interrupt(struct pt_regs *regs)
 	if ((UICB0_UIC0CI & uic_msr) || (UICB0_UIC0NCI & uic_msr))
 		uic_interrupt(UIC0_DCR_BASE, 0);
 #endif
-#else /* CONFIG_440 */
+#else				/* CONFIG_440 */
 	uic_interrupt(UIC0_DCR_BASE, 0);
-#endif /* CONFIG_440 */
+#endif				/* CONFIG_440 */
 
 	mtdcr(UIC_BSR, uic_msr);
 
@@ -313,7 +338,8 @@ void irq_install_handler(int vec, interrupt_handler_t *
handler, void *arg)
 	/*
 	 * Print warning when replacing with a different irq vector
 	 */
-	if ((irq_vecs[vec].handler != NULL) && (irq_vecs[vec].handler != handler)) {
+	if ((irq_vecs[vec].handler != NULL)
+	    && (irq_vecs[vec].handler != handler)) {
 		printf("Interrupt vector %d: handler 0x%x replacing 0x%x\n",
 		       vec, (uint) handler, (uint) irq_vecs[vec].handler);
 	}
@@ -339,7 +365,7 @@ void irq_install_handler(int vec, interrupt_handler_t *
handler, void *arg)
 	debug("Install interrupt for vector %d ==> %p\n", vec, handler);
 }
 
-void irq_free_handler (int vec)
+void irq_free_handler(int vec)
 {
 	int i;
 
@@ -365,28 +391,166 @@ void irq_free_handler (int vec)
 	irq_vecs[vec].handler = NULL;
 	irq_vecs[vec].arg = NULL;
 }
+#else
+
+#define intc    XPAR_INTC_0_BASEADDR
+#define ISR (0*4)		/* Interrupt Status Register */
+#define IPR (1*4)		/* Interrupt Pending Register */
+#define IER (2*4)		/* Interrupt Enable Register */
+#define IAR (3*4)		/* Interrupt Acknowledge Register */
+#define SIE (4*4)		/* Set Interrupt Enable bits */
+#define CIE (5*4)		/* Clear Interrupt Enable bits */
+#define IVR (6*4)		/* Interrupt Vector Register */
+#define MER (7*4)		/* Master Enable Register */

these look weird to me - have defines value in the middle of source code -> maybe header.

this looks like duplication with MB where I use interrupt controller.


+#define intc_out_be32(addr, mask)     out32((addr), (mask))
+#define intc_in_be32(addr)            in32((addr))
+
+void xilinx_pic_enable(void)
+{
+
+	printf("Xilinx PIC at 0x%8x\n", intc);
+
+	/*
+	 * Disable all external interrupts until they are
+	 * explicitly requested.
+	 */
+	intc_out_be32(intc + IER, 0);
+
+	/* Acknowledge any pending interrupts just in case. */
+	intc_out_be32(intc + IAR, ~(u32) 0);
+
+	/* Turn on the Master Enable. */
+	intc_out_be32(intc + MER, 0x3UL);
+
+	return;
+
+}
+
+int xilinx_pic_irq_get(void)
+{
+	u32 irq;
+	irq = intc_in_be32(intc + IVR);
+
+	/* If no interrupt is pending then all bits of the IVR are set to 1. As
+	 * the IVR is as many bits wide as numbers of inputs are available.
+	 * Therefore, if all bits of the IVR are set to one, its content will
+	 * be bigger than XPAR_INTC_MAX_NUM_INTR_INPUTS.
+	 */
+	if (irq >= XPAR_INTC_MAX_NUM_INTR_INPUTS)
+		irq = -1;	/* report no pending interrupt. */
+
+	debug("get_irq: %d\n", irq);
+	return (irq);
+}
+
+static void xilinx_pic_irq_enable(unsigned int irq)
+{
+	unsigned long mask = (0x00000001 << (irq & 31));
+	debug("enable: %d\n", irq);
+	intc_out_be32(intc + SIE, mask);
+}
+
+static void xilinx_pic_irq_disable(unsigned int irq)
+{
+	unsigned long mask = (0x00000001 << (irq & 31));
+	debug("disable: %d\n", irq);
+	intc_out_be32(intc + CIE, mask);
+}
+
+static void xilinx_pic_irq_ack(unsigned int irq)
+{
+	unsigned long mask = (0x00000001 << (irq & 31));
+	debug("ack: %d\n", irq);
+	intc_out_be32(intc + IAR, mask);
+}
+
+static void xilinx_pic_interrupt(void)
+{
+	int irq;
+
+	irq = xilinx_pic_irq_get();
+	if (irq < 0)
+		return;
+
+	irq_vecs[irq].count++;
+
+	if (irq_vecs[irq].handler != NULL) {
+		/* call isr */
+		(*irq_vecs[irq].handler) (irq_vecs[irq].arg);
+
+	} else {
+		xilinx_pic_irq_disable(irq);
+		printf("Masking bogus interrupt %d\n", irq);
+	}
+
+	xilinx_pic_irq_ack(irq);
+	return;
+}
+
+void external_interrupt(struct pt_regs *regs)
+{
+	xilinx_pic_interrupt();
+}
+
+/*
+ * Install and free a interrupt handler.
+ */
+void irq_install_handler(int vec, interrupt_handler_t * handler, void *arg)
+{
+	/*
+	 * Print warning when replacing with a different irq vector
+	 */
+	if ((irq_vecs[vec].handler != NULL)
+	    && (irq_vecs[vec].handler != handler)) {
+		printf("Interrupt vector %d: handler 0x%x replacing 0x%x\n",
+		       vec, (uint) handler, (uint) irq_vecs[vec].handler);
+	}
+	irq_vecs[vec].handler = handler;
+	irq_vecs[vec].arg = arg;
+
+	xilinx_pic_irq_enable(vec);
+
+	debug("Install interrupt for vector %d ==> %p\n", vec, handler);
+}
+
+void irq_free_handler(int vec)
+{
+	debug("Free interrupt for vector %d ==> %p\n",
+	      vec, irq_vecs[vec].handler);
+
+	xilinx_pic_irq_disable(vec);
+
+	irq_vecs[vec].handler = NULL;
+	irq_vecs[vec].arg = NULL;
+}
+
+#endif
 
-void timer_interrupt_cpu (struct pt_regs *regs)
+void timer_interrupt_cpu(struct pt_regs *regs)
 {
 	/* nothing to do here */
 	return;
 }
 
 #if defined(CONFIG_CMD_IRQ)
-int do_irqinfo(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+int do_irqinfo(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
 {
 	int vec;
 
-	printf ("Interrupt-Information:\n");
-	printf ("Nr  Routine   Arg       Count\n");
+	printf("Interrupt-Information:\n");
+	printf("Nr  Routine   Arg       Count\n");
 
+#if !defined (CONFIG_440_VIRTEX5)
 	for (vec = 0; vec < (UIC_MAX * 32); vec++) {
+#else
+	for (vec = 0; vec < XPAR_INTC_MAX_NUM_INTR_INPUTS; vec++) {
+#endif
 		if (irq_vecs[vec].handler != NULL) {
-			printf ("%02d  %08lx  %08lx  %d\n",
-				vec,
-				(ulong)irq_vecs[vec].handler,
-				(ulong)irq_vecs[vec].arg,
-				irq_vecs[vec].count);
+			printf("%02d  %08lx  %08lx  %d\n",
+			       vec,
+			       (ulong) irq_vecs[vec].handler,
+			       (ulong) irq_vecs[vec].arg, irq_vecs[vec].count);
 		}
 	}
 
diff --git a/cpu/ppc4xx/miiphy.c b/cpu/ppc4xx/miiphy.c
index c882720..172fbcd 100644
--- a/cpu/ppc4xx/miiphy.c
+++ b/cpu/ppc4xx/miiphy.c
@@ -43,6 +43,9 @@
 #include <405_mal.h>
 #include <miiphy.h>
 
+
+#if !defined(CONFIG_440_VIRTEX5)
+
 #if !defined(CONFIG_PHY_CLK_FREQ)
 #define CONFIG_PHY_CLK_FREQ	0
 #endif
@@ -331,3 +334,5 @@ int emac4xx_miiphy_write (char *devname, unsigned char addr,
unsigned char reg,
 {
 	return emac_miiphy_command(addr, reg, EMAC_STACR_WRITE, value);
 }
+
+#endif
diff --git a/cpu/ppc4xx/speed.c b/cpu/ppc4xx/speed.c
index 34bd721..d1681e4 100644
--- a/cpu/ppc4xx/speed.c
+++ b/cpu/ppc4xx/speed.c
@@ -415,7 +415,8 @@ ulong get_PCI_freq (void)
 	return sys_info.freqPCI;
 }
 
-#elif !defined(CONFIG_440GX) && !defined(CONFIG_440SP) &&
!defined(CONFIG_440SPE)
+#elif !defined(CONFIG_440GX) && !defined(CONFIG_440SP) &&
!defined(CONFIG_440SPE)\
+	&&!defined(CONFIG_440_VIRTEX5)
 void get_sys_info (sys_info_t * sysInfo)
 {
 	unsigned long strp0;
@@ -448,6 +449,8 @@ void get_sys_info (sys_info_t * sysInfo)
 	sysInfo->freqUART = sysInfo->freqPLB;
 }
 #else
+
+#if !defined(CONFIG_440_VIRTEX5)
 void get_sys_info (sys_info_t * sysInfo)
 {
 	unsigned long strp0;
@@ -534,6 +537,7 @@ void get_sys_info (sys_info_t * sysInfo)
 }
 
 #endif
+#endif
 
 #if defined(CONFIG_YUCCA)
 unsigned long determine_sysper(void)
diff --git a/include/asm-ppc/processor.h b/include/asm-ppc/processor.h
index 10fd478..88f193a 100644
--- a/include/asm-ppc/processor.h
+++ b/include/asm-ppc/processor.h
@@ -827,13 +827,12 @@
 #define PVR_7400	0x000C0000
 #define PVR_7410	0x800C0000
 #define PVR_7450	0x80000000
-
 #define PVR_85xx	0x80200000
 #define PVR_85xx_REV1	(PVR_85xx | 0x0010)
 #define PVR_85xx_REV2	(PVR_85xx | 0x0020)
-
 #define PVR_86xx	0x80040000
 #define PVR_86xx_REV1	(PVR_86xx | 0x0010)
+#define PVR_VIRTEX5     0x7ff21912
 
 /*
  * For the 8xx processors, all of them report the same PVR family for
diff --git a/net/eth.c b/net/eth.c
index 7fc9aee..54b59b8 100644
--- a/net/eth.c
+++ b/net/eth.c
@@ -621,7 +621,8 @@ int eth_initialize(bd_t *bis)
 	at91rm9200_miiphy_initialize(bis);
 #endif
 #if defined(CONFIG_4xx) && !defined(CONFIG_IOP480) \
-	&& !defined(CONFIG_AP1000) && !defined(CONFIG_405)
+	&& !defined(CONFIG_AP1000) && !defined(CONFIG_405) \
+	&& !defined(CONFIG_440_VIRTEX5)
 	emac4xx_miiphy_initialize(bis);
 #endif
 #if defined(CONFIG_MCF52x2)
-- 
1.5.6.2


-------------------------------------------------------------------------
Sponsored by: SourceForge.net Community Choice Awards: VOTE NOW!
Studies have shown that voting for your favorite open source project,
along with a healthy diet, reduces your potential for chronic lameness
and boredom. Vote Now at http://www.sourceforge.net/community/cca08
_______________________________________________
U-Boot-Users mailing list

U-Boot-Users at lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/u-boot-users

^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 11:35 [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX Ricardo Ribalda Delgado
  2008-07-11 12:09 ` Michal Simek
@ 2008-07-11 12:22 ` Stefan Roese
  2008-07-11 12:36   ` Ricardo Ribalda Delgado
  2008-07-14  0:45   ` Ricardo Ribalda Delgado
  1 sibling, 2 replies; 22+ messages in thread
From: Stefan Roese @ 2008-07-11 12:22 UTC (permalink / raw)
  To: u-boot

Ricardo,

On Friday 11 July 2008, Ricardo Ribalda Delgado wrote:
> This patchs gives support for the embbedded ppc440
> on the Virtex5 FPGAs

Thanks.

Some general comments:

Please rebase your 4xx related patches on the "next" branch of my 
u-boot-ppc4xx repository. I just pushed some bigger rework/cleanup patchsets 
that are destined for the next merge window.

And please add "ppc4xx: " to the beginning of the patch subject and add me to 
CC on 4xx related patches.

More comments below...

> ---
>  cpu/ppc4xx/4xx_enet.c       |    3 +-
>  cpu/ppc4xx/4xx_uart.c       |    3 +
>  cpu/ppc4xx/cpu.c            |    4 +
>  cpu/ppc4xx/gpio.c           |    5 +
>  cpu/ppc4xx/interrupts.c     |  238
> ++++++++++++++++++++++++++++++++++++------- cpu/ppc4xx/miiphy.c         |  
>  5 +
>  cpu/ppc4xx/speed.c          |    6 +-
>  include/asm-ppc/processor.h |    3 +-
>  net/eth.c                   |    3 +-
>  9 files changed, 228 insertions(+), 42 deletions(-)
>
> diff --git a/cpu/ppc4xx/4xx_enet.c b/cpu/ppc4xx/4xx_enet.c
> index 4e863dc..cf26237 100644
> --- a/cpu/ppc4xx/4xx_enet.c
> +++ b/cpu/ppc4xx/4xx_enet.c
> @@ -97,7 +97,8 @@
>   * network support enabled.
>   * Remark: CONFIG_405 describes Xilinx PPC405 FPGA without EMAC
> controller! */
> -#if defined(CONFIG_CMD_NET) && !defined(CONFIG_405) &&
> !defined(CONFIG_IOP480) +#if defined(CONFIG_CMD_NET) &&
> !defined(CONFIG_405) && !defined(CONFIG_IOP480) \ +	&&
> !defined(CONFIG_440_VIRTEX5)
>
>  #if !(defined(CONFIG_MII) || defined(CONFIG_CMD_MII))
>  #error "CONFIG_MII has to be defined!"
> diff --git a/cpu/ppc4xx/4xx_uart.c b/cpu/ppc4xx/4xx_uart.c
> index a7587d4..37d3dbc 100644
> --- a/cpu/ppc4xx/4xx_uart.c
> +++ b/cpu/ppc4xx/4xx_uart.c
> @@ -48,6 +48,7 @@
>  #include <watchdog.h>
>  #include <asm/ppc4xx-intvec.h>
>
> +#if !defined(CONFIG_440_VIRTEX5)

You add this "#if !defined(CONFIG_440_VIRTEX5)" to many of the cpu/ppc4xx 
files with this patch. I don't like this. We should let the Makefile handle 
this. Perhaps something like this:

ifndef $(CONFIG_440_VIRTEX5)
COBJS   += 4xx_enet.o
...
endif

>  #ifdef CONFIG_SERIAL_MULTI
>  #include <serial.h>
>  #endif
> @@ -873,3 +874,5 @@ int serial_tstc(void)
>  #endif /* CONFIG_SERIAL_MULTI */
>
>  #endif	/* CONFIG_405GP || CONFIG_405CR */
> +
> +#endif
> diff --git a/cpu/ppc4xx/cpu.c b/cpu/ppc4xx/cpu.c
> index 39f439d..f510cdd 100644
> --- a/cpu/ppc4xx/cpu.c
> +++ b/cpu/ppc4xx/cpu.c
> @@ -508,6 +508,10 @@ int checkcpu (void)
>  		puts("GT Rev. A");
>  		strcpy(addstr, "Security/Kasumi support");
>  		break;
> +
> +	case PVR_VIRTEX5:
> +		printf(" VIRTEX5");
> +		break;
>
>  	default:
>  		printf (" UNKNOWN (PVR=%08x)", pvr);
> diff --git a/cpu/ppc4xx/gpio.c b/cpu/ppc4xx/gpio.c
> index df99f53..59159ee 100644
> --- a/cpu/ppc4xx/gpio.c
> +++ b/cpu/ppc4xx/gpio.c
> @@ -26,6 +26,9 @@
>  #include <asm/io.h>
>  #include <asm/gpio.h>
>
> +
> +#if !defined(CONFIG_440_VIRTEX5)
> +

Again, move this to the Makefile instead.

>  #if defined(CFG_4xx_GPIO_TABLE)
>  gpio_param_s const gpio_tab[GPIO_GROUP_MAX][GPIO_MAX] =
> CFG_4xx_GPIO_TABLE; #endif
> @@ -253,3 +256,5 @@ void gpio_set_chip_configuration(void)
>  	}
>  }
>  #endif /* CFG_4xx_GPIO_TABLE */
> +
> +#endif
> diff --git a/cpu/ppc4xx/interrupts.c b/cpu/ppc4xx/interrupts.c
> index 8620e2b..4648f52 100644
> --- a/cpu/ppc4xx/interrupts.c
> +++ b/cpu/ppc4xx/interrupts.c
> @@ -8,6 +8,10 @@
>   * (C) Copyright 2003 (440GX port)
>   * Travis B. Sawyer, Sandburst Corporation, tsawyer at sandburst.com
>   *
> + * (C) Copyright 2008 (PPC440X05 port for Virtex 5 FX)
> + * Ricardo Ribalda, Universidad Autonoma de Madrid, ricardo.ribalda at uam.es
> + * Work supported by Qtechnology (htpp://qtec.com)
> + *
>   * See file CREDITS for list of people who contributed to this
>   * project.
>   *
> @@ -41,6 +45,7 @@ DECLARE_GLOBAL_DATA_PTR;
>  /*
>   * Define the number of UIC's
>   */
> +#if !defined(CONFIG_440_VIRTEX5)
>  #if defined(CONFIG_440SPE) || \
>      defined(CONFIG_460EX) || defined(CONFIG_460GT)
>  #define UIC_MAX		4
> @@ -54,17 +59,23 @@ DECLARE_GLOBAL_DATA_PTR;
>  #else
>  #define UIC_MAX		1
>  #endif
> -
> +#else
> +void xilinx_pic_enable(void);
> +#endif
>  /*
>   * CPM interrupt vector functions.
>   */
> -struct	irq_action {
> +struct irq_action {

You seem to have run Lindent on this file too, correct? Please don't do this 
when you also add and/or fix something. This makes it hard to see the "real" 
changes. Only run Lindent on newly created files.

>  	interrupt_handler_t *handler;
>  	void *arg;
>  	int count;
>  };
>
> +#if !defined(CONFIG_440_VIRTEX5)
>  static struct irq_action irq_vecs[UIC_MAX * 32];
> +#else
> +static struct irq_action irq_vecs[XPAR_INTC_MAX_NUM_INTR_INPUTS];
> +#endif
>
>  u32 get_dcr(u16);
>  void set_dcr(u16, u32);
> @@ -81,27 +92,25 @@ static __inline__ void set_evpr(unsigned long val)
>  	asm volatile("mtspr 0x03f,%0" : : "r" (val));
>  }
>
> -#else /* !defined(CONFIG_440) */
> +#else				/* !defined(CONFIG_440) */
>
>  static __inline__ void set_pit(unsigned long val)
>  {
>  	asm volatile("mtpit %0" : : "r" (val));
>  }
>
> -
>  static __inline__ void set_tcr(unsigned long val)
>  {
>  	asm volatile("mttcr %0" : : "r" (val));
>  }
>
> -
>  static __inline__ void set_evpr(unsigned long val)
>  {
>  	asm volatile("mtevpr %0" : : "r" (val));
>  }
> -#endif /* defined(CONFIG_440 */
> +#endif				/* defined(CONFIG_440 */
>
> -int interrupt_init_cpu (unsigned *decrementer_count)
> +int interrupt_init_cpu(unsigned *decrementer_count)
>  {
>  	int vec;
>  	unsigned long val;
> @@ -112,7 +121,11 @@ int interrupt_init_cpu (unsigned *decrementer_count)
>  	/*
>  	 * Mark all irqs as free
>  	 */
> +#if !defined (CONFIG_440_VIRTEX5)
>  	for (vec = 0; vec < (UIC_MAX * 32); vec++) {
> +#else
> +	for (vec = 0; vec < XPAR_INTC_MAX_NUM_INTR_INPUTS; vec++) {
> +#endif
>  		irq_vecs[vec].handler = NULL;
>  		irq_vecs[vec].arg = NULL;
>  		irq_vecs[vec].count = 0;
> @@ -123,19 +136,19 @@ int interrupt_init_cpu (unsigned *decrementer_count)
>  	 * Init PIT
>  	 */
>  #if defined(CONFIG_440)
> -	val = mfspr( tcr );
> -	val &= (~0x04400000);		/* clear DIS & ARE */
> -	mtspr( tcr, val );
> -	mtspr( dec, 0 );		/* Prevent exception after TSR clear*/
> -	mtspr( decar, 0 );		/* clear reload */
> -	mtspr( tsr, 0x08000000 );	/* clear DEC status */
> -	val = gd->bd->bi_intfreq/1000;	/* 1 msec */
> -	mtspr( decar, val );		/* Set auto-reload value */
> -	mtspr( dec, val );		/* Set inital val */
> +	val = mfspr(tcr);
> +	val &= (~0x04400000);	/* clear DIS & ARE */
> +	mtspr(tcr, val);
> +	mtspr(dec, 0);		/* Prevent exception after TSR clear */
> +	mtspr(decar, 0);	/* clear reload */
> +	mtspr(tsr, 0x08000000);	/* clear DEC status */
> +	val = gd->bd->bi_intfreq / 1000;	/* 1 msec */
> +	mtspr(decar, val);	/* Set auto-reload value */
> +	mtspr(dec, val);	/* Set inital val */
>  #else
>  	set_pit(gd->bd->bi_intfreq / 1000);
>  #endif
> -#endif  /* CONFIG_4xx */
> +#endif				/* CONFIG_4xx */
>
>  #ifdef CONFIG_ADCIOP
>  	/*
> @@ -156,6 +169,8 @@ int interrupt_init_cpu (unsigned *decrementer_count)
>  	 */
>  	set_evpr(0x00000000);
>
> +#if !defined (CONFIG_440_VIRTEX5)
> +
>  #if !defined(CONFIG_440GX)
>  #if (UIC_MAX > 1)
>  	/* Install the UIC1 handlers */
> @@ -170,7 +185,7 @@ int interrupt_init_cpu (unsigned *decrementer_count)
>  	irq_install_handler(VECNUM_UIC3NC, uic_cascade_interrupt, 0);
>  	irq_install_handler(VECNUM_UIC3C, uic_cascade_interrupt, 0);
>  #endif
> -#else /* !defined(CONFIG_440GX) */
> +#else				/* !defined(CONFIG_440GX) */
>  	/* Take the GX out of compatibility mode
>  	 * Travis Sawyer, 9 Mar 2004
>  	 * NOTE: 440gx user manual inconsistency here
> @@ -179,18 +194,27 @@ int interrupt_init_cpu (unsigned *decrementer_count)
>  	 */
>  	mfsdr(sdr_mfr, val);
>  	val &= ~0x10000000;
> -	mtsdr(sdr_mfr,val);
> +	mtsdr(sdr_mfr, val);
>
>  	/* Enable UIC interrupts via UIC Base Enable Register */
>  	mtdcr(uicb0sr, UICB0_ALL);
>  	mtdcr(uicb0er, 0x54000000);
>  	/* None are critical */
>  	mtdcr(uicb0cr, 0);
> -#endif /* !defined(CONFIG_440GX) */
> +#endif				/* !defined(CONFIG_440GX) */
> +
> +#else
> +	/*
> +	 * Enable xilinx pic
> +	 */
> +	xilinx_pic_enable();
> +
> +#endif
>
>  	return (0);
>  }
>
> +#if !defined(CONFIG_440_VIRTEX5)
>  /* Handler for UIC interrupt */
>  static void uic_interrupt(u32 uic_base, int vec_base)
>  {
> @@ -214,7 +238,7 @@ static void uic_interrupt(u32 uic_base, int vec_base)
>
>  			if (irq_vecs[vec].handler != NULL) {
>  				/* call isr */
> -				(*irq_vecs[vec].handler)(irq_vecs[vec].arg);
> +				(*irq_vecs[vec].handler) (irq_vecs[vec].arg);
>  			} else {
>  				set_dcr(uic_base + UIC_ER,
>  					get_dcr(uic_base + UIC_ER) &
> @@ -227,7 +251,8 @@ static void uic_interrupt(u32 uic_base, int vec_base)
>  			 * After servicing the interrupt, we have to remove the
>  			 * status indicator
>  			 */
> -			set_dcr(uic_base + UIC_SR, (0x80000000 >> (vec & 0x1f)));
> +			set_dcr(uic_base + UIC_SR,
> +				(0x80000000 >> (vec & 0x1f)));
>  		}
>
>  		/*
> @@ -254,10 +279,10 @@ static void uic_cascade_interrupt(void *para)
>  #define UIC_BMSR	uic0msr
>  #define UIC_BSR		uic0sr
>  #endif
> -#else /* CONFIG_440 */
> +#else				/* CONFIG_440 */
>  #define UIC_BMSR	uicmsr
>  #define UIC_BSR		uicsr
> -#endif /* CONFIG_440 */
> +#endif				/* CONFIG_440 */
>
>  /*
>   * Handle external interrupts
> @@ -294,9 +319,9 @@ void external_interrupt(struct pt_regs *regs)
>  	if ((UICB0_UIC0CI & uic_msr) || (UICB0_UIC0NCI & uic_msr))
>  		uic_interrupt(UIC0_DCR_BASE, 0);
>  #endif
> -#else /* CONFIG_440 */
> +#else				/* CONFIG_440 */
>  	uic_interrupt(UIC0_DCR_BASE, 0);
> -#endif /* CONFIG_440 */
> +#endif				/* CONFIG_440 */
>
>  	mtdcr(UIC_BSR, uic_msr);
>
> @@ -313,7 +338,8 @@ void irq_install_handler(int vec, interrupt_handler_t *
> handler, void *arg) /*
>  	 * Print warning when replacing with a different irq vector
>  	 */
> -	if ((irq_vecs[vec].handler != NULL) && (irq_vecs[vec].handler !=
> handler)) { +	if ((irq_vecs[vec].handler != NULL)
> +	    && (irq_vecs[vec].handler != handler)) {
>  		printf("Interrupt vector %d: handler 0x%x replacing 0x%x\n",
>  		       vec, (uint) handler, (uint) irq_vecs[vec].handler);
>  	}
> @@ -339,7 +365,7 @@ void irq_install_handler(int vec, interrupt_handler_t *
> handler, void *arg) debug("Install interrupt for vector %d ==> %p\n", vec,
> handler); }
>
> -void irq_free_handler (int vec)
> +void irq_free_handler(int vec)
>  {
>  	int i;
>
> @@ -365,28 +391,166 @@ void irq_free_handler (int vec)
>  	irq_vecs[vec].handler = NULL;
>  	irq_vecs[vec].arg = NULL;
>  }
> +#else
> +
> +#define intc    XPAR_INTC_0_BASEADDR
> +#define ISR (0*4)		/* Interrupt Status Register */
> +#define IPR (1*4)		/* Interrupt Pending Register */
> +#define IER (2*4)		/* Interrupt Enable Register */
> +#define IAR (3*4)		/* Interrupt Acknowledge Register */
> +#define SIE (4*4)		/* Set Interrupt Enable bits */
> +#define CIE (5*4)		/* Clear Interrupt Enable bits */
> +#define IVR (6*4)		/* Interrupt Vector Register */
> +#define MER (7*4)		/* Master Enable Register */

This seems to be a completely different interrupt handler than used on 
IBM/AMCC PPC4xx. Please don't add this code to this file but to a new file. 
Does this Xilinx interrupt controller have a name? I'll probably rename the 
current interrupt.c to uic.c soon.

> +#define intc_out_be32(addr, mask)     out32((addr), (mask))
> +#define intc_in_be32(addr)            in32((addr))

Please don't define new accessor macros here. Use the existing ones, this 
makes the code better readable.

And use out_be32()/in_be32() instead of out32()/in32().

> +void xilinx_pic_enable(void)
> +{
> +
> +	printf("Xilinx PIC at 0x%8x\n", intc);
> +
> +	/*
> +	 * Disable all external interrupts until they are
> +	 * explicitly requested.
> +	 */
> +	intc_out_be32(intc + IER, 0);
> +
> +	/* Acknowledge any pending interrupts just in case. */
> +	intc_out_be32(intc + IAR, ~(u32) 0);
> +
> +	/* Turn on the Master Enable. */
> +	intc_out_be32(intc + MER, 0x3UL);
> +
> +	return;
> +
> +}
> +
> +int xilinx_pic_irq_get(void)
> +{
> +	u32 irq;
> +	irq = intc_in_be32(intc + IVR);
> +
> +	/* If no interrupt is pending then all bits of the IVR are set to 1. As
> +	 * the IVR is as many bits wide as numbers of inputs are available.
> +	 * Therefore, if all bits of the IVR are set to one, its content will
> +	 * be bigger than XPAR_INTC_MAX_NUM_INTR_INPUTS.
> +	 */
> +	if (irq >= XPAR_INTC_MAX_NUM_INTR_INPUTS)
> +		irq = -1;	/* report no pending interrupt. */
> +
> +	debug("get_irq: %d\n", irq);
> +	return (irq);
> +}
> +
> +static void xilinx_pic_irq_enable(unsigned int irq)
> +{
> +	unsigned long mask = (0x00000001 << (irq & 31));
> +	debug("enable: %d\n", irq);
> +	intc_out_be32(intc + SIE, mask);
> +}
> +
> +static void xilinx_pic_irq_disable(unsigned int irq)
> +{
> +	unsigned long mask = (0x00000001 << (irq & 31));
> +	debug("disable: %d\n", irq);
> +	intc_out_be32(intc + CIE, mask);
> +}
> +
> +static void xilinx_pic_irq_ack(unsigned int irq)
> +{
> +	unsigned long mask = (0x00000001 << (irq & 31));
> +	debug("ack: %d\n", irq);
> +	intc_out_be32(intc + IAR, mask);
> +}
> +
> +static void xilinx_pic_interrupt(void)
> +{
> +	int irq;
> +
> +	irq = xilinx_pic_irq_get();
> +	if (irq < 0)
> +		return;
> +
> +	irq_vecs[irq].count++;
> +
> +	if (irq_vecs[irq].handler != NULL) {
> +		/* call isr */
> +		(*irq_vecs[irq].handler) (irq_vecs[irq].arg);
> +
> +	} else {
> +		xilinx_pic_irq_disable(irq);
> +		printf("Masking bogus interrupt %d\n", irq);
> +	}
> +
> +	xilinx_pic_irq_ack(irq);
> +	return;
> +}
> +
> +void external_interrupt(struct pt_regs *regs)
> +{
> +	xilinx_pic_interrupt();
> +}
> +
> +/*
> + * Install and free a interrupt handler.
> + */
> +void irq_install_handler(int vec, interrupt_handler_t * handler, void
> *arg) +{
> +	/*
> +	 * Print warning when replacing with a different irq vector
> +	 */
> +	if ((irq_vecs[vec].handler != NULL)
> +	    && (irq_vecs[vec].handler != handler)) {
> +		printf("Interrupt vector %d: handler 0x%x replacing 0x%x\n",
> +		       vec, (uint) handler, (uint) irq_vecs[vec].handler);
> +	}
> +	irq_vecs[vec].handler = handler;
> +	irq_vecs[vec].arg = arg;
> +
> +	xilinx_pic_irq_enable(vec);
> +
> +	debug("Install interrupt for vector %d ==> %p\n", vec, handler);
> +}
> +
> +void irq_free_handler(int vec)
> +{
> +	debug("Free interrupt for vector %d ==> %p\n",
> +	      vec, irq_vecs[vec].handler);
> +
> +	xilinx_pic_irq_disable(vec);
> +
> +	irq_vecs[vec].handler = NULL;
> +	irq_vecs[vec].arg = NULL;
> +}
> +
> +#endif
>
> -void timer_interrupt_cpu (struct pt_regs *regs)
> +void timer_interrupt_cpu(struct pt_regs *regs)
>  {
>  	/* nothing to do here */
>  	return;
>  }
>
>  #if defined(CONFIG_CMD_IRQ)
> -int do_irqinfo(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
> +int do_irqinfo(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
>  {
>  	int vec;
>
> -	printf ("Interrupt-Information:\n");
> -	printf ("Nr  Routine   Arg       Count\n");
> +	printf("Interrupt-Information:\n");
> +	printf("Nr  Routine   Arg       Count\n");
>
> +#if !defined (CONFIG_440_VIRTEX5)
>  	for (vec = 0; vec < (UIC_MAX * 32); vec++) {
> +#else
> +	for (vec = 0; vec < XPAR_INTC_MAX_NUM_INTR_INPUTS; vec++) {
> +#endif
>  		if (irq_vecs[vec].handler != NULL) {
> -			printf ("%02d  %08lx  %08lx  %d\n",
> -				vec,
> -				(ulong)irq_vecs[vec].handler,
> -				(ulong)irq_vecs[vec].arg,
> -				irq_vecs[vec].count);
> +			printf("%02d  %08lx  %08lx  %d\n",
> +			       vec,
> +			       (ulong) irq_vecs[vec].handler,
> +			       (ulong) irq_vecs[vec].arg, irq_vecs[vec].count);
>  		}
>  	}
>
> diff --git a/cpu/ppc4xx/miiphy.c b/cpu/ppc4xx/miiphy.c
> index c882720..172fbcd 100644
> --- a/cpu/ppc4xx/miiphy.c
> +++ b/cpu/ppc4xx/miiphy.c
> @@ -43,6 +43,9 @@
>  #include <405_mal.h>
>  #include <miiphy.h>
>
> +
> +#if !defined(CONFIG_440_VIRTEX5)
> +

-> Makefile.

>  #if !defined(CONFIG_PHY_CLK_FREQ)
>  #define CONFIG_PHY_CLK_FREQ	0
>  #endif
> @@ -331,3 +334,5 @@ int emac4xx_miiphy_write (char *devname, unsigned char
> addr, unsigned char reg, {
>  	return emac_miiphy_command(addr, reg, EMAC_STACR_WRITE, value);
>  }
> +
> +#endif
> diff --git a/cpu/ppc4xx/speed.c b/cpu/ppc4xx/speed.c
> index 34bd721..d1681e4 100644
> --- a/cpu/ppc4xx/speed.c
> +++ b/cpu/ppc4xx/speed.c
> @@ -415,7 +415,8 @@ ulong get_PCI_freq (void)
>  	return sys_info.freqPCI;
>  }
>
> -#elif !defined(CONFIG_440GX) && !defined(CONFIG_440SP) &&
> !defined(CONFIG_440SPE) +#elif !defined(CONFIG_440GX) &&
> !defined(CONFIG_440SP) && !defined(CONFIG_440SPE)\
> +	&&!defined(CONFIG_440_VIRTEX5)
>  void get_sys_info (sys_info_t * sysInfo)
>  {
>  	unsigned long strp0;
> @@ -448,6 +449,8 @@ void get_sys_info (sys_info_t * sysInfo)
>  	sysInfo->freqUART = sysInfo->freqPLB;
>  }
>  #else
> +
> +#if !defined(CONFIG_440_VIRTEX5)
>  void get_sys_info (sys_info_t * sysInfo)
>  {
>  	unsigned long strp0;
> @@ -534,6 +537,7 @@ void get_sys_info (sys_info_t * sysInfo)
>  }
>
>  #endif
> +#endif
>
>  #if defined(CONFIG_YUCCA)
>  unsigned long determine_sysper(void)
> diff --git a/include/asm-ppc/processor.h b/include/asm-ppc/processor.h
> index 10fd478..88f193a 100644
> --- a/include/asm-ppc/processor.h
> +++ b/include/asm-ppc/processor.h
> @@ -827,13 +827,12 @@
>  #define PVR_7400	0x000C0000
>  #define PVR_7410	0x800C0000
>  #define PVR_7450	0x80000000
> -
>  #define PVR_85xx	0x80200000
>  #define PVR_85xx_REV1	(PVR_85xx | 0x0010)
>  #define PVR_85xx_REV2	(PVR_85xx | 0x0020)
> -

Please don't remove those empty lines here.

>  #define PVR_86xx	0x80040000
>  #define PVR_86xx_REV1	(PVR_86xx | 0x0010)
> +#define PVR_VIRTEX5     0x7ff21912
>
>  /*
>   * For the 8xx processors, all of them report the same PVR family for
> diff --git a/net/eth.c b/net/eth.c
> index 7fc9aee..54b59b8 100644
> --- a/net/eth.c
> +++ b/net/eth.c
> @@ -621,7 +621,8 @@ int eth_initialize(bd_t *bis)
>  	at91rm9200_miiphy_initialize(bis);
>  #endif
>  #if defined(CONFIG_4xx) && !defined(CONFIG_IOP480) \
> -	&& !defined(CONFIG_AP1000) && !defined(CONFIG_405)
> +	&& !defined(CONFIG_AP1000) && !defined(CONFIG_405) \
> +	&& !defined(CONFIG_440_VIRTEX5)
>  	emac4xx_miiphy_initialize(bis);
>  #endif
>  #if defined(CONFIG_MCF52x2)

Please send this eth.c patch as a separate patch. It need to go through the 
networking custodian.

Please fix and resubmit. Thanks.

Best regards,
Stefan

=====================================================================
DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: +49-8142-66989-0 Fax: +49-8142-66989-80  Email: office at denx.de
=====================================================================

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 12:09 ` Michal Simek
@ 2008-07-11 12:30   ` Stefan Roese
  2008-07-11 12:35     ` Ricardo Ribalda Delgado
  2008-07-11 13:52     ` Michal Simek
  2008-07-11 12:33   ` Ricardo Ribalda Delgado
  1 sibling, 2 replies; 22+ messages in thread
From: Stefan Roese @ 2008-07-11 12:30 UTC (permalink / raw)
  To: u-boot

On Friday 11 July 2008, Michal Simek wrote:
> Some days ago a sent to mailing list patch (currently is in) where I rename
> CONFIG_XILINX_ML300 -> CONFIG_XILINX_405.
>
> I would like to see if you can use the same style for 440 ->
> CONFIG_XILINX_440. I have no detail information about ppc440 but IMHO only
> virtex5 fx (or whatever) support it -> make no sense to me use virtex5 in
> name.
>
> SR: Do you agree with me?

Yes, renaming this to CONFIG_XILINX_440 is a good idea.

> There is big part of code relate with interrupt controller which is the
> same with microblaze. This should be handled in the same way. Any
> suggestion? (Do generic driver?)

Yes, I already mentioned in my review, that this code should go into a 
separate file. If the microblaze implementation is the same or very similar 
then please use the same code here and move to to a common directory. 
Perhaps:

drivers/interrupt/xilinx.c ?

Comments?

> M
>
> BTW: some comments in code.

Michal, your comments are very hard to spot since you don't quote the original 
code by "> ".

Best regards,
Stefan

=====================================================================
DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: +49-8142-66989-0 Fax: +49-8142-66989-80  Email: office at denx.de
=====================================================================

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 12:09 ` Michal Simek
  2008-07-11 12:30   ` Stefan Roese
@ 2008-07-11 12:33   ` Ricardo Ribalda Delgado
  1 sibling, 0 replies; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-11 12:33 UTC (permalink / raw)
  To: u-boot

Hello Stefan


  If everyone agrees I can change the naming, no big problem there.

> I would like to see if you can use the same style for 440 -> CONFIG_XILINX_440.
> I have no detail information about ppc440 but IMHO only virtex5 fx (or whatever) support it ->
> make no sense to me use virtex5 in name.
>
> SR: Do you agree with me?




>
> There is big part of code relate with interrupt controller which is the same with microblaze.
> This should be handled in the same way. Any suggestion? (Do generic driver?)

I will suggest the creation of a new directory /drivers/interrupt/

 And  locate there the pic drivers

>
> :-( no use this loooooooooooooong value which comes from generated xparameters.h.
> SR:Am I understand correctly that 405 or 440 use 32 bits (64...) wide interrupt controllers?

I prefer using the xparameters.h values. IMO this helps the creation
of the u-boot for a board



Best regards and thanks for the comments


-- 
Ricardo Ribalda
http://www.eps.uam.es/~rribalda/

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 12:30   ` Stefan Roese
@ 2008-07-11 12:35     ` Ricardo Ribalda Delgado
  2008-07-11 13:52     ` Michal Simek
  1 sibling, 0 replies; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-11 12:35 UTC (permalink / raw)
  To: u-boot

Hello Stefan

> Yes, renaming this to CONFIG_XILINX_440 is a good idea.

I will rename it and resend

> Yes, I already mentioned in my review, that this code should go into a
> separate file. If the microblaze implementation is the same or very similar
> then please use the same code here and move to to a common directory.
> Perhaps:
>
> drivers/interrupt/xilinx.c ?
>
> Comments?
Completely with you. I can create a generic driver if you would like.



   Best Regards


-- 
Ricardo Ribalda
http://www.eps.uam.es/~rribalda/

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 12:22 ` Stefan Roese
@ 2008-07-11 12:36   ` Ricardo Ribalda Delgado
  2008-07-14  0:45   ` Ricardo Ribalda Delgado
  1 sibling, 0 replies; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-11 12:36 UTC (permalink / raw)
  To: u-boot

Hello Stefan


  I will regenerate the patches and send then again. I will be out 'till Monay.



            Best Regards and thanks for your comments

On Fri, Jul 11, 2008 at 2:22 PM, Stefan Roese <sr@denx.de> wrote:
> Ricardo,
>
> On Friday 11 July 2008, Ricardo Ribalda Delgado wrote:
>> This patchs gives support for the embbedded ppc440
>> on the Virtex5 FPGAs
>
> Thanks.
>
> Some general comments:
>
> Please rebase your 4xx related patches on the "next" branch of my
> u-boot-ppc4xx repository. I just pushed some bigger rework/cleanup patchsets
> that are destined for the next merge window.
>
> And please add "ppc4xx: " to the beginning of the patch subject and add me to
> CC on 4xx related patches.
>
> More comments below...
>
>> ---
>>  cpu/ppc4xx/4xx_enet.c       |    3 +-
>>  cpu/ppc4xx/4xx_uart.c       |    3 +
>>  cpu/ppc4xx/cpu.c            |    4 +
>>  cpu/ppc4xx/gpio.c           |    5 +
>>  cpu/ppc4xx/interrupts.c     |  238
>> ++++++++++++++++++++++++++++++++++++------- cpu/ppc4xx/miiphy.c         |
>>  5 +
>>  cpu/ppc4xx/speed.c          |    6 +-
>>  include/asm-ppc/processor.h |    3 +-
>>  net/eth.c                   |    3 +-
>>  9 files changed, 228 insertions(+), 42 deletions(-)
>>
>> diff --git a/cpu/ppc4xx/4xx_enet.c b/cpu/ppc4xx/4xx_enet.c
>> index 4e863dc..cf26237 100644
>> --- a/cpu/ppc4xx/4xx_enet.c
>> +++ b/cpu/ppc4xx/4xx_enet.c
>> @@ -97,7 +97,8 @@
>>   * network support enabled.
>>   * Remark: CONFIG_405 describes Xilinx PPC405 FPGA without EMAC
>> controller! */
>> -#if defined(CONFIG_CMD_NET) && !defined(CONFIG_405) &&
>> !defined(CONFIG_IOP480) +#if defined(CONFIG_CMD_NET) &&
>> !defined(CONFIG_405) && !defined(CONFIG_IOP480) \ +   &&
>> !defined(CONFIG_440_VIRTEX5)
>>
>>  #if !(defined(CONFIG_MII) || defined(CONFIG_CMD_MII))
>>  #error "CONFIG_MII has to be defined!"
>> diff --git a/cpu/ppc4xx/4xx_uart.c b/cpu/ppc4xx/4xx_uart.c
>> index a7587d4..37d3dbc 100644
>> --- a/cpu/ppc4xx/4xx_uart.c
>> +++ b/cpu/ppc4xx/4xx_uart.c
>> @@ -48,6 +48,7 @@
>>  #include <watchdog.h>
>>  #include <asm/ppc4xx-intvec.h>
>>
>> +#if !defined(CONFIG_440_VIRTEX5)
>
> You add this "#if !defined(CONFIG_440_VIRTEX5)" to many of the cpu/ppc4xx
> files with this patch. I don't like this. We should let the Makefile handle
> this. Perhaps something like this:
>
> ifndef $(CONFIG_440_VIRTEX5)
> COBJS   += 4xx_enet.o
> ..
> endif
>
>>  #ifdef CONFIG_SERIAL_MULTI
>>  #include <serial.h>
>>  #endif
>> @@ -873,3 +874,5 @@ int serial_tstc(void)
>>  #endif /* CONFIG_SERIAL_MULTI */
>>
>>  #endif       /* CONFIG_405GP || CONFIG_405CR */
>> +
>> +#endif
>> diff --git a/cpu/ppc4xx/cpu.c b/cpu/ppc4xx/cpu.c
>> index 39f439d..f510cdd 100644
>> --- a/cpu/ppc4xx/cpu.c
>> +++ b/cpu/ppc4xx/cpu.c
>> @@ -508,6 +508,10 @@ int checkcpu (void)
>>               puts("GT Rev. A");
>>               strcpy(addstr, "Security/Kasumi support");
>>               break;
>> +
>> +     case PVR_VIRTEX5:
>> +             printf(" VIRTEX5");
>> +             break;
>>
>>       default:
>>               printf (" UNKNOWN (PVR=%08x)", pvr);
>> diff --git a/cpu/ppc4xx/gpio.c b/cpu/ppc4xx/gpio.c
>> index df99f53..59159ee 100644
>> --- a/cpu/ppc4xx/gpio.c
>> +++ b/cpu/ppc4xx/gpio.c
>> @@ -26,6 +26,9 @@
>>  #include <asm/io.h>
>>  #include <asm/gpio.h>
>>
>> +
>> +#if !defined(CONFIG_440_VIRTEX5)
>> +
>
> Again, move this to the Makefile instead.
>
>>  #if defined(CFG_4xx_GPIO_TABLE)
>>  gpio_param_s const gpio_tab[GPIO_GROUP_MAX][GPIO_MAX] =
>> CFG_4xx_GPIO_TABLE; #endif
>> @@ -253,3 +256,5 @@ void gpio_set_chip_configuration(void)
>>       }
>>  }
>>  #endif /* CFG_4xx_GPIO_TABLE */
>> +
>> +#endif
>> diff --git a/cpu/ppc4xx/interrupts.c b/cpu/ppc4xx/interrupts.c
>> index 8620e2b..4648f52 100644
>> --- a/cpu/ppc4xx/interrupts.c
>> +++ b/cpu/ppc4xx/interrupts.c
>> @@ -8,6 +8,10 @@
>>   * (C) Copyright 2003 (440GX port)
>>   * Travis B. Sawyer, Sandburst Corporation, tsawyer at sandburst.com
>>   *
>> + * (C) Copyright 2008 (PPC440X05 port for Virtex 5 FX)
>> + * Ricardo Ribalda, Universidad Autonoma de Madrid, ricardo.ribalda at uam.es
>> + * Work supported by Qtechnology (htpp://qtec.com)
>> + *
>>   * See file CREDITS for list of people who contributed to this
>>   * project.
>>   *
>> @@ -41,6 +45,7 @@ DECLARE_GLOBAL_DATA_PTR;
>>  /*
>>   * Define the number of UIC's
>>   */
>> +#if !defined(CONFIG_440_VIRTEX5)
>>  #if defined(CONFIG_440SPE) || \
>>      defined(CONFIG_460EX) || defined(CONFIG_460GT)
>>  #define UIC_MAX              4
>> @@ -54,17 +59,23 @@ DECLARE_GLOBAL_DATA_PTR;
>>  #else
>>  #define UIC_MAX              1
>>  #endif
>> -
>> +#else
>> +void xilinx_pic_enable(void);
>> +#endif
>>  /*
>>   * CPM interrupt vector functions.
>>   */
>> -struct       irq_action {
>> +struct irq_action {
>
> You seem to have run Lindent on this file too, correct? Please don't do this
> when you also add and/or fix something. This makes it hard to see the "real"
> changes. Only run Lindent on newly created files.
>
>>       interrupt_handler_t *handler;
>>       void *arg;
>>       int count;
>>  };
>>
>> +#if !defined(CONFIG_440_VIRTEX5)
>>  static struct irq_action irq_vecs[UIC_MAX * 32];
>> +#else
>> +static struct irq_action irq_vecs[XPAR_INTC_MAX_NUM_INTR_INPUTS];
>> +#endif
>>
>>  u32 get_dcr(u16);
>>  void set_dcr(u16, u32);
>> @@ -81,27 +92,25 @@ static __inline__ void set_evpr(unsigned long val)
>>       asm volatile("mtspr 0x03f,%0" : : "r" (val));
>>  }
>>
>> -#else /* !defined(CONFIG_440) */
>> +#else                                /* !defined(CONFIG_440) */
>>
>>  static __inline__ void set_pit(unsigned long val)
>>  {
>>       asm volatile("mtpit %0" : : "r" (val));
>>  }
>>
>> -
>>  static __inline__ void set_tcr(unsigned long val)
>>  {
>>       asm volatile("mttcr %0" : : "r" (val));
>>  }
>>
>> -
>>  static __inline__ void set_evpr(unsigned long val)
>>  {
>>       asm volatile("mtevpr %0" : : "r" (val));
>>  }
>> -#endif /* defined(CONFIG_440 */
>> +#endif                               /* defined(CONFIG_440 */
>>
>> -int interrupt_init_cpu (unsigned *decrementer_count)
>> +int interrupt_init_cpu(unsigned *decrementer_count)
>>  {
>>       int vec;
>>       unsigned long val;
>> @@ -112,7 +121,11 @@ int interrupt_init_cpu (unsigned *decrementer_count)
>>       /*
>>        * Mark all irqs as free
>>        */
>> +#if !defined (CONFIG_440_VIRTEX5)
>>       for (vec = 0; vec < (UIC_MAX * 32); vec++) {
>> +#else
>> +     for (vec = 0; vec < XPAR_INTC_MAX_NUM_INTR_INPUTS; vec++) {
>> +#endif
>>               irq_vecs[vec].handler = NULL;
>>               irq_vecs[vec].arg = NULL;
>>               irq_vecs[vec].count = 0;
>> @@ -123,19 +136,19 @@ int interrupt_init_cpu (unsigned *decrementer_count)
>>        * Init PIT
>>        */
>>  #if defined(CONFIG_440)
>> -     val = mfspr( tcr );
>> -     val &= (~0x04400000);           /* clear DIS & ARE */
>> -     mtspr( tcr, val );
>> -     mtspr( dec, 0 );                /* Prevent exception after TSR clear*/
>> -     mtspr( decar, 0 );              /* clear reload */
>> -     mtspr( tsr, 0x08000000 );       /* clear DEC status */
>> -     val = gd->bd->bi_intfreq/1000;  /* 1 msec */
>> -     mtspr( decar, val );            /* Set auto-reload value */
>> -     mtspr( dec, val );              /* Set inital val */
>> +     val = mfspr(tcr);
>> +     val &= (~0x04400000);   /* clear DIS & ARE */
>> +     mtspr(tcr, val);
>> +     mtspr(dec, 0);          /* Prevent exception after TSR clear */
>> +     mtspr(decar, 0);        /* clear reload */
>> +     mtspr(tsr, 0x08000000); /* clear DEC status */
>> +     val = gd->bd->bi_intfreq / 1000;        /* 1 msec */
>> +     mtspr(decar, val);      /* Set auto-reload value */
>> +     mtspr(dec, val);        /* Set inital val */
>>  #else
>>       set_pit(gd->bd->bi_intfreq / 1000);
>>  #endif
>> -#endif  /* CONFIG_4xx */
>> +#endif                               /* CONFIG_4xx */
>>
>>  #ifdef CONFIG_ADCIOP
>>       /*
>> @@ -156,6 +169,8 @@ int interrupt_init_cpu (unsigned *decrementer_count)
>>        */
>>       set_evpr(0x00000000);
>>
>> +#if !defined (CONFIG_440_VIRTEX5)
>> +
>>  #if !defined(CONFIG_440GX)
>>  #if (UIC_MAX > 1)
>>       /* Install the UIC1 handlers */
>> @@ -170,7 +185,7 @@ int interrupt_init_cpu (unsigned *decrementer_count)
>>       irq_install_handler(VECNUM_UIC3NC, uic_cascade_interrupt, 0);
>>       irq_install_handler(VECNUM_UIC3C, uic_cascade_interrupt, 0);
>>  #endif
>> -#else /* !defined(CONFIG_440GX) */
>> +#else                                /* !defined(CONFIG_440GX) */
>>       /* Take the GX out of compatibility mode
>>        * Travis Sawyer, 9 Mar 2004
>>        * NOTE: 440gx user manual inconsistency here
>> @@ -179,18 +194,27 @@ int interrupt_init_cpu (unsigned *decrementer_count)
>>        */
>>       mfsdr(sdr_mfr, val);
>>       val &= ~0x10000000;
>> -     mtsdr(sdr_mfr,val);
>> +     mtsdr(sdr_mfr, val);
>>
>>       /* Enable UIC interrupts via UIC Base Enable Register */
>>       mtdcr(uicb0sr, UICB0_ALL);
>>       mtdcr(uicb0er, 0x54000000);
>>       /* None are critical */
>>       mtdcr(uicb0cr, 0);
>> -#endif /* !defined(CONFIG_440GX) */
>> +#endif                               /* !defined(CONFIG_440GX) */
>> +
>> +#else
>> +     /*
>> +      * Enable xilinx pic
>> +      */
>> +     xilinx_pic_enable();
>> +
>> +#endif
>>
>>       return (0);
>>  }
>>
>> +#if !defined(CONFIG_440_VIRTEX5)
>>  /* Handler for UIC interrupt */
>>  static void uic_interrupt(u32 uic_base, int vec_base)
>>  {
>> @@ -214,7 +238,7 @@ static void uic_interrupt(u32 uic_base, int vec_base)
>>
>>                       if (irq_vecs[vec].handler != NULL) {
>>                               /* call isr */
>> -                             (*irq_vecs[vec].handler)(irq_vecs[vec].arg);
>> +                             (*irq_vecs[vec].handler) (irq_vecs[vec].arg);
>>                       } else {
>>                               set_dcr(uic_base + UIC_ER,
>>                                       get_dcr(uic_base + UIC_ER) &
>> @@ -227,7 +251,8 @@ static void uic_interrupt(u32 uic_base, int vec_base)
>>                        * After servicing the interrupt, we have to remove the
>>                        * status indicator
>>                        */
>> -                     set_dcr(uic_base + UIC_SR, (0x80000000 >> (vec & 0x1f)));
>> +                     set_dcr(uic_base + UIC_SR,
>> +                             (0x80000000 >> (vec & 0x1f)));
>>               }
>>
>>               /*
>> @@ -254,10 +279,10 @@ static void uic_cascade_interrupt(void *para)
>>  #define UIC_BMSR     uic0msr
>>  #define UIC_BSR              uic0sr
>>  #endif
>> -#else /* CONFIG_440 */
>> +#else                                /* CONFIG_440 */
>>  #define UIC_BMSR     uicmsr
>>  #define UIC_BSR              uicsr
>> -#endif /* CONFIG_440 */
>> +#endif                               /* CONFIG_440 */
>>
>>  /*
>>   * Handle external interrupts
>> @@ -294,9 +319,9 @@ void external_interrupt(struct pt_regs *regs)
>>       if ((UICB0_UIC0CI & uic_msr) || (UICB0_UIC0NCI & uic_msr))
>>               uic_interrupt(UIC0_DCR_BASE, 0);
>>  #endif
>> -#else /* CONFIG_440 */
>> +#else                                /* CONFIG_440 */
>>       uic_interrupt(UIC0_DCR_BASE, 0);
>> -#endif /* CONFIG_440 */
>> +#endif                               /* CONFIG_440 */
>>
>>       mtdcr(UIC_BSR, uic_msr);
>>
>> @@ -313,7 +338,8 @@ void irq_install_handler(int vec, interrupt_handler_t *
>> handler, void *arg) /*
>>        * Print warning when replacing with a different irq vector
>>        */
>> -     if ((irq_vecs[vec].handler != NULL) && (irq_vecs[vec].handler !=
>> handler)) { + if ((irq_vecs[vec].handler != NULL)
>> +         && (irq_vecs[vec].handler != handler)) {
>>               printf("Interrupt vector %d: handler 0x%x replacing 0x%x\n",
>>                      vec, (uint) handler, (uint) irq_vecs[vec].handler);
>>       }
>> @@ -339,7 +365,7 @@ void irq_install_handler(int vec, interrupt_handler_t *
>> handler, void *arg) debug("Install interrupt for vector %d ==> %p\n", vec,
>> handler); }
>>
>> -void irq_free_handler (int vec)
>> +void irq_free_handler(int vec)
>>  {
>>       int i;
>>
>> @@ -365,28 +391,166 @@ void irq_free_handler (int vec)
>>       irq_vecs[vec].handler = NULL;
>>       irq_vecs[vec].arg = NULL;
>>  }
>> +#else
>> +
>> +#define intc    XPAR_INTC_0_BASEADDR
>> +#define ISR (0*4)            /* Interrupt Status Register */
>> +#define IPR (1*4)            /* Interrupt Pending Register */
>> +#define IER (2*4)            /* Interrupt Enable Register */
>> +#define IAR (3*4)            /* Interrupt Acknowledge Register */
>> +#define SIE (4*4)            /* Set Interrupt Enable bits */
>> +#define CIE (5*4)            /* Clear Interrupt Enable bits */
>> +#define IVR (6*4)            /* Interrupt Vector Register */
>> +#define MER (7*4)            /* Master Enable Register */
>
> This seems to be a completely different interrupt handler than used on
> IBM/AMCC PPC4xx. Please don't add this code to this file but to a new file.
> Does this Xilinx interrupt controller have a name? I'll probably rename the
> current interrupt.c to uic.c soon.
>
>> +#define intc_out_be32(addr, mask)     out32((addr), (mask))
>> +#define intc_in_be32(addr)            in32((addr))
>
> Please don't define new accessor macros here. Use the existing ones, this
> makes the code better readable.
>
> And use out_be32()/in_be32() instead of out32()/in32().
>
>> +void xilinx_pic_enable(void)
>> +{
>> +
>> +     printf("Xilinx PIC at 0x%8x\n", intc);
>> +
>> +     /*
>> +      * Disable all external interrupts until they are
>> +      * explicitly requested.
>> +      */
>> +     intc_out_be32(intc + IER, 0);
>> +
>> +     /* Acknowledge any pending interrupts just in case. */
>> +     intc_out_be32(intc + IAR, ~(u32) 0);
>> +
>> +     /* Turn on the Master Enable. */
>> +     intc_out_be32(intc + MER, 0x3UL);
>> +
>> +     return;
>> +
>> +}
>> +
>> +int xilinx_pic_irq_get(void)
>> +{
>> +     u32 irq;
>> +     irq = intc_in_be32(intc + IVR);
>> +
>> +     /* If no interrupt is pending then all bits of the IVR are set to 1. As
>> +      * the IVR is as many bits wide as numbers of inputs are available.
>> +      * Therefore, if all bits of the IVR are set to one, its content will
>> +      * be bigger than XPAR_INTC_MAX_NUM_INTR_INPUTS.
>> +      */
>> +     if (irq >= XPAR_INTC_MAX_NUM_INTR_INPUTS)
>> +             irq = -1;       /* report no pending interrupt. */
>> +
>> +     debug("get_irq: %d\n", irq);
>> +     return (irq);
>> +}
>> +
>> +static void xilinx_pic_irq_enable(unsigned int irq)
>> +{
>> +     unsigned long mask = (0x00000001 << (irq & 31));
>> +     debug("enable: %d\n", irq);
>> +     intc_out_be32(intc + SIE, mask);
>> +}
>> +
>> +static void xilinx_pic_irq_disable(unsigned int irq)
>> +{
>> +     unsigned long mask = (0x00000001 << (irq & 31));
>> +     debug("disable: %d\n", irq);
>> +     intc_out_be32(intc + CIE, mask);
>> +}
>> +
>> +static void xilinx_pic_irq_ack(unsigned int irq)
>> +{
>> +     unsigned long mask = (0x00000001 << (irq & 31));
>> +     debug("ack: %d\n", irq);
>> +     intc_out_be32(intc + IAR, mask);
>> +}
>> +
>> +static void xilinx_pic_interrupt(void)
>> +{
>> +     int irq;
>> +
>> +     irq = xilinx_pic_irq_get();
>> +     if (irq < 0)
>> +             return;
>> +
>> +     irq_vecs[irq].count++;
>> +
>> +     if (irq_vecs[irq].handler != NULL) {
>> +             /* call isr */
>> +             (*irq_vecs[irq].handler) (irq_vecs[irq].arg);
>> +
>> +     } else {
>> +             xilinx_pic_irq_disable(irq);
>> +             printf("Masking bogus interrupt %d\n", irq);
>> +     }
>> +
>> +     xilinx_pic_irq_ack(irq);
>> +     return;
>> +}
>> +
>> +void external_interrupt(struct pt_regs *regs)
>> +{
>> +     xilinx_pic_interrupt();
>> +}
>> +
>> +/*
>> + * Install and free a interrupt handler.
>> + */
>> +void irq_install_handler(int vec, interrupt_handler_t * handler, void
>> *arg) +{
>> +     /*
>> +      * Print warning when replacing with a different irq vector
>> +      */
>> +     if ((irq_vecs[vec].handler != NULL)
>> +         && (irq_vecs[vec].handler != handler)) {
>> +             printf("Interrupt vector %d: handler 0x%x replacing 0x%x\n",
>> +                    vec, (uint) handler, (uint) irq_vecs[vec].handler);
>> +     }
>> +     irq_vecs[vec].handler = handler;
>> +     irq_vecs[vec].arg = arg;
>> +
>> +     xilinx_pic_irq_enable(vec);
>> +
>> +     debug("Install interrupt for vector %d ==> %p\n", vec, handler);
>> +}
>> +
>> +void irq_free_handler(int vec)
>> +{
>> +     debug("Free interrupt for vector %d ==> %p\n",
>> +           vec, irq_vecs[vec].handler);
>> +
>> +     xilinx_pic_irq_disable(vec);
>> +
>> +     irq_vecs[vec].handler = NULL;
>> +     irq_vecs[vec].arg = NULL;
>> +}
>> +
>> +#endif
>>
>> -void timer_interrupt_cpu (struct pt_regs *regs)
>> +void timer_interrupt_cpu(struct pt_regs *regs)
>>  {
>>       /* nothing to do here */
>>       return;
>>  }
>>
>>  #if defined(CONFIG_CMD_IRQ)
>> -int do_irqinfo(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
>> +int do_irqinfo(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
>>  {
>>       int vec;
>>
>> -     printf ("Interrupt-Information:\n");
>> -     printf ("Nr  Routine   Arg       Count\n");
>> +     printf("Interrupt-Information:\n");
>> +     printf("Nr  Routine   Arg       Count\n");
>>
>> +#if !defined (CONFIG_440_VIRTEX5)
>>       for (vec = 0; vec < (UIC_MAX * 32); vec++) {
>> +#else
>> +     for (vec = 0; vec < XPAR_INTC_MAX_NUM_INTR_INPUTS; vec++) {
>> +#endif
>>               if (irq_vecs[vec].handler != NULL) {
>> -                     printf ("%02d  %08lx  %08lx  %d\n",
>> -                             vec,
>> -                             (ulong)irq_vecs[vec].handler,
>> -                             (ulong)irq_vecs[vec].arg,
>> -                             irq_vecs[vec].count);
>> +                     printf("%02d  %08lx  %08lx  %d\n",
>> +                            vec,
>> +                            (ulong) irq_vecs[vec].handler,
>> +                            (ulong) irq_vecs[vec].arg, irq_vecs[vec].count);
>>               }
>>       }
>>
>> diff --git a/cpu/ppc4xx/miiphy.c b/cpu/ppc4xx/miiphy.c
>> index c882720..172fbcd 100644
>> --- a/cpu/ppc4xx/miiphy.c
>> +++ b/cpu/ppc4xx/miiphy.c
>> @@ -43,6 +43,9 @@
>>  #include <405_mal.h>
>>  #include <miiphy.h>
>>
>> +
>> +#if !defined(CONFIG_440_VIRTEX5)
>> +
>
> -> Makefile.
>
>>  #if !defined(CONFIG_PHY_CLK_FREQ)
>>  #define CONFIG_PHY_CLK_FREQ  0
>>  #endif
>> @@ -331,3 +334,5 @@ int emac4xx_miiphy_write (char *devname, unsigned char
>> addr, unsigned char reg, {
>>       return emac_miiphy_command(addr, reg, EMAC_STACR_WRITE, value);
>>  }
>> +
>> +#endif
>> diff --git a/cpu/ppc4xx/speed.c b/cpu/ppc4xx/speed.c
>> index 34bd721..d1681e4 100644
>> --- a/cpu/ppc4xx/speed.c
>> +++ b/cpu/ppc4xx/speed.c
>> @@ -415,7 +415,8 @@ ulong get_PCI_freq (void)
>>       return sys_info.freqPCI;
>>  }
>>
>> -#elif !defined(CONFIG_440GX) && !defined(CONFIG_440SP) &&
>> !defined(CONFIG_440SPE) +#elif !defined(CONFIG_440GX) &&
>> !defined(CONFIG_440SP) && !defined(CONFIG_440SPE)\
>> +     &&!defined(CONFIG_440_VIRTEX5)
>>  void get_sys_info (sys_info_t * sysInfo)
>>  {
>>       unsigned long strp0;
>> @@ -448,6 +449,8 @@ void get_sys_info (sys_info_t * sysInfo)
>>       sysInfo->freqUART = sysInfo->freqPLB;
>>  }
>>  #else
>> +
>> +#if !defined(CONFIG_440_VIRTEX5)
>>  void get_sys_info (sys_info_t * sysInfo)
>>  {
>>       unsigned long strp0;
>> @@ -534,6 +537,7 @@ void get_sys_info (sys_info_t * sysInfo)
>>  }
>>
>>  #endif
>> +#endif
>>
>>  #if defined(CONFIG_YUCCA)
>>  unsigned long determine_sysper(void)
>> diff --git a/include/asm-ppc/processor.h b/include/asm-ppc/processor.h
>> index 10fd478..88f193a 100644
>> --- a/include/asm-ppc/processor.h
>> +++ b/include/asm-ppc/processor.h
>> @@ -827,13 +827,12 @@
>>  #define PVR_7400     0x000C0000
>>  #define PVR_7410     0x800C0000
>>  #define PVR_7450     0x80000000
>> -
>>  #define PVR_85xx     0x80200000
>>  #define PVR_85xx_REV1        (PVR_85xx | 0x0010)
>>  #define PVR_85xx_REV2        (PVR_85xx | 0x0020)
>> -
>
> Please don't remove those empty lines here.
>
>>  #define PVR_86xx     0x80040000
>>  #define PVR_86xx_REV1        (PVR_86xx | 0x0010)
>> +#define PVR_VIRTEX5     0x7ff21912
>>
>>  /*
>>   * For the 8xx processors, all of them report the same PVR family for
>> diff --git a/net/eth.c b/net/eth.c
>> index 7fc9aee..54b59b8 100644
>> --- a/net/eth.c
>> +++ b/net/eth.c
>> @@ -621,7 +621,8 @@ int eth_initialize(bd_t *bis)
>>       at91rm9200_miiphy_initialize(bis);
>>  #endif
>>  #if defined(CONFIG_4xx) && !defined(CONFIG_IOP480) \
>> -     && !defined(CONFIG_AP1000) && !defined(CONFIG_405)
>> +     && !defined(CONFIG_AP1000) && !defined(CONFIG_405) \
>> +     && !defined(CONFIG_440_VIRTEX5)
>>       emac4xx_miiphy_initialize(bis);
>>  #endif
>>  #if defined(CONFIG_MCF52x2)
>
> Please send this eth.c patch as a separate patch. It need to go through the
> networking custodian.
>
> Please fix and resubmit. Thanks.
>
> Best regards,
> Stefan
>
> =====================================================================
> DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
> HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
> Phone: +49-8142-66989-0 Fax: +49-8142-66989-80  Email: office at denx.de
> =====================================================================
>



-- 
Ricardo Ribalda
http://www.eps.uam.es/~rribalda/

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 12:30   ` Stefan Roese
  2008-07-11 12:35     ` Ricardo Ribalda Delgado
@ 2008-07-11 13:52     ` Michal Simek
  2008-07-11 15:03       ` Wolfgang Denk
  2008-07-14 11:46       ` Ricardo Ribalda Delgado
  1 sibling, 2 replies; 22+ messages in thread
From: Michal Simek @ 2008-07-11 13:52 UTC (permalink / raw)
  To: u-boot

Hi Stefan,


>> Some days ago a sent to mailing list patch (currently is in) where I rename
>> CONFIG_XILINX_ML300 -> CONFIG_XILINX_405.
>>
>> I would like to see if you can use the same style for 440 ->
>> CONFIG_XILINX_440. I have no detail information about ppc440 but IMHO only
>> virtex5 fx (or whatever) support it -> make no sense to me use virtex5 in
>> name.
>>
>> SR: Do you agree with me?
> 
> Yes, renaming this to CONFIG_XILINX_440 is a good idea.

nice to hear.

>> There is big part of code relate with interrupt controller which is the
>> same with microblaze. This should be handled in the same way. Any
>> suggestion? (Do generic driver?)
> 
> Yes, I already mentioned in my review, that this code should go into a 
> separate file. If the microblaze implementation is the same or very similar 
> then please use the same code here and move to to a common directory. 
> Perhaps:
> 
> drivers/interrupt/xilinx.c ?
> 
> Comments?

1. use macros names which are in microblaze xparameters.h. These values are
generate by u-boot BSP. Add ppc440 to it solves your problem with generic boards.
2. I don't know if is good idea to create drivers for interrupt controllers.
If yes xilinx_intc.c, will be better.
I will wait for WD comments.

>>
>> BTW: some comments in code.
> 
> Michal, your comments are very hard to spot since you don't quote the original 
> code by "> ".

I used web based email which is ...

Michal

> Best regards,
> Stefan
> 
> =====================================================================
> DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
> HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
> Phone: +49-8142-66989-0 Fax: +49-8142-66989-80  Email: office at denx.de
> =====================================================================
> 

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 13:52     ` Michal Simek
@ 2008-07-11 15:03       ` Wolfgang Denk
  2008-07-11 15:10         ` Stefan Roese
  2008-07-14 11:46       ` Ricardo Ribalda Delgado
  1 sibling, 1 reply; 22+ messages in thread
From: Wolfgang Denk @ 2008-07-11 15:03 UTC (permalink / raw)
  To: u-boot

In message <48776598.8050403@seznam.cz> you wrote:
> 
> 2. I don't know if is good idea to create drivers for interrupt controllers.

I have to admit that such an idea surprises me a bit.

> If yes xilinx_intc.c, will be better.
> I will wait for WD comments.

In my opinion an interrupt controller is fundamentally different from
an device that is handled by a device driver. It therefore has no
place in the drivers/ directory.

Best regards,

Wolfgang Denk

-- 
DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: (+49)-8142-66989-10 Fax: (+49)-8142-66989-80 Email: wd at denx.de
Horses just naturally have mohawk haircuts.

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 15:03       ` Wolfgang Denk
@ 2008-07-11 15:10         ` Stefan Roese
  2008-07-11 19:35           ` Michal Simek
  0 siblings, 1 reply; 22+ messages in thread
From: Stefan Roese @ 2008-07-11 15:10 UTC (permalink / raw)
  To: u-boot

On Friday 11 July 2008, Wolfgang Denk wrote:
> In message <48776598.8050403@seznam.cz> you wrote:
> > 2. I don't know if is good idea to create drivers for interrupt
> > controllers.
>
> I have to admit that such an idea surprises me a bit.
>
> > If yes xilinx_intc.c, will be better.
> > I will wait for WD comments.
>
> In my opinion an interrupt controller is fundamentally different from
> an device that is handled by a device driver. It therefore has no
> place in the drivers/ directory.

Yes, I was hesitating here too. Only other idea that comes to my mind is:

cpu/xilinx/interrupt.c

Better?

Best regards,
Stefan

=====================================================================
DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: +49-8142-66989-0 Fax: +49-8142-66989-80  Email: office at denx.de
=====================================================================

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 15:10         ` Stefan Roese
@ 2008-07-11 19:35           ` Michal Simek
  0 siblings, 0 replies; 22+ messages in thread
From: Michal Simek @ 2008-07-11 19:35 UTC (permalink / raw)
  To: u-boot

>> In message <48776598.8050403@seznam.cz> you wrote:
>>> 2. I don't know if is good idea to create drivers for interrupt
>>> controllers.
>> I have to admit that such an idea surprises me a bit.
>>
>>> If yes xilinx_intc.c, will be better.
>>> I will wait for WD comments.
>> In my opinion an interrupt controller is fundamentally different from
>> an device that is handled by a device driver. It therefore has no
>> place in the drivers/ directory.
> 
> Yes, I was hesitating here too. Only other idea that comes to my mind is:
> 
> cpu/xilinx/interrupt.c
>
> Better?
>
xilinx is not type of cpu. :-( I'll think about smarter way.

Best regards,
Michal


> Best regards,
> Stefan
> 
> =====================================================================
> DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
> HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
> Phone: +49-8142-66989-0 Fax: +49-8142-66989-80  Email: office at denx.de
> =====================================================================
> 
> No virus found in this incoming message.
> Checked by AVG - http://www.avg.com 
> Version: 8.0.138 / Virus Database: 270.4.7/1545 - Release Date: 10.7.2008 06:43
> 
> 
> 

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 12:22 ` Stefan Roese
  2008-07-11 12:36   ` Ricardo Ribalda Delgado
@ 2008-07-14  0:45   ` Ricardo Ribalda Delgado
  2008-07-14  8:11     ` Stefan Roese
  1 sibling, 1 reply; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-14  0:45 UTC (permalink / raw)
  To: u-boot

Hello Stefan

  I'm back from short hollydays, so expect some patches in this week
:). Some general questions:


master or next:
Shall I apply the patches to master or to next? Both have
modifications from 2 days ago.


interrupts:
I have been thinking about the irq handler and I am going to create this files:

   -interrupt.c (actual file) -> common part
   -uic.c (new file) -> uic part (extracted from interrupt.c)
   -xilinx_iic.c (new file) -> Xilinx Irq handler

The Makefile will select among uic.c or xilinx_iic.c

ml507:
As you know I have been sending patches for the ml507 board. I will
wait until this patch in accepted until I resend the ml507 patch. Is
this ok?




  Thanks
-- 
Ricardo Ribalda
http://www.eps.uam.es/~rribalda/

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-14  0:45   ` Ricardo Ribalda Delgado
@ 2008-07-14  8:11     ` Stefan Roese
  2008-07-14 10:12       ` Ricardo Ribalda Delgado
  0 siblings, 1 reply; 22+ messages in thread
From: Stefan Roese @ 2008-07-14  8:11 UTC (permalink / raw)
  To: u-boot

Hi Racardo,

On Monday 14 July 2008, Ricardo Ribalda Delgado wrote:
>   I'm back from short hollydays, so expect some patches in this week
> :). Some general questions:
>
> master or next:
> Shall I apply the patches to master or to next? Both have
> modifications from 2 days ago.

"next" please. "master" is only for bug fixes now, since the merge window is 
closed.

> interrupts:
> I have been thinking about the irq handler and I am going to create this
> files:
>
>    -interrupt.c (actual file) -> common part
>    -uic.c (new file) -> uic part (extracted from interrupt.c)
>    -xilinx_iic.c (new file) -> Xilinx Irq handler

xilinx_iic.c ??? This really sounds like I2C. Please choose a different name.

> The Makefile will select among uic.c or xilinx_iic.c

Yes, this is possible. But IIRC then the microblaze CPU suport has the same or 
at least a similar interrupt handler. Isn't there a way to use some interrupt 
code on both CPU architectures?

> ml507:
> As you know I have been sending patches for the ml507 board. I will
> wait until this patch in accepted until I resend the ml507 patch. Is
> this ok?

To clarify: You will wait to send the ml507 board support patches until the 
CPU & interrupt stuff is accepted?

Best regards,
Stefan

=====================================================================
DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: +49-8142-66989-0 Fax: +49-8142-66989-80  Email: office at denx.de
=====================================================================

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-14  8:11     ` Stefan Roese
@ 2008-07-14 10:12       ` Ricardo Ribalda Delgado
  2008-07-14 12:06         ` Wolfgang Denk
  0 siblings, 1 reply; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-14 10:12 UTC (permalink / raw)
  To: u-boot

Hello again



> "next" please. "master" is only for bug fixes now, since the merge window is
> closed.

 ACK


> xilinx_iic.c ??? This really sounds like I2C. Please choose a different name.
What about xilinx_irq?


>
>> The Makefile will select among uic.c or xilinx_iic.c
>
> Yes, this is possible. But IIRC then the microblaze CPU suport has the same or
> at least a similar interrupt handler. Isn't there a way to use some interrupt
> code on both CPU architectures?

You are right, but I cannot see how to share code between
architechtures... If WD don't have a good idea we should have here the
xilinx iic code repeated.

>
>> ml507:
>> As you know I have been sending patches for the ml507 board. I will
>> wait until this patch in accepted until I resend the ml507 patch. Is
>> this ok?
>
> To clarify: You will wait to send the ml507 board support patches until the
> CPU & interrupt stuff is accepted?

  Yes, because the ml507 code depends directly on the CPU and the IRQ stuff.


  Best Regards

-- 
Ricardo Ribalda
http://www.eps.uam.es/~rribalda/

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-11 13:52     ` Michal Simek
  2008-07-11 15:03       ` Wolfgang Denk
@ 2008-07-14 11:46       ` Ricardo Ribalda Delgado
  2008-07-14 12:06         ` Michal Simek
  1 sibling, 1 reply; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-14 11:46 UTC (permalink / raw)
  To: u-boot

Hi Michal

  I am trying to solve the xilinx irq.... I have some questions:

  1) Where can I find the official u-boot bsp for edk?
http://git.monstr.eu/ is dead
  2) Do we really need a new bsp for this? Can't we just use the
Linux_2_6. I just need a couple of definitions...


   Best Regards



-- 
Ricardo Ribalda
http://www.eps.uam.es/~rribalda/

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-14 10:12       ` Ricardo Ribalda Delgado
@ 2008-07-14 12:06         ` Wolfgang Denk
  2008-07-14 12:11           ` Michal Simek
  0 siblings, 1 reply; 22+ messages in thread
From: Wolfgang Denk @ 2008-07-14 12:06 UTC (permalink / raw)
  To: u-boot

In message <aa76a2be0807140312p233f1b35lf9e4dc736ff6e620@mail.gmail.com> you wrote:
> 
> You are right, but I cannot see how to share code between
> architechtures... If WD don't have a good idea we should have here the
> xilinx iic code repeated.

No. Duplicating code is never a good idea.


Best regards,

Wolfgang Denk

-- 
DENX Software Engineering GmbH,     MD: Wolfgang Denk & Detlev Zundel
HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany
Phone: (+49)-8142-66989-10 Fax: (+49)-8142-66989-80 Email: wd at denx.de
The trouble with our times is that the future is not what it used  to
be.                                                     - Paul Valery

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-14 11:46       ` Ricardo Ribalda Delgado
@ 2008-07-14 12:06         ` Michal Simek
  0 siblings, 0 replies; 22+ messages in thread
From: Michal Simek @ 2008-07-14 12:06 UTC (permalink / raw)
  To: u-boot

Hi Ricardo,

> Hi Michal
> 
>   I am trying to solve the xilinx irq.... I have some questions:
> 
>   1) Where can I find the official u-boot bsp for edk?
> http://git.monstr.eu/ is dead

yes. git.monstr.eu was temporary down because I was changing my servers. currently is server up.

>   2) Do we really need a new bsp for this? Can't we just use the
> Linux_2_6. I just need a couple of definitions...
 
No. we don't need new BSP for this. The BSP exists more than year.
http://git.monstr.eu/cgi-bin/gitweb.cgi?p=u-boot-bsp.git;a=summary
and description is at:
http://www.monstr.eu/wiki/doku.php?id=uboot:uboot

Could you send me your mhs and mss file? I'll add it to u-boot bsp and I send you bsp and output.

Thanks,
Michal



 
>    Best Regards
> 
> 
> 
> -- 
> Ricardo Ribalda
> http://www.eps.uam.es/~rribalda/
> 
> 
> 

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-14 12:06         ` Wolfgang Denk
@ 2008-07-14 12:11           ` Michal Simek
  2008-07-14 13:12             ` Ricardo Ribalda Delgado
  0 siblings, 1 reply; 22+ messages in thread
From: Michal Simek @ 2008-07-14 12:11 UTC (permalink / raw)
  To: u-boot

> > You are right, but I cannot see how to share code between
> > architechtures... If WD don't have a good idea we should have here the
> > xilinx iic code repeated.
> 
> No. Duplicating code is never a good idea.
 
I agree. 

Michal
 
> Best regards,
> 
> Wolfgang Denk

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-14 12:11           ` Michal Simek
@ 2008-07-14 13:12             ` Ricardo Ribalda Delgado
  0 siblings, 0 replies; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-14 13:12 UTC (permalink / raw)
  To: u-boot

Hello All:

  I am preparing a patch for ppc.c that divides interrupts.c in
interrupts.c and ioc.c. My idea was to add a new file called
xilinx_irq.c and place there the xilinx interrupt handling.

   I would like that microblaze and xilinx_irq.c use the same code:
but I see this quite complicated. I can create a file with the xilinx
irq logic (init, enable, disable and ack) but I cannot see where shall
I place it if there is no drivers/interrupt/ directory

   One more question: interrupts/microblace access the pic registers like:
 address=&PIC;
 pic=value;
   If I create a new file, I suppose that I have to move it to
out_be32() and in_be32(). Am I right?


      Best regards





-- 
Ricardo Ribalda
http://www.eps.uam.es/~rribalda/

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
@ 2008-07-14 17:03 Ricardo Ribalda Delgado
  2008-07-14 17:03 ` Ricardo Ribalda Delgado
  0 siblings, 1 reply; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-14 17:03 UTC (permalink / raw)
  To: u-boot

-Support for the embbedded ppc440 on the Virtex5 FPGAs
-New uic.c and xilinx_irq.c external interrupt handlers

^ permalink raw reply	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-14 17:03 Ricardo Ribalda Delgado
@ 2008-07-14 17:03 ` Ricardo Ribalda Delgado
  2008-07-14 17:06   ` Ricardo Ribalda Delgado
  0 siblings, 1 reply; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-14 17:03 UTC (permalink / raw)
  To: u-boot

-Support for the embbedded ppc440 on the Virtex5 FPGAs
-New uic.c and xilinx_irq.c external interrupt handlers

Signed-off-by: Ricardo Ribalda Delgado <ricardo.ribalda@uam.es>
---
 cpu/ppc4xx/Makefile         |   15 +++-
 cpu/ppc4xx/cpu.c            |    4 +
 cpu/ppc4xx/interrupts.c     |  178 ++++++---------------------------
 cpu/ppc4xx/speed.c          |    6 +-
 cpu/ppc4xx/uic.c            |  238 +++++++++++++++++++++++++++++++++++++++++++
 cpu/ppc4xx/xilinx_irq.c     |  115 +++++++++++++++++++++
 include/asm-ppc/interrupt.h |   51 +++++++++
 include/asm-ppc/processor.h |    2 +
 8 files changed, 459 insertions(+), 150 deletions(-)
 create mode 100644 cpu/ppc4xx/uic.c
 create mode 100644 cpu/ppc4xx/xilinx_irq.c
 create mode 100644 include/asm-ppc/interrupt.h

diff --git a/cpu/ppc4xx/Makefile b/cpu/ppc4xx/Makefile
index 800bb41..b006127 100644
--- a/cpu/ppc4xx/Makefile
+++ b/cpu/ppc4xx/Makefile
@@ -35,10 +35,14 @@ SOBJS	+= kgdb.o
 COBJS	:= 40x_spd_sdram.o
 COBJS	+= 44x_spd_ddr.o
 COBJS	+= 44x_spd_ddr2.o
-COBJS	+= 4xx_enet.o
+ifndef CONFIG_XILINX_440
+COBJS   += 4xx_enet.o
+endif
 COBJS	+= 4xx_pci.o
 COBJS	+= 4xx_pcie.o
+ifndef CONFIG_XILINX_440
 COBJS	+= 4xx_uart.o
+endif
 COBJS	+= bedbug_405.o
 COBJS	+= commproc.o
 COBJS	+= cpu.o
@@ -47,11 +51,20 @@ COBJS	+= denali_data_eye.o
 COBJS	+= denali_spd_ddr2.o
 COBJS	+= ecc.o
 COBJS	+= fdt.o
+ifndef CONFIG_XILINX_440
 COBJS	+= gpio.o
+endif
 COBJS	+= i2c.o
 COBJS	+= interrupts.o
+ifndef CONFIG_XILINX_440
+COBJS	+= uic.o
+else
+COBJS	+= xilinx_irq.o
+endif
 COBJS	+= iop480_uart.o
+ifndef CONFIG_XILINX_440
 COBJS	+= miiphy.o
+endif
 COBJS	+= ndfc.o
 COBJS	+= sdram.o
 COBJS	+= speed.o
diff --git a/cpu/ppc4xx/cpu.c b/cpu/ppc4xx/cpu.c
index ef32bc6..2b9b364 100644
--- a/cpu/ppc4xx/cpu.c
+++ b/cpu/ppc4xx/cpu.c
@@ -541,6 +541,10 @@ int checkcpu (void)
 		puts("GX Rev. A");
 		strcpy(addstr, "No Security support");
 		break;
+	
+	case PVR_VIRTEX5:
+		puts(" VIRTEX5");
+		break;
 
 	default:
 		printf (" UNKNOWN (PVR=%08x)", pvr);
diff --git a/cpu/ppc4xx/interrupts.c b/cpu/ppc4xx/interrupts.c
index 8215dc6..58d1d81 100644
--- a/cpu/ppc4xx/interrupts.c
+++ b/cpu/ppc4xx/interrupts.c
@@ -8,6 +8,10 @@
  * (C) Copyright 2003 (440GX port)
  * Travis B. Sawyer, Sandburst Corporation, tsawyer at sandburst.com
  *
+ * (C) Copyright 2008 (PPC440X05 port for Virtex 5 FX)
+ * Ricardo Ribalda-Universidad Autonoma de Madrid-ricardo.ribalda at uam.es
+ * Work supported by Qtechnology (htpp://qtec.com)
+ *
  * See file CREDITS for list of people who contributed to this
  * project.
  *
@@ -31,23 +35,11 @@
 #include <watchdog.h>
 #include <command.h>
 #include <asm/processor.h>
+#include <asm/interrupt.h>
 #include <ppc4xx.h>
 #include <ppc_asm.tmpl>
 #include <commproc.h>
 
-#if (UIC_MAX > 3)
-#define UICB0_ALL	(UIC_MASK(VECNUM_UIC1CI) | UIC_MASK(VECNUM_UIC1NCI) | \
-			 UIC_MASK(VECNUM_UIC2CI) | UIC_MASK(VECNUM_UIC2NCI) | \
-			 UIC_MASK(VECNUM_UIC3CI) | UIC_MASK(VECNUM_UIC3NCI))
-#elif (UIC_MAX > 2)
-#define UICB0_ALL	(UIC_MASK(VECNUM_UIC1CI) | UIC_MASK(VECNUM_UIC1NCI) | \
-			 UIC_MASK(VECNUM_UIC2CI) | UIC_MASK(VECNUM_UIC2NCI))
-#elif (UIC_MAX > 1)
-#define UICB0_ALL	(UIC_MASK(VECNUM_UIC1CI) | UIC_MASK(VECNUM_UIC1NCI))
-#else
-#define UICB0_ALL	0
-#endif
-
 DECLARE_GLOBAL_DATA_PTR;
 
 /*
@@ -58,11 +50,7 @@ struct	irq_action {
 	void *arg;
 	int count;
 };
-
-static struct irq_action irq_vecs[UIC_MAX * 32];
-
-u32 get_dcr(u16);
-void set_dcr(u16, u32);
+static struct irq_action irq_vecs[IRQ_MAX];
 
 #if defined(CONFIG_440)
 
@@ -103,7 +91,7 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	/*
 	 * Mark all irqs as free
 	 */
-	for (vec = 0; vec < (UIC_MAX * 32); vec++) {
+	for (vec = 0; vec < IRQ_MAX; vec++) {
 		irq_vecs[vec].handler = NULL;
 		irq_vecs[vec].arg = NULL;
 		irq_vecs[vec].count = 0;
@@ -147,110 +135,36 @@ int interrupt_init_cpu (unsigned *decrementer_count)
 	 */
 	set_evpr(0x00000000);
 
-#if (UIC_MAX > 1)
-	/* Install the UIC1 handlers */
-	irq_install_handler(VECNUM_UIC1NCI, (void *)(void *)external_interrupt, 0);
-	irq_install_handler(VECNUM_UIC1CI, (void *)(void *)external_interrupt, 0);
-#endif
-#if (UIC_MAX > 2)
-	irq_install_handler(VECNUM_UIC2NCI, (void *)(void *)external_interrupt, 0);
-	irq_install_handler(VECNUM_UIC2CI, (void *)(void *)external_interrupt, 0);
-#endif
-#if (UIC_MAX > 3)
-	irq_install_handler(VECNUM_UIC3NCI, (void *)(void *)external_interrupt, 0);
-	irq_install_handler(VECNUM_UIC3CI, (void *)(void *)external_interrupt, 0);
-#endif
+	/*
+	 *Call uic or xilinx_irq pic_enable
+	 */
+	pic_enable();
 
 	return (0);
 }
 
-/* Handler for UIC interrupt */
-static void uic_interrupt(u32 uic_base, int vec_base)
+void timer_interrupt_cpu(struct pt_regs *regs)
 {
-	u32 uic_msr;
-	u32 msr_shift;
-	int vec;
-
-	/*
-	 * Read masked interrupt status register to determine interrupt source
-	 */
-	uic_msr = get_dcr(uic_base + UIC_MSR);
-	msr_shift = uic_msr;
-	vec = vec_base;
-
-	while (msr_shift != 0) {
-		if (msr_shift & 0x80000000) {
-			/*
-			 * Increment irq counter (for debug purpose only)
-			 */
-			irq_vecs[vec].count++;
-
-			if (irq_vecs[vec].handler != NULL) {
-				/* call isr */
-				(*irq_vecs[vec].handler)(irq_vecs[vec].arg);
-			} else {
-				set_dcr(uic_base + UIC_ER,
-					get_dcr(uic_base + UIC_ER) & ~UIC_MASK(vec));
-				printf("Masking bogus interrupt vector %d"
-				       " (UIC_BASE=0x%x)\n", vec, uic_base);
-			}
-
-			/*
-			 * After servicing the interrupt, we have to remove the
-			 * status indicator
-			 */
-			set_dcr(uic_base + UIC_SR, UIC_MASK(vec));
-		}
-
-		/*
-		 * Shift msr to next position and increment vector
-		 */
-		msr_shift <<= 1;
-		vec++;
-	}
+	/* nothing to do here */
+	return;
 }
 
-/*
- * Handle external interrupts
- */
-void external_interrupt(struct pt_regs *regs)
+void interrupt_run_handler(int vec)
 {
-	u32 uic_msr;
-
-	/*
-	 * Read masked interrupt status register to determine interrupt source
-	 */
-	uic_msr = mfdcr(uic0msr);
-
-#if (UIC_MAX > 1)
-	if ((UIC_MASK(VECNUM_UIC1CI) & uic_msr) ||
-	    (UIC_MASK(VECNUM_UIC1NCI) & uic_msr))
-		uic_interrupt(UIC1_DCR_BASE, 32);
-#endif
-
-#if (UIC_MAX > 2)
-	if ((UIC_MASK(VECNUM_UIC2CI) & uic_msr) ||
-	    (UIC_MASK(VECNUM_UIC2NCI) & uic_msr))
-		uic_interrupt(UIC2_DCR_BASE, 64);
-#endif
-
-#if (UIC_MAX > 3)
-	if ((UIC_MASK(VECNUM_UIC3CI) & uic_msr) ||
-	    (UIC_MASK(VECNUM_UIC3NCI) & uic_msr))
-		uic_interrupt(UIC3_DCR_BASE, 96);
-#endif
-
-	if (uic_msr & ~(UICB0_ALL))
-		uic_interrupt(UIC0_DCR_BASE, 0);
-
-	mtdcr(uic0sr, uic_msr);
+	irq_vecs[vec].count++;
+
+	if (irq_vecs[vec].handler != NULL) {
+		/* call isr */
+		(*irq_vecs[vec].handler) (irq_vecs[vec].arg);
+	} else {
+		pic_irq_disable(vec);
+		printf("Masking bogus interrupt vector %d\n", vec);
+	}
 
+	pic_irq_ack(vec);
 	return;
 }
 
-/*
- * Install and free a interrupt handler.
- */
 void irq_install_handler(int vec, interrupt_handler_t * handler, void *arg)
 {
 	/*
@@ -263,51 +177,19 @@ void irq_install_handler(int vec, interrupt_handler_t * handler, void *arg)
 	irq_vecs[vec].handler = handler;
 	irq_vecs[vec].arg = arg;
 
-	if ((vec >= 0) && (vec < 32))
-		mtdcr(uicer, mfdcr(uicer) | UIC_MASK(vec));
-#if (UIC_MAX > 1)
-	else if ((vec >= 32) && (vec < 64))
-		mtdcr(uic1er, mfdcr(uic1er) | UIC_MASK(vec));
-#endif
-#if (UIC_MAX > 2)
-	else if ((vec >= 64) && (vec < 96))
-		mtdcr(uic2er, mfdcr(uic2er) | UIC_MASK(vec));
-#endif
-#if (UIC_MAX > 3)
-	else if (vec >= 96)
-		mtdcr(uic3er, mfdcr(uic3er) | UIC_MASK(vec));
-#endif
-
-	debug("Install interrupt for vector %d ==> %p\n", vec, handler);
+	pic_irq_enable(vec);
+	return;
 }
 
-void irq_free_handler (int vec)
+void irq_free_handler(int vec)
 {
 	debug("Free interrupt for vector %d ==> %p\n",
 	      vec, irq_vecs[vec].handler);
 
-	if ((vec >= 0) && (vec < 32))
-		mtdcr(uicer, mfdcr(uicer) & ~UIC_MASK(vec));
-#if (UIC_MAX > 1)
-	else if ((vec >= 32) && (vec < 64))
-		mtdcr(uic1er, mfdcr(uic1er) & ~UIC_MASK(vec));
-#endif
-#if (UIC_MAX > 2)
-	else if ((vec >= 64) && (vec < 96))
-		mtdcr(uic2er, mfdcr(uic2er) & ~UIC_MASK(vec));
-#endif
-#if (UIC_MAX > 3)
-	else if (vec >= 96)
-		mtdcr(uic3er, mfdcr(uic3er) & ~UIC_MASK(vec));
-#endif
+	pic_irq_disable(vec);
 
 	irq_vecs[vec].handler = NULL;
 	irq_vecs[vec].arg = NULL;
-}
-
-void timer_interrupt_cpu (struct pt_regs *regs)
-{
-	/* nothing to do here */
 	return;
 }
 
@@ -319,7 +201,7 @@ int do_irqinfo(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
 	printf ("Interrupt-Information:\n");
 	printf ("Nr  Routine   Arg       Count\n");
 
-	for (vec = 0; vec < (UIC_MAX * 32); vec++) {
+	for (vec = 0; vec < IRQ_MAX; vec++) {
 		if (irq_vecs[vec].handler != NULL) {
 			printf ("%02d  %08lx  %08lx  %d\n",
 				vec,
diff --git a/cpu/ppc4xx/speed.c b/cpu/ppc4xx/speed.c
index b86b6de..d21bd82 100644
--- a/cpu/ppc4xx/speed.c
+++ b/cpu/ppc4xx/speed.c
@@ -416,7 +416,8 @@ ulong get_PCI_freq (void)
 	return sys_info.freqPCI;
 }
 
-#elif !defined(CONFIG_440GX) && !defined(CONFIG_440SP) && !defined(CONFIG_440SPE)
+#elif !defined(CONFIG_440GX) && !defined(CONFIG_440SP) && !defined(CONFIG_440SPE) \
+	&& !defined(CONFIG_XILINX_440)
 void get_sys_info (sys_info_t * sysInfo)
 {
 	unsigned long strp0;
@@ -449,6 +450,8 @@ void get_sys_info (sys_info_t * sysInfo)
 	sysInfo->freqUART = sysInfo->freqPLB;
 }
 #else
+
+#if !defined(CONFIG_XILINX_440)
 void get_sys_info (sys_info_t * sysInfo)
 {
 	unsigned long strp0;
@@ -535,6 +538,7 @@ void get_sys_info (sys_info_t * sysInfo)
 }
 
 #endif
+#endif /* CONFIG_XILINX_440 */
 
 #if defined(CONFIG_YUCCA)
 unsigned long determine_sysper(void)
diff --git a/cpu/ppc4xx/uic.c b/cpu/ppc4xx/uic.c
new file mode 100644
index 0000000..92350dc
--- /dev/null
+++ b/cpu/ppc4xx/uic.c
@@ -0,0 +1,238 @@
+/*
+ * (C) Copyright 2000-2002
+ * Wolfgang Denk, DENX Software Engineering, wd at denx.de.
+ *
+ * (C) Copyright 2002 (440 port)
+ * Scott McNutt, Artesyn Communication Producs, smcnutt at artsyncp.com
+ *
+ * (C) Copyright 2003 (440GX port)
+ * Travis B. Sawyer, Sandburst Corporation, tsawyer at sandburst.com
+ *
+ * (C) Copyright 2008 (PPC440X05 port for Virtex 5 FX)
+ * Ricardo Ribalda-Universidad Autonoma de Madrid-ricardo.ribalda at uam.es
+ * Work supported by Qtechnology (htpp://qtec.com)
+ *
+ * See file CREDITS for list of people who contributed to this
+ * project.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ */
+
+#include <common.h>
+#include <watchdog.h>
+#include <command.h>
+#include <asm/processor.h>
+#include <asm/interrupt.h>
+#include <ppc4xx.h>
+#include <ppc_asm.tmpl>
+#include <commproc.h>
+
+#if (UIC_MAX > 3)
+#define UICB0_ALL	(UIC_MASK(VECNUM_UIC1CI) | UIC_MASK(VECNUM_UIC1NCI) | \
+			 UIC_MASK(VECNUM_UIC2CI) | UIC_MASK(VECNUM_UIC2NCI) | \
+			 UIC_MASK(VECNUM_UIC3CI) | UIC_MASK(VECNUM_UIC3NCI))
+#elif (UIC_MAX > 2)
+#define UICB0_ALL	(UIC_MASK(VECNUM_UIC1CI) | UIC_MASK(VECNUM_UIC1NCI) | \
+			 UIC_MASK(VECNUM_UIC2CI) | UIC_MASK(VECNUM_UIC2NCI))
+#elif (UIC_MAX > 1)
+#define UICB0_ALL	(UIC_MASK(VECNUM_UIC1CI) | UIC_MASK(VECNUM_UIC1NCI))
+#else
+#define UICB0_ALL	0
+#endif
+
+#if (UIC_MAX > 1) && !defined(CONFIG_440GX)
+static void uic_cascade_interrupt(void *para);
+#endif
+
+DECLARE_GLOBAL_DATA_PTR;
+
+static void pic_enable()
+{
+	int vec;
+
+#if !defined (CONFIG_440_VIRTEX5)
+
+#if (UIC_MAX > 1)
+	/* Install the UIC1 handlers */
+	irq_install_handler(VECNUM_UIC1NCI, (void *)(void *)external_interrupt,
+			    0);
+	irq_install_handler(VECNUM_UIC1CI, (void *)(void *)external_interrupt,
+			    0);
+#endif
+#if (UIC_MAX > 2)
+	irq_install_handler(VECNUM_UIC2NCI, (void *)(void *)external_interrupt,
+			    0);
+	irq_install_handler(VECNUM_UIC2CI, (void *)(void *)external_interrupt,
+			    0);
+#endif
+#if (UIC_MAX > 3)
+	irq_install_handler(VECNUM_UIC3NCI, (void *)(void *)external_interrupt,
+			    0);
+	irq_install_handler(VECNUM_UIC3CI, (void *)(void *)external_interrupt,
+			    0);
+#endif
+#else				/* !defined(CONFIG_440GX) */
+	/* Take the GX out of compatibility mode
+	 * Travis Sawyer, 9 Mar 2004
+	 * NOTE: 440gx user manual inconsistency here
+	 *       Compatibility mode and Ethernet Clock select are not
+	 *       correct in the manual
+	 */
+	mfsdr(sdr_mfr, val);
+	val &= ~0x10000000;
+	mtsdr(sdr_mfr, val);
+
+	/* Enable UIC interrupts via UIC Base Enable Register */
+	mtdcr(uicb0sr, UICB0_ALL);
+	mtdcr(uicb0er, 0x54000000);
+	/* None are critical */
+	mtdcr(uicb0cr, 0);
+#endif				/* !defined(CONFIG_440GX) */
+
+}
+
+#if (UIC_MAX > 1) && !defined(CONFIG_440GX)
+static void uic_cascade_interrupt(void *para)
+{
+	external_interrupt(para);
+}
+#endif
+
+/* Handler for UIC interrupt */
+static void uic_interrupt(u32 uic_base, int vec_base)
+{
+	u32 uic_msr;
+	u32 msr_shift;
+	int vec;
+
+	/*
+	 * Read masked interrupt status register to determine interrupt source
+	 */
+	uic_msr = get_dcr(uic_base + UIC_MSR);
+	msr_shift = uic_msr;
+	vec = vec_base;
+
+	while (msr_shift != 0) {
+		if (msr_shift & 0x80000000)
+			interrupt_run_handler(vec);
+		/*
+		 * Shift msr to next position and increment vector
+		 */
+		msr_shift <<= 1;
+		vec++;
+	}
+}
+
+/*
+ * Handle external interrupts
+ */
+void external_interrupt(struct pt_regs *regs)
+{
+	u32 uic_msr;
+
+	/*
+	 * Read masked interrupt status register to determine interrupt source
+	 */
+	uic_msr = mfdcr(uic0msr);
+
+#if (UIC_MAX > 1)
+	if ((UIC_MASK(VECNUM_UIC1CI) & uic_msr) ||
+	    (UIC_MASK(VECNUM_UIC1NCI) & uic_msr))
+		uic_interrupt(UIC1_DCR_BASE, 32);
+#endif
+
+#if (UIC_MAX > 2)
+	if ((UIC_MASK(VECNUM_UIC2CI) & uic_msr) ||
+	    (UIC_MASK(VECNUM_UIC2NCI) & uic_msr))
+		uic_interrupt(UIC2_DCR_BASE, 64);
+#endif
+
+#if (UIC_MAX > 3)
+	if ((UIC_MASK(VECNUM_UIC3CI) & uic_msr) ||
+	    (UIC_MASK(VECNUM_UIC3NCI) & uic_msr))
+		uic_interrupt(UIC3_DCR_BASE, 96);
+#endif
+
+	if (uic_msr & ~(UICB0_ALL))
+		uic_interrupt(UIC0_DCR_BASE, 0);
+
+	mtdcr(uic0sr, uic_msr);
+
+	return;
+}
+
+void pic_irq_ack(int vec)
+{
+
+	if ((vec >= 0) && (vec < 32))
+		mtdcr(uicsr, UIC_MASK(vec));
+#if (UIC_MAX > 1)
+	else if ((vec >= 32) && (vec < 64))
+		mtdcr(uic1sr, UIC_MASK(vec));
+#endif
+#if (UIC_MAX > 2)
+	else if ((vec >= 64) && (vec < 96))
+		mtdcr(uic2sr, UIC_MASK(vec));
+#endif
+#if (UIC_MAX > 3)
+	else if (vec >= 96)
+		mtdcr(uic3sr, UIC_MASK(vec));
+#endif
+}
+
+/*
+ * Install and free a interrupt handler.
+ */
+void pic_irq_enable(int vec, interrupt_handler_t * handler, void *arg)
+{
+
+	if ((vec >= 0) && (vec < 32))
+		mtdcr(uicer, mfdcr(uicer) | UIC_MASK(vec));
+#if (UIC_MAX > 1)
+	else if ((vec >= 32) && (vec < 64))
+		mtdcr(uic1er, mfdcr(uic1er) | UIC_MASK(vec));
+#endif
+#if (UIC_MAX > 2)
+	else if ((vec >= 64) && (vec < 96))
+		mtdcr(uic2er, mfdcr(uic2er) | UIC_MASK(vec));
+#endif
+#if (UIC_MAX > 3)
+	else if (vec >= 96)
+		mtdcr(uic3er, mfdcr(uic3er) | UIC_MASK(vec));
+#endif
+
+	debug("Install interrupt for vector %d ==> %p\n", vec, handler);
+}
+
+void pic_irq_disable(int vec)
+{
+
+	if ((vec >= 0) && (vec < 32))
+		mtdcr(uicer, mfdcr(uicer) & ~UIC_MASK(vec));
+#if (UIC_MAX > 1)
+	else if ((vec >= 32) && (vec < 64))
+		mtdcr(uic1er, mfdcr(uic1er) & ~UIC_MASK(vec));
+#endif
+#if (UIC_MAX > 2)
+	else if ((vec >= 64) && (vec < 96))
+		mtdcr(uic2er, mfdcr(uic2er) & ~UIC_MASK(vec));
+#endif
+#if (UIC_MAX > 3)
+	else if (vec >= 96)
+		mtdcr(uic3er, mfdcr(uic3er) & ~UIC_MASK(vec));
+#endif
+
+}
diff --git a/cpu/ppc4xx/xilinx_irq.c b/cpu/ppc4xx/xilinx_irq.c
new file mode 100644
index 0000000..6c37863
--- /dev/null
+++ b/cpu/ppc4xx/xilinx_irq.c
@@ -0,0 +1,115 @@
+/*   
+    (C) Copyright 2008
+    Ricado Ribalda-Universidad Autonoma de Madrid-ricardo.ribalda at uam.es 
+    This work has been supported by: Q-Technology  http://qtec.com/
+    Based on interrupts.c Wolfgang Denk-DENX Software Engineering-wd at denx.de
+
+    This program is free software: you can redistribute it and/or modify
+    it under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 2 of the License, or
+    (at your option) any later version.
+
+    This program is distributed in the hope that it will be useful,
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+    GNU General Public License for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with this program.  If not, see <http://www.gnu.org/licenses/>.
+*/
+#include <common.h>
+#include <watchdog.h>
+#include <command.h>
+#include <asm/processor.h>
+#include <asm/interrupt.h>
+#include <ppc4xx.h>
+#include <ppc_asm.tmpl>
+#include <commproc.h>
+#include <asm/ppc4xx-intvec.h>
+#include <asm/io.h>
+
+DECLARE_GLOBAL_DATA_PTR;
+
+#define intc XPAR_INTC_0_BASEADDR
+#define ISR (u32*)(intc+(0*4))	/* Interrupt Status Register */
+#define IPR (u32*)(intc+(1*4))	/* Interrupt Pending Register */
+#define IER (u32*)(intc+(2*4))	/* Interrupt Enable Register */
+#define IAR (u32*)(intc+(3*4))	/* Interrupt Acknowledge Register */
+#define SIE (u32*)(intc+(4*4))	/* Set Interrupt Enable bits */
+#define CIE (u32*)(intc+(5*4))	/* Clear Interrupt Enable bits */
+#define IVR (u32*)(intc+(6*4))	/* Interrupt Vector Register */
+#define MER (u32*)(intc+(7*4))	/* Master Enable Register */
+
+#define IRQ_MASK(irq) (1<<(irq&0x1f))
+
+void pic_enable(void)
+{
+
+	printf("Xilinx PIC@0x%8x\n", intc);
+
+	/*
+	 * Disable all external interrupts until they are
+	 * explicitly requested.
+	 */
+	out_be32(IER, 0);
+
+	/* Acknowledge any pending interrupts just in case. */
+	out_be32(IAR, ~(u32) 0);
+
+	/* Turn on the Master Enable. */
+	out_be32(MER, 0x3UL);
+
+	return;
+
+}
+
+int xilinx_pic_irq_get(void)
+{
+	u32 irq;
+	irq = in_be32(IVR);
+
+	/* If no interrupt is pending then all bits of the IVR are set to 1. As
+	 * the IVR is as many bits wide as numbers of inputs are available.
+	 * Therefore, if all bits of the IVR are set to one, its content will
+	 * be bigger than XPAR_INTC_MAX_NUM_INTR_INPUTS.
+	 */
+	if (irq >= XPAR_INTC_MAX_NUM_INTR_INPUTS)
+		irq = -1;	/* report no pending interrupt. */
+
+	debug("get_irq: %d\n", irq);
+	return (irq);
+}
+
+void pic_irq_enable(unsigned int irq)
+{
+	unsigned long mask = IRQ_MASK(irq);
+	debug("enable: %d\n", irq);
+	out_be32(SIE, mask);
+}
+
+void pic_irq_disable(unsigned int irq)
+{
+	unsigned long mask = IRQ_MASK(irq);
+	debug("disable: %d\n", irq);
+	out_be32(CIE, mask);
+}
+
+void pic_irq_ack(unsigned int irq)
+{
+	unsigned long mask = IRQ_MASK(irq);
+	debug("ack: %d\n", irq);
+	out_be32(IAR, mask);
+}
+
+void external_interrupt(struct pt_regs *regs)
+{
+	int irq;
+
+	irq = xilinx_pic_irq_get();
+	if (irq < 0)
+		return;
+
+	interrupt_run_handler(irq);
+
+	return;
+}
diff --git a/include/asm-ppc/interrupt.h b/include/asm-ppc/interrupt.h
new file mode 100644
index 0000000..b625b92
--- /dev/null
+++ b/include/asm-ppc/interrupt.h
@@ -0,0 +1,51 @@
+/*   
+    (C) Copyright 2008
+    Ricado Ribalda-Universidad Autonoma de Madrid-ricardo.ribalda at uam.es 
+    This work has been supported by: Q-Technology  http://qtec.com/
+    Based on interrupts.c Wolfgang Denk-DENX Software Engineering-wd@denx.de
+
+    This program is free software: you can redistribute it and/or modify
+    it under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 2 of the License, or
+    (at your option) any later version.
+
+    This program is distributed in the hope that it will be useful,
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+    GNU General Public License for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with this program.  If not, see <http://www.gnu.org/licenses/>.
+*/
+#ifndef INTERRUPT_H
+#define INTERRUPT_H
+
+#if defined(CONFIG_440SPE) || \
+    defined(CONFIG_460EX) || defined(CONFIG_460GT)
+#define UIC_MAX		4
+#elif defined(CONFIG_440GX) || \
+    defined(CONFIG_440EPX) || defined(CONFIG_440GRX) || \
+    defined(CONFIG_405EX)
+#define UIC_MAX		3
+#elif defined(CONFIG_440GP) || defined(CONFIG_440SP) || \
+    defined(CONFIG_440EP) || defined(CONFIG_440GR)
+#define UIC_MAX		2
+#else
+#define UIC_MAX		1
+#endif
+
+#if defined(CONFIG_440_VIRTEX5)
+#define IRQ_MAX XPAR_INTC_MAX_NUM_INTR_INPUTS
+#else
+#define IRQ_MAX UIC_MAX * 32
+#endif
+
+
+void pic_enable(void);
+void pic_irq_enable(unsigned int irq);
+void pic_irq_disable(unsigned int irq);
+void pic_irq_ack(unsigned int irq);
+void external_interrupt(struct pt_regs *regs);
+void interrupt_run_handler(int vec);
+
+#endif
diff --git a/include/asm-ppc/processor.h b/include/asm-ppc/processor.h
index 6e134c3..5501244 100644
--- a/include/asm-ppc/processor.h
+++ b/include/asm-ppc/processor.h
@@ -839,6 +839,8 @@
 #define PVR_86xx	0x80040000
 #define PVR_86xx_REV1	(PVR_86xx | 0x0010)
 
+#define PVR_VIRTEX5     0x7ff21912
+
 /*
  * For the 8xx processors, all of them report the same PVR family for
  * the PowerPC core. The various versions of these processors must be
-- 
1.5.6.2

^ permalink raw reply related	[flat|nested] 22+ messages in thread

* [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX
  2008-07-14 17:03 ` Ricardo Ribalda Delgado
@ 2008-07-14 17:06   ` Ricardo Ribalda Delgado
  0 siblings, 0 replies; 22+ messages in thread
From: Ricardo Ribalda Delgado @ 2008-07-14 17:06 UTC (permalink / raw)
  To: u-boot

Hello List:

 I have prepared this patch as preliminar/beta. The interrupt.c has
been divided in two parts:
            - Code undependent to the pic (interrupt.c)
            -Code dependent to the pic (uic.c and xilinx_irq.c)

   The code in xilinx_irq.c can be reused by any other architechture.

  Any comment about this code will be very wellcomed.

    Regards



-- 
Ricardo Ribalda
http://www.eps.uam.es/~rribalda/

^ permalink raw reply	[flat|nested] 22+ messages in thread

end of thread, other threads:[~2008-07-14 17:06 UTC | newest]

Thread overview: 22+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2008-07-11 11:35 [U-Boot-Users] [PATCH] CPU PPC440x5 on Virtex5 FX Ricardo Ribalda Delgado
2008-07-11 12:09 ` Michal Simek
2008-07-11 12:30   ` Stefan Roese
2008-07-11 12:35     ` Ricardo Ribalda Delgado
2008-07-11 13:52     ` Michal Simek
2008-07-11 15:03       ` Wolfgang Denk
2008-07-11 15:10         ` Stefan Roese
2008-07-11 19:35           ` Michal Simek
2008-07-14 11:46       ` Ricardo Ribalda Delgado
2008-07-14 12:06         ` Michal Simek
2008-07-11 12:33   ` Ricardo Ribalda Delgado
2008-07-11 12:22 ` Stefan Roese
2008-07-11 12:36   ` Ricardo Ribalda Delgado
2008-07-14  0:45   ` Ricardo Ribalda Delgado
2008-07-14  8:11     ` Stefan Roese
2008-07-14 10:12       ` Ricardo Ribalda Delgado
2008-07-14 12:06         ` Wolfgang Denk
2008-07-14 12:11           ` Michal Simek
2008-07-14 13:12             ` Ricardo Ribalda Delgado
  -- strict thread matches above, loose matches on Subject: below --
2008-07-14 17:03 Ricardo Ribalda Delgado
2008-07-14 17:03 ` Ricardo Ribalda Delgado
2008-07-14 17:06   ` Ricardo Ribalda Delgado

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.