diff options
author | Stephen Rothwell <sfr@canb.auug.org.au> | 2011-03-29 10:12:37 +1100 |
---|---|---|
committer | Stephen Rothwell <sfr@canb.auug.org.au> | 2011-03-29 10:12:37 +1100 |
commit | 37371e48a5c589c129107af11e0e25dac3a3b730 (patch) | |
tree | 1c981717b893faf923a6da96871aa3af843df3ca | |
parent | 23f2249ce14a9cb5f3ecd865ddf92cb8efc8929a (diff) | |
parent | 944afcb4c53f3b841d63ce337fe37b71cea2f52f (diff) |
Merge remote-tracking branch 'xtensa/master'
Conflicts:
arch/xtensa/configs/iss_defconfig
-rw-r--r-- | arch/xtensa/Kconfig | 17 | ||||
-rw-r--r-- | arch/xtensa/Makefile | 5 | ||||
-rw-r--r-- | arch/xtensa/boot/Makefile | 1 | ||||
-rw-r--r-- | arch/xtensa/include/asm/coprocessor.h | 9 | ||||
-rw-r--r-- | arch/xtensa/include/asm/io.h | 40 | ||||
-rw-r--r-- | arch/xtensa/include/asm/irq.h | 7 | ||||
-rw-r--r-- | arch/xtensa/include/asm/serial.h | 12 | ||||
-rw-r--r-- | arch/xtensa/kernel/Makefile | 4 | ||||
-rw-r--r-- | arch/xtensa/kernel/time.c | 2 | ||||
-rw-r--r-- | arch/xtensa/platforms/xtavnet/Makefile | 10 | ||||
-rw-r--r-- | arch/xtensa/platforms/xtavnet/include/platform/hardware.h | 85 | ||||
-rw-r--r-- | arch/xtensa/platforms/xtavnet/include/platform/lcd.h | 22 | ||||
-rw-r--r-- | arch/xtensa/platforms/xtavnet/include/platform/serial.h | 1 | ||||
-rw-r--r-- | arch/xtensa/platforms/xtavnet/lcd.c | 79 | ||||
-rw-r--r-- | arch/xtensa/platforms/xtavnet/setup.c | 269 |
15 files changed, 526 insertions, 37 deletions
diff --git a/arch/xtensa/Kconfig b/arch/xtensa/Kconfig index 1d730b5579a0..d425d952f0a5 100644 --- a/arch/xtensa/Kconfig +++ b/arch/xtensa/Kconfig @@ -79,10 +79,10 @@ config XTENSA_VARIANT_S6000 endchoice config XTENSA_UNALIGNED_USER - bool "Unaligned memory access in use space" + bool "Unaligned memory access in user space" help - The Xtensa architecture currently does not handle unaligned - memory accesses in hardware but through an exception handler. + Xtensa processors are often not configured to handle unaligned + memory accesses in hardware, but rather through an exception handler. Per default, unaligned memory accesses are disabled in user space. Say Y here to enable unaligned memory access in user space. @@ -152,8 +152,15 @@ config XTENSA_PLATFORM_ISS config XTENSA_PLATFORM_XT2000 bool "XT2000" help - XT2000 is the name of Tensilica's feature-rich emulation platform. - This hardware is capable of running a full Linux distribution. + XT2000 is the name of Tensilica's older emulation platform. + +config XTENSA_PLATFORM_XTAVNET + bool "XTAVNET" + select XTENSA_CALIBRATE_CCOUNT + select ETHOC + help + Selects support for the Tensilica-configured Avnet emulation boards. + These include the LX60 (XT-AV60), LX200 (XT-AV200), and LX110 (XT-AV110). config XTENSA_PLATFORM_S6105 bool "S6105" diff --git a/arch/xtensa/Makefile b/arch/xtensa/Makefile index 7608559de93a..34d8427622eb 100644 --- a/arch/xtensa/Makefile +++ b/arch/xtensa/Makefile @@ -24,6 +24,7 @@ export VARIANT # Platform configuration platform-$(CONFIG_XTENSA_PLATFORM_XT2000) := xt2000 +platform-$(CONFIG_XTENSA_PLATFORM_XTAVNET) := xtavnet platform-$(CONFIG_XTENSA_PLATFORM_ISS) := iss platform-$(CONFIG_XTENSA_PLATFORM_S6105) := s6105 @@ -61,7 +62,9 @@ ifneq ($(VARIANT),) ifneq ($(COMPILE_ARCH), xtensa) ifndef CROSS_COMPILE - CROSS_COMPILE = xtensa_$(VARIANT)- + CROSS_COMPILE := $(call cc-cross-prefix, xtensa_$(VARIANT)- \ + xtensa-linux-uclibc- xtensa_$(VARIANT)-linux-uclibc- \ + xtensa-linux-gnu- xtensa_$(VARIANT)-linux-gnu-) endif endif endif diff --git a/arch/xtensa/boot/Makefile b/arch/xtensa/boot/Makefile index 70fd1453e172..068f143a42a2 100644 --- a/arch/xtensa/boot/Makefile +++ b/arch/xtensa/boot/Makefile @@ -23,6 +23,7 @@ subdir-y := lib bootdir-$(CONFIG_XTENSA_PLATFORM_ISS) += boot-elf bootdir-$(CONFIG_XTENSA_PLATFORM_XT2000) += boot-redboot boot-elf +bootdir-$(CONFIG_XTENSA_PLATFORM_XTAVNET) += boot-redboot boot-elf zImage zImage.initrd Image Image.initrd: $(bootdir-y) diff --git a/arch/xtensa/include/asm/coprocessor.h b/arch/xtensa/include/asm/coprocessor.h index 75c94a1658b0..42da613d1623 100644 --- a/arch/xtensa/include/asm/coprocessor.h +++ b/arch/xtensa/include/asm/coprocessor.h @@ -1,11 +1,11 @@ /* - * include/asm-xtensa/coprocessor.h + * arch/xtensa/include/asm/coprocessor.h * * This file is subject to the terms and conditions of the GNU General Public * License. See the file "COPYING" in the main directory of this archive * for more details. * - * Copyright (C) 2003 - 2007 Tensilica Inc. + * Copyright (C) 2003-2010 Tensilica Inc. */ @@ -15,9 +15,10 @@ #include <linux/stringify.h> #include <variant/core.h> #include <variant/tie.h> +#include <variant/core.h> #include <asm/types.h> -#ifdef __ASSEMBLY__ +#if defined(__ASSEMBLY__) && !defined(LINKER_SCRIPT) # include <variant/tie-asm.h> .macro xchal_sa_start a b @@ -70,7 +71,7 @@ -#endif /* __ASSEMBLY__ */ +#endif /* __ASSEMBLY__ && !LINKER_SCRIPT */ /* * XTENSA_HAVE_COPROCESSOR(x) returns 1 if coprocessor x is configured. diff --git a/arch/xtensa/include/asm/io.h b/arch/xtensa/include/asm/io.h index d04cd3a625fa..145db5cc6191 100644 --- a/arch/xtensa/include/asm/io.h +++ b/arch/xtensa/include/asm/io.h @@ -1,11 +1,11 @@ /* - * include/asm-xtensa/io.h + * arch/xtensa/include/asm/io.h * * This file is subject to the terms and conditions of the GNU General Public * License. See the file "COPYING" in the main directory of this archive * for more details. * - * Copyright (C) 2001 - 2005 Tensilica Inc. + * Copyright (C) 2001-2010 Tensilica Inc. */ #ifndef _XTENSA_IO_H @@ -63,40 +63,33 @@ static inline void * phys_to_virt(unsigned long address) #define bus_to_virt(x) phys_to_virt(x) /* - * Return the virtual (cached) address for the specified bus memory. + * Return the virtual (uncached) address for the specified bus memory + * (which is, for now, simply a physical address). * Note that we currently don't support any address outside the KIO segment. + * See also arch/mips/include/asm/io.h for nice comments. */ -static inline void *ioremap(unsigned long offset, unsigned long size) +static inline void __iomem *__ioremap(unsigned long offset, unsigned long size) { #ifdef CONFIG_MMU if (offset >= XCHAL_KIO_PADDR - && offset < XCHAL_KIO_PADDR + XCHAL_KIO_SIZE) - return (void*)(offset-XCHAL_KIO_PADDR+XCHAL_KIO_BYPASS_VADDR); + && offset <= XCHAL_KIO_PADDR + XCHAL_KIO_SIZE - 1) + return (void __iomem *)(offset - XCHAL_KIO_PADDR + XCHAL_KIO_BYPASS_VADDR); else BUG(); #else - return (void *)offset; + return (void __iomem *)offset; #endif } -static inline void *ioremap_nocache(unsigned long offset, unsigned long size) -{ -#ifdef CONFIG_MMU - if (offset >= XCHAL_KIO_PADDR - && offset < XCHAL_KIO_PADDR + XCHAL_KIO_SIZE) - return (void*)(offset-XCHAL_KIO_PADDR+XCHAL_KIO_CACHED_VADDR); - else - BUG(); -#else - return (void *)offset; -#endif -} +#define ioremap(offset, size) __ioremap(offset, size) +#define ioremap_nocache(offset, size) __ioremap(offset, size) -static inline void iounmap(void *addr) +static inline void iounmap(void __iomem *addr) { } + /* * Generic I/O */ @@ -191,6 +184,13 @@ extern void outsl (unsigned long port, const void *src, unsigned long count); #endif +#ifndef CONFIG_GENERIC_IOMAP +/* Partial Simple MMIO */ +#define ioread32(a) __raw_readl(a) +#define iowrite32(v,a) __raw_writel((v),(a)) +#endif + + /* * Convert a physical pointer to a virtual kernel pointer for /dev/mem access */ diff --git a/arch/xtensa/include/asm/irq.h b/arch/xtensa/include/asm/irq.h index 4c0ccc9c4f4c..6af436f4429d 100644 --- a/arch/xtensa/include/asm/irq.h +++ b/arch/xtensa/include/asm/irq.h @@ -1,11 +1,11 @@ /* - * include/asm-xtensa/irq.h + * arch/xtensa/include/asm/irq.h * * This file is subject to the terms and conditions of the GNU General Public * License. See the file "COPYING" in the main directory of this archive * for more details. * - * Copyright (C) 2001 - 2005 Tensilica Inc. + * Copyright (C) 2001-2010 Tensilica Inc. */ #ifndef _XTENSA_IRQ_H @@ -22,6 +22,9 @@ static inline void variant_irq_enable(unsigned int irq) { } static inline void variant_irq_disable(unsigned int irq) { } #endif +/* This number is used when no interrupt has been assigned. */ +#define NO_IRQ (-1) + #ifndef VARIANT_NR_IRQS # define VARIANT_NR_IRQS 0 #endif diff --git a/arch/xtensa/include/asm/serial.h b/arch/xtensa/include/asm/serial.h index a8a2493260f6..c55a0e2b47ca 100644 --- a/arch/xtensa/include/asm/serial.h +++ b/arch/xtensa/include/asm/serial.h @@ -1,5 +1,5 @@ /* - * include/asm-xtensa/serial.h + * arch/xtensa/include/asm/serial.h * * Configuration details for 8250, 16450, 16550, etc. serial ports * @@ -7,12 +7,20 @@ * License. See the file "COPYING" in the main directory of this archive * for more details. * - * Copyright (C) 2001 - 2005 Tensilica Inc. + * Copyright (C) 2001-2010 Tensilica Inc. */ #ifndef _XTENSA_SERIAL_H #define _XTENSA_SERIAL_H +#include <asm/irq.h> #include <platform/serial.h> +/* The 8250 driver treats IRQ 0 as absent. For the Xtensa architecture, + interrupt 0 is valid, must compare against NO_IRQ instead. */ +#ifdef is_real_interrupt +#undef is_real_interrupt +#define is_real_interrupt(irq) ((irq) != NO_IRQ) +#endif + #endif /* _XTENSA_SERIAL_H */ diff --git a/arch/xtensa/kernel/Makefile b/arch/xtensa/kernel/Makefile index 2d2728b3e862..e426a4ec7f22 100644 --- a/arch/xtensa/kernel/Makefile +++ b/arch/xtensa/kernel/Makefile @@ -27,8 +27,8 @@ sed-y = -e 's/\*(\(\.[a-z]*it\|\.ref\|\)\.text)/*(\1.literal \1.text)/g' \ -e 's/\*(\(\.text\.[a-z]*\))/*(\1.literal \1)/g' quiet_cmd__cpp_lds_S = LDS $@ - cmd__cpp_lds_S = $(CPP) $(cpp_flags) -P -C -Uxtensa -D__ASSEMBLY__ $< \ - | sed $(sed-y) >$@ + cmd__cpp_lds_S = $(CPP) $(cpp_flags) -P -C -Uxtensa -D__ASSEMBLY__ \ + -DLINKER_SCRIPT $< | sed $(sed-y) >$@ $(obj)/vmlinux.lds: $(src)/vmlinux.lds.S FORCE $(call if_changed_dep,_cpp_lds_S) diff --git a/arch/xtensa/kernel/time.c b/arch/xtensa/kernel/time.c index f3e5eb43f71c..db18807bb9e7 100644 --- a/arch/xtensa/kernel/time.c +++ b/arch/xtensa/kernel/time.c @@ -31,7 +31,7 @@ unsigned long ccount_per_jiffy; /* per 1/HZ */ unsigned long nsec_per_ccount; /* nsec per ccount increment */ #endif -static cycle_t ccount_read(void) +static cycle_t ccount_read(struct clocksource *cs) { return (cycle_t)get_ccount(); } diff --git a/arch/xtensa/platforms/xtavnet/Makefile b/arch/xtensa/platforms/xtavnet/Makefile new file mode 100644 index 000000000000..06b120b40015 --- /dev/null +++ b/arch/xtensa/platforms/xtavnet/Makefile @@ -0,0 +1,10 @@ +# Makefile for the Tensilica Avnet-based Emulation Boards +# +# Note! Dependencies are done automagically by 'make dep', which also +# removes any old dependencies. DON'T put your own dependencies here +# unless it's something special (ie not a .c file). +# +# Note 2! The CFLAGS definitions are in the main makefile... + +obj-y = setup.o lcd.o + diff --git a/arch/xtensa/platforms/xtavnet/include/platform/hardware.h b/arch/xtensa/platforms/xtavnet/include/platform/hardware.h new file mode 100644 index 000000000000..5301be745113 --- /dev/null +++ b/arch/xtensa/platforms/xtavnet/include/platform/hardware.h @@ -0,0 +1,85 @@ +/* + * arch/xtensa/platforms/xtavnet/include/platform/hardware.h + * + * This file contains the hardware configuration of Tensilica Avnet boards + * (XT-AV60, XT-AV110, XT-AV200, derived from Avnet LX60, LX110, LX200 + * boards respectively). + * + * Copyright (C) 2006-2010 Tensilica Inc. + * + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file "COPYING" in the main directory of this archive + * for more details. + */ + +#ifndef __XTAVNET_HARDWARE_H +#define __XTAVNET_HARDWARE_H + +#include <variant/core.h> + +/* Memory configuration. */ + +#define PLATFORM_DEFAULT_MEM_START 0x00000000 +#define PLATFORM_DEFAULT_MEM_SIZE 0x04000000 + +/* Interrupt configuration. */ + +#define PLATFORM_NR_IRQS 2 + +/* + * Default assignment of XTAVnet devices to external interrupts. + * + * CONFIG_ARCH_HAS_SMP means the hardware supports SMP, ie. is Xtensa MX. + * + * Systems with SMP support (MX) have an External Interrupt Distributor + * between external interrupts and the core's interrupts. The first three + * core interrupts are used for IPI (interprocessor interrupts), so + * external (board device) interrupts end up shifted up by 3. + */ + +/* UART interrupt: */ +#ifdef CONFIG_ARCH_HAS_SMP +#define UART_INTNUM XCHAL_EXTINT3_NUM +#else +#define UART_INTNUM XCHAL_EXTINT0_NUM +#endif + +/* Ethernet interrupt: */ +#ifdef CONFIG_ARCH_HAS_SMP +#define OETH_IRQ XCHAL_EXTINT4_NUM +#else +#define OETH_IRQ XCHAL_EXTINT1_NUM +#endif + +/* + * Device addresses and parameters. + */ + +/* UART */ +#define UART_PADDR 0xFD050020 + +/* LCD instruction and data virt. addresses. */ +#define LCD_INSTR_ADDR (char*)(0xFD040000) +#define LCD_DATA_ADDR (char*)(0xFD040004) + +/* Misc. */ +#define XTAVNET_FPGAREGS_VADDR 0xFD020000 +/* Clock frequency in Hz (read-only): */ +#define XTAVNET_CLKFRQ_VADDR (XTAVNET_FPGAREGS_VADDR + 0x04) +/* Setting of 8 DIP switches: */ +#define DIP_SWITCHES_VADDR (XTAVNET_FPGAREGS_VADDR + 0x0C) +/* Software reset (write 0xdead): */ +#define XTAVNET_SWRST_VADDR (XTAVNET_FPGAREGS_VADDR + 0x10) + +/* OpenCores Ethernet controller: */ +#define OETH_REGS_PADDR IOADDR(0xD030000) /* regs + RX/TX descriptors */ +#define OETH_REGS_VADDR 0xFD030000 +#define OETH_REGS_SIZE 0x1000 +#define OETH_SRAMBUFF_PADDR 0xFD800000 +#define OETH_SRAMBUFF_SIZE (5*0x600 + 5*0x600) /* 5*rx buffs + 5*tx buffs */ +/*#define OETH_SRAMBUFF_SIZE 0x3C00*/ /* probably 0x4000 ? */ +/* The MAC address for these boards is 00:50:c2:13:6f:xx. + The last byte (here as zero) is read from the DIP switches on the board. */ +#define OETH_MACADDR 0x00, 0x50, 0xc2, 0x13, 0x6f, 0 + +#endif /* __XTAVNET_HARDWARE_H */ diff --git a/arch/xtensa/platforms/xtavnet/include/platform/lcd.h b/arch/xtensa/platforms/xtavnet/include/platform/lcd.h new file mode 100644 index 000000000000..67de96acb2f9 --- /dev/null +++ b/arch/xtensa/platforms/xtavnet/include/platform/lcd.h @@ -0,0 +1,22 @@ +/* + * arch/xtensa/platforms/xtavnet/include/platform/lcd.h + * + * Copyright (C) 2001-2006 Tensilica Inc. + * + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file "COPYING" in the main directory of this archive + * for more details. + */ + +#ifndef __XTAVNET_LCD_H +#define __XTAVNET_LCD_H + +/* Display string STR at position POS on the LCD. */ +void lcd_disp_at_pos(char *str, unsigned char pos); + +/* Shift the contents of the LCD display left or right. */ +void lcd_shiftleft(void); +void lcd_shiftright(void); + +#endif + diff --git a/arch/xtensa/platforms/xtavnet/include/platform/serial.h b/arch/xtensa/platforms/xtavnet/include/platform/serial.h new file mode 100644 index 000000000000..a0cb0caff152 --- /dev/null +++ b/arch/xtensa/platforms/xtavnet/include/platform/serial.h @@ -0,0 +1 @@ +#include <asm-generic/serial.h> diff --git a/arch/xtensa/platforms/xtavnet/lcd.c b/arch/xtensa/platforms/xtavnet/lcd.c new file mode 100644 index 000000000000..283986f158ad --- /dev/null +++ b/arch/xtensa/platforms/xtavnet/lcd.c @@ -0,0 +1,79 @@ +/* + * Driver for the LCD display on the Tensilica LX60 Board. + * This code has no effect on the LX200 board. (LX110: TBD) + * + * Copyright (C) 2001-2006 Tensilica Inc. + * + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file "COPYING" in the main directory of this archive + * for more details. + */ + +/* + * + * FIXME: this code is from the examples from the LX60 user guide. + * + * The lcd_pause function does busy waiting, which is probably not + * great. Maybe the code could be changed to use kernel timers, or + * change the hardware to not need to wait. + */ + +#include <linux/init.h> + +#include <platform/hardware.h> +#include <asm/processor.h> +#include <platform/lcd.h> +#include <linux/delay.h> + +#define LCD_PAUSE_ITERATIONS 4000 +#define LCD_CLEAR 0x1 +#define LCD_DISPLAY_ON 0xc + +/* 8bit and 2 lines display */ +#define LCD_DISPLAY_MODE8BIT 0x38 +#define LCD_DISPLAY_POS 0x80 +#define LCD_SHIFT_LEFT 0x18 +#define LCD_SHIFT_RIGHT 0x1c + +static int __init lcd_init(void) +{ + *LCD_INSTR_ADDR = LCD_DISPLAY_MODE8BIT; + mdelay(5); + *LCD_INSTR_ADDR = LCD_DISPLAY_MODE8BIT; + udelay(200); + *LCD_INSTR_ADDR = LCD_DISPLAY_MODE8BIT; + udelay(50); + *LCD_INSTR_ADDR = LCD_DISPLAY_ON; + udelay(50); + *LCD_INSTR_ADDR = LCD_CLEAR; + mdelay(10); + lcd_disp_at_pos("XTENSA LINUX", 0); + + return 0; +} + +void lcd_disp_at_pos (char *str, unsigned char pos) +{ + *LCD_INSTR_ADDR = LCD_DISPLAY_POS | pos; + udelay(100); + while (*str != 0){ + *LCD_DATA_ADDR = *str; + udelay(200); + str++; + } +} + +void lcd_shiftleft(void) +{ + *LCD_INSTR_ADDR = LCD_SHIFT_LEFT; + udelay(50); +} + +void lcd_shiftright(void) +{ + *LCD_INSTR_ADDR = LCD_SHIFT_RIGHT; + udelay(50); +} + +arch_initcall(lcd_init); + diff --git a/arch/xtensa/platforms/xtavnet/setup.c b/arch/xtensa/platforms/xtavnet/setup.c new file mode 100644 index 000000000000..256fcb2b2af4 --- /dev/null +++ b/arch/xtensa/platforms/xtavnet/setup.c @@ -0,0 +1,269 @@ +/* + * arch/xtensa/platform-xtavnet/setup.c + * + * Setup/initialization for Tensilica Avnet boards (XT-AV60, XT-AV110, XT-AV200, + * derived from Avnet LX60, LX110, LX200 boards respectively). + * For details, see "Tensilica Avnet LX### (XT-AV###) Board User's Guide" + * (where ### is 60, 110, or 200). + * + * Authors: Chris Zankel <chris@zankel.net> + * Joe Taylor <joe@tensilica.com> + * Pete Delaney <piet@tensilica.com> + * Marc Gauthier <marc@tensilica.com> <marc@alumni.uwaterloo.ca> + * + * Copyright 2001-2010 Tensilica Inc. + * + * This file is subject to the terms and conditions of the GNU General Public + * License, version 2. See the file "COPYING" in the main directory of this + * archive for more details. + */ + +#include <linux/stddef.h> +#include <linux/kernel.h> +#include <linux/init.h> +#include <linux/errno.h> +#include <linux/reboot.h> +#include <linux/kdev_t.h> +#include <linux/types.h> +#include <linux/major.h> +#include <linux/console.h> +#include <linux/delay.h> +#include <linux/stringify.h> +#include <linux/platform_device.h> +#include <linux/serial_8250.h> +#include <asm/timex.h> + +#include <linux/etherdevice.h> +#include <net/ethoc.h> + +#include <asm/processor.h> +#include <asm/platform.h> +#include <asm/bootparam.h> +#include <platform/lcd.h> +#include <platform/hardware.h> +#include <variant/core.h> + +/* For doing extra init. beyond what the ethoc driver does. */ +struct oeth_regs { + unsigned moder; /* Mode Register */ + unsigned int_src; /* Interrupt Source Register */ + unsigned int_mask; /* Interrupt Mask Register */ + unsigned ipgt; /* Back to Bak Inter Packet Gap Register */ + unsigned ipgr1; /* Non Back to Back Inter Packet Gap Register 1 */ + unsigned ipgr2; /* Non Back to Back Inter Packet Gap Register 2 */ + unsigned packet_len; /* Packet Length Register (min. and max.) */ + unsigned collconf; /* Collision and Retry Configuration Register */ + unsigned tx_bd_num; /* Transmit Buffer Descriptor Number Register */ + unsigned ctrlmoder; /* Control Module Mode Register */ + unsigned miimoder; /* MII Mode Register */ + unsigned miicommand; /* MII Command Register */ + unsigned miiaddress; /* MII Address Register */ + unsigned miitx_data; /* MII Transmit Data Register */ + unsigned miirx_data; /* MII Receive Data Register */ + unsigned miistatus; /* MII Status Register */ + unsigned mac_addr0; /* MAC Individual Address Register 0 */ + unsigned mac_addr1; /* MAC Individual Address Register 1 */ + unsigned hash_addr0; /* Hash Register 0 */ + unsigned hash_addr1; /* Hash Register 1 */ +}; +/* MODER Register */ +#define OETH_MODER_RST 0x00000800 /* Reset MAC */ +/* MII Mode Register */ +#define OETH_MIIMODER_CLKDIV 0x000000FF /* Clock Divider */ + + + +void platform_halt(void) +{ + /* Just display HALT on LCD display, and loop. */ + lcd_disp_at_pos(" HALT ", 0); + local_irq_disable(); + while (1); +} + +void platform_power_off(void) +{ + /* No software-controlled power-off, just display POWEROFF and loop. */ + lcd_disp_at_pos ("POWEROFF", 0); + local_irq_disable(); + while (1); +} + +void platform_restart(void) +{ + /* Software-initiated board reset. */ + *(volatile unsigned *)XTAVNET_SWRST_VADDR = 0xdead; +} + +void platform_heartbeat(void) +{ + /* Executes every timer tick. */ +} + + +/* + * Called from time_init(). "Calibrating" is a misnomer, here we just read + * the clock rate from the board specific FPGA registers. + */ +void platform_calibrate_ccount(void) +{ + long clk_freq = *(long *)XTAVNET_CLKFRQ_VADDR; + + ccount_per_jiffy = clk_freq / HZ; + nsec_per_ccount = 1000000000UL / clk_freq; +} + + +/*---------------------------------------------------------------------------- + * Ethernet -- OpenCores Ethernet MAC (ethoc driver) + */ + +static struct resource ethoc_res[] = { + [0] = { /* register space */ + .start = OETH_REGS_PADDR, + .end = OETH_REGS_PADDR + OETH_REGS_SIZE - 1, + .flags = IORESOURCE_MEM, + }, + [1] = { /* buffer space */ + .start = OETH_SRAMBUFF_PADDR, + .end = OETH_SRAMBUFF_PADDR + OETH_SRAMBUFF_SIZE - 1, + .flags = IORESOURCE_MEM, + }, + [2] = { /* IRQ number */ + .start = OETH_IRQ, + .end = OETH_IRQ, + .flags = IORESOURCE_IRQ, + }, +}; + +static struct ethoc_platform_data ethoc_pdata = { + .hwaddr = { OETH_MACADDR }, /* last byte written in setup below */ + .phy_id = -1, +}; + +static struct platform_device ethoc_device = { + .name = "ethoc", + .id = -1, + .num_resources = ARRAY_SIZE(ethoc_res), + .resource = ethoc_res, + .dev = { + .platform_data = ðoc_pdata, + }, +}; + + +/*---------------------------------------------------------------------------- + * UART + */ + +static struct resource serial_resource = { + .start = UART_PADDR, + .end = UART_PADDR + 0x1f, + .flags = IORESOURCE_MEM, +}; + +static struct plat_serial8250_port serial_platform_data[] = { + [0] = { + .mapbase = UART_PADDR, + .irq = UART_INTNUM, + .flags = UPF_BOOT_AUTOCONF | UPF_SKIP_TEST | UPF_IOREMAP, + .iotype = UPIO_MEM32, + .regshift = 2, + .uartclk = 0, /* set in xtavnet_init() */ + }, + { }, +}; + +static struct platform_device xtavnet_uart = { + .name = "serial8250", + .id = PLAT8250_DEV_PLATFORM, + .dev = { + .platform_data = serial_platform_data, + }, + .num_resources = 1, + .resource = &serial_resource, +}; + + +/*---------------------------------------------------------------------------- + */ + +/* platform devices */ +static struct platform_device *platform_devices[] = { + ðoc_device, + &xtavnet_uart, +}; + + + +/* very early init */ +void __init platform_setup(char **cmdline) +{ + if (cmdline) { + if (cmdline[0]) + printk("XTAVnet: platform_setup(cmdline[0]:'%s')\n", cmdline[0]); + else + printk("XTAVnet: platform_setup(cmdline[0]:<null>)\n"); + } +} + +/* early initialization, before secondary cpu's have been brought up */ + +void platform_init(bp_tag_t *bootparams) +{ + printk("\n"); + if( bootparams ) + printk("XTAVnet: platform_init(bootparams:0x%x)\n", (unsigned)bootparams); +} + +static int xtavnet_init(void) +{ + volatile struct oeth_regs *regs = (volatile struct oeth_regs*)OETH_REGS_VADDR; + + /* + * Do some of the initialization missing in the ETHOC driver. + * (Perhaps not all necessary, but was in a previously used driver.) + */ + + /* Reset the controller. */ + regs->moder = OETH_MODER_RST; /* Reset ON */ + regs->moder &= ~OETH_MODER_RST; /* Reset OFF */ + + regs->packet_len = (64 << 16) | 1536; + regs->ipgr1 = 0x0000000c; + regs->ipgr2 = 0x00000012; + regs->collconf = 0x000f003f; + regs->ctrlmoder = 0; + regs->miimoder = (OETH_MIIMODER_CLKDIV & 0x2); + + /* + * Setup dynamic info in platform device init structures. + */ + + /* Ethernet MAC address. */ + ethoc_pdata.hwaddr[5] = *(u32*)DIP_SWITCHES_VADDR; + + /* Clock rate varies among FPGA bitstreams; board specific FPGA register + * reports the actual clock rate. */ + serial_platform_data[0].uartclk = *(long *)XTAVNET_CLKFRQ_VADDR; + + + /* register platform devices */ + platform_add_devices(platform_devices, ARRAY_SIZE(platform_devices)); + + /* ETHOC driver is a bit quiet; at least display Ethernet MAC, so user + knows whether they set it correctly on the DIP switches. */ + printk("XTAVnet: Ethernet MAC %02x:%02x:%02x:%02x:%02x:%02x\n", + ethoc_pdata.hwaddr[0], ethoc_pdata.hwaddr[1], ethoc_pdata.hwaddr[2], + ethoc_pdata.hwaddr[3], ethoc_pdata.hwaddr[4], ethoc_pdata.hwaddr[5]); + + return 0; +} + + +/* + * Register to be done during do_initcalls(). + */ +arch_initcall(xtavnet_init); + + |