U-Boot
Threads by month
- ----- 2025 -----
- May
- April
- March
- February
- January
- ----- 2024 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2023 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2022 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2021 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2020 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2019 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2018 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2017 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2016 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2015 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2014 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2013 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2012 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2011 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2010 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2009 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2008 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2007 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2006 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2005 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2004 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2003 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2002 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2001 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2000 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
August 2008
- 172 participants
- 523 discussions
*CHANGELOG Added Support for Embedded Planet Boards EP852 EP866 and
EP85xxm. See respective board config file for original author
information. Merged from internal company port and QUICCstart kit into
the most recent u-boot git by J. Mann, Embedded Planet, 2006-JUL-27.
(this is part 2 of 2 split in half for size reasons.)
(the first attempt to send this e-mail resulted in a message too big
error. Sorry if you get two on acident)
2
1

29 Nov '08
3
2
The patch is to add support functions which load and boot WinCE image.
It introduces one new CMD macro named 'CONFIG_CMD_WINCE'.
The source codes have tested on STLS board.
Signed-off-by: Ryan Chen <ryan.chen(a)st.com>
---
common/Makefile | 1 +
common/cmd_bootm.c | 32 ++++++++
common/cmd_wince.c | 193 ++++++++++++++++++++++++++++++++++++++++++++++
include/config_cmd_all.h | 1 +
include/image.h | 1 +
5 files changed, 228 insertions(+), 0 deletions(-)
create mode 100644 common/cmd_wince.c
diff --git a/common/Makefile b/common/Makefile
index 4287108..e427828 100644
--- a/common/Makefile
+++ b/common/Makefile
@@ -144,6 +144,7 @@ COBJS-y += cmd_mac.o
COBJS-$(CONFIG_CMD_MFSL) += cmd_mfsl.o
COBJS-$(CONFIG_MP) += cmd_mp.o
COBJS-$(CONFIG_CMD_SF) += cmd_sf.o
+COBJS-$(CONFIG_CMD_WINCE) += cmd_wince.o
COBJS := $(COBJS-y)
SRCS := $(AOBJS:.o=.S) $(COBJS:.o=.c)
diff --git a/common/cmd_bootm.c b/common/cmd_bootm.c
index 1c0a416..e6397d7 100644
--- a/common/cmd_bootm.c
+++ b/common/cmd_bootm.c
@@ -106,6 +106,10 @@ int do_bootelf (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]);
#if defined(CONFIG_ARTOS) && defined(CONFIG_PPC)
static boot_os_fn do_bootm_artos;
#endif
+#if defined(CONFIG_CMD_WINCE)
+static boot_os_fn do_bootm_wince;
+int do_bootwince (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]);
+#endif
ulong load_addr = CFG_LOAD_ADDR; /* Default Load Address */
static bootm_headers_t images; /* pointers to os/initrd/fdt images */
@@ -358,6 +362,12 @@ int do_bootm (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
do_bootm_artos (cmdtp, flag, argc, argv, &images);
break;
#endif
+
+#ifdef CONFIG_CMD_WINCE
+ case IH_OS_WINCE:
+ do_bootm_wince (cmdtp, flag, argc, argv, &images);
+ break;
+#endif
}
show_boot_progress (-9);
@@ -1142,3 +1152,25 @@ static void do_bootm_artos (cmd_tbl_t *cmdtp, int flag,
(*entry) (kbd, cmdline, fwenv, top);
}
#endif
+
+#if defined(CONFIG_CMD_WINCE)
+static void do_bootm_wince (cmd_tbl_t *cmdtp, int flag,
+ int argc, char *argv[],
+ bootm_headers_t *images)
+{
+ char str[80];
+ image_header_t *hdr = &images->legacy_hdr_os_copy;
+
+#if defined(CONFIG_FIT)
+ if (!images->legacy_hdr_valid) {
+ fit_unsupported_reset ("WinCE");
+ do_reset (cmdtp, flag, argc, argv);
+ }
+#endif
+
+ sprintf(str, "%x", image_get_ep (hdr)); /* write entry-point into string */
+ setenv("loadaddr", str);
+ do_bootwince(cmdtp, 0, 0, NULL);
+}
+#endif/* CONFIG_CMD_WINCE */
+
diff --git a/common/cmd_wince.c b/common/cmd_wince.c
new file mode 100644
index 0000000..fdc2e6b
--- /dev/null
+++ b/common/cmd_wince.c
@@ -0,0 +1,193 @@
+/*
+ * 2008 (c) STMicroelectronics, Inc.
+ * Author: Ryan Chen <Ryan.Chen(a)st.com>
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Opsycon AB, Sweden.
+ * 4. The name of the author may not be used to endorse or promote products
+ * derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
+ * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <common.h>
+#include <command.h>
+#include <linux/ctype.h>
+#include <net.h>
+
+/*
+ * Windows CE Binary Image Data Format
+ * The binary image (.bin) file format organizes data by sections. Each section contains
+ * a section header that specifies the starting address, length, and checksum for that
+ * section.
+ *
+ * Refer to <http://msdn.microsoft.com/en-us/library/ms924510.aspx>
+ *
+ * The following table shows the .bin file format.
+ * Field Length (bytes) Description
+ * Sync bytes (optional) 7 Byte 0 is B, indicating a .bin file format.
+ * Bytes 1-6 are reserved and set to 0, 0, 0, F, F, \n.
+ * Run-time image address 4 Physical starting address of the run-time image.
+ * Run-time image length 4 Physical length, in bytes, of the run-time image.
+ * Record Address 4 Physical starting address of data record.
+ * If this value is zero, the Record Address is the end of
+ * the file, and record length contains the starting address
+ * of the run-time image.
+ * Record length 4 Length of record data, in bytes.
+ * Record checksum 4 Signed 32-bit sum of record data bytes.
+ * Record data Record length Record data.
+ */
+#define WINCE_IMAGE_SYNC_SIZE 7
+#define WINCE_IMAGE_SYNC "B000FF\n"
+
+typedef struct {
+ unsigned char sync_bytes[WINCE_IMAGE_SYNC_SIZE];
+ unsigned int img_addr;
+ unsigned int img_length;
+} type_wince_image_header;
+
+int check_sum(unsigned char * buf, int len, unsigned int checksum)
+{
+ unsigned int count,i;
+
+ for (i = 0,count = 0 ; i < len ; i++)
+ count += buf[i];
+
+ if (count == checksum)
+ return 0;
+
+ return 1;
+}
+
+/* ======================================================================
+ * Determine if a valid WinCE image exists at the given memory location.
+ * First looks at the image header field, the makes sure that it is
+ * WinCE image.
+ * ====================================================================== */
+int valid_wince_image (unsigned long addr)
+{
+ type_wince_image_header *p = (type_wince_image_header *)addr;
+
+ if(strcmp((char *)p->sync_bytes, (char *)WINCE_IMAGE_SYNC) != 0)
+ return 0;
+
+ return 1;
+}
+
+/* ======================================================================
+ * A very simple WinCE image loader, assumes the image is valid, returns the
+ * entry point address.
+ * ====================================================================== */
+unsigned long load_wince_image (unsigned long addr)
+{
+ unsigned char *p = (unsigned char *)addr;
+ u32 start_addr, total_length;
+ u32 record_addr, record_length, record_checksum;
+ u32 i = 0;
+
+ if(valid_wince_image(addr) == 0)
+ return ~0;
+
+ printf("WINCE image is found: ");
+ p += WINCE_IMAGE_SYNC_SIZE;
+ start_addr = (u32)(p[3]<<24) + (u32)(p[2]<<16) + (u32)(p[1]<<8) + (u32)p[0];
+ p += 4;
+ total_length = (u32)(p[3]<<24) + (u32)(p[2]<<16) + (u32)(p[1]<<8) + (u32)p[0];
+ printf(" Start Address = 0x%x @ Total Length = 0x%x\n", start_addr, total_length);
+ p += 4;
+
+ /* read each records */
+ while(1) {
+ record_length = (u32)(p[7]<<24) + (u32)(p[6]<<16) + (u32)(p[5]<<8) + (u32)p[4];
+ record_checksum = (u32)(p[11]<<24) + (u32)(p[10]<<16) + (u32)(p[9]<<8) + (u32)p[8];
+ record_addr = (u32)(p[3]<<24) + (u32)(p[2]<<16) + (u32)(p[1]<<8) + (u32)p[0];
+ if(record_addr == 0)
+ break;
+
+ if(check_sum((unsigned char *)&p[12], record_length, record_checksum) != 0) {
+ printf("Checksum Error!\n");
+ return (unsigned long)~0;
+ }
+ memcpy ((void *)record_addr, (const void *)&p[12], (unsigned long)record_length);
+ printf("Region %d: Loading from 0x%x to 0x%x @ Length 0x%x\n", i, (unsigned int)&p[12], \
+ (unsigned int)record_addr, record_length);
+ p = p + 12 + record_length;
+ i++;
+ }
+
+ /* the lastest checksun should be zero */
+ if(record_checksum != 0) {
+ printf("Checksum Error!\n");
+ return (unsigned long)~0;
+ }
+
+ /* the lastest length is entry address */
+ return (unsigned long)record_length;
+}
+
+/* ======================================================================
+ * Interpreter command to boot WinCE from a memory image. The image can
+ * be an WinCE image. WinCE image do not need the
+ * bootline and other parameters.
+ * ====================================================================== */
+int do_bootwince (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+ unsigned long addr; /* Address of image */
+
+ /*
+ * Check the loadaddr variable.
+ * If we don't know where the image is then we're done.
+ */
+ if (argc < 2)
+ addr = load_addr;
+ else
+ addr = simple_strtoul (argv[1], NULL, 16);
+
+#if defined(CONFIG_CMD_NET)
+ /* Check to see if we need to tftp the image ourselves before starting */
+ if ((argc == 2) && (strcmp (argv[1], "tftp") == 0)) {
+ if (NetLoop (TFTP) <= 0)
+ return 1;
+ printf ("Automatic boot of WinCE image at address 0x%08lx ... \n", addr);
+ }
+#endif
+
+ /*
+ * If the data at the load address is an WinCE image, then
+ * treat it like an WinCE image. Otherwise, return 1
+ */
+ if (valid_wince_image (addr)) {
+ addr = load_wince_image (addr);
+ } else {
+ puts ("## Not an WinCE image, exit!\n");
+ return 1;
+ /* leave addr as load_addr */
+ }
+
+ printf ("## Starting Wince at 0x%08lx ...\n", addr);
+
+ ((void (*)(void)) addr) ();
+
+ puts ("## WinCE terminated\n");
+ return 1;
+}
+
diff --git a/include/config_cmd_all.h b/include/config_cmd_all.h
index c2bb094..5f6fab5 100644
--- a/include/config_cmd_all.h
+++ b/include/config_cmd_all.h
@@ -81,5 +81,6 @@
#define CONFIG_CMD_VFD /* VFD support (TRAB) */
#define CONFIG_CMD_XIMG /* Load part of Multi Image */
#define CONFIG_CMD_AT91_SPIMUX /* AT91 MMC/SPI Mux Support */
+#define CONFIG_CMD_WINCE /* WinCE load/boot cmd */
#endif /* _CONFIG_CMD_ALL_H */
diff --git a/include/image.h b/include/image.h
index 46138fa..7253278 100644
--- a/include/image.h
+++ b/include/image.h
@@ -85,6 +85,7 @@
#define IH_OS_RTEMS 18 /* RTEMS */
#define IH_OS_ARTOS 19 /* ARTOS */
#define IH_OS_UNITY 20 /* Unity OS */
+#define IH_OS_WINCE 21 /* WinCE OS */
/*
* CPU Architecture Codes (supported by Linux)
--
1.6.0.rc1
3
3
This patch provides support for AFEB9260 board, a product of
OpenSource hardware and software. Some commertial projects
are made with this design. A board is basically AT91SAM9260-EK
with some modifications and different peripherals and different
parts used. Main purpose of this project is to gain experience in
hardware design.
More info: http://groups.google.com/group/arm9fpga-evolution-board
(In Russian only, sorry).
Subversion repository: svn://194.85.238.22/home/users/george/svn/arm9eb
Signed-off-by: Sergey Lapin <slapin(a)ossfans.org>
---
Makefile | 3 +
board/afeb9260/Makefile | 56 +++++++++++
board/afeb9260/afeb9260.c | 230 ++++++++++++++++++++++++++++++++++++++++++++
board/afeb9260/config.mk | 1 +
board/afeb9260/nand.c | 79 +++++++++++++++
board/afeb9260/partition.c | 36 +++++++
include/configs/afeb9260.h | 169 ++++++++++++++++++++++++++++++++
7 files changed, 574 insertions(+), 0 deletions(-)
create mode 100644 board/afeb9260/Makefile
create mode 100644 board/afeb9260/afeb9260.c
create mode 100644 board/afeb9260/config.mk
create mode 100644 board/afeb9260/nand.c
create mode 100644 board/afeb9260/partition.c
create mode 100644 include/configs/afeb9260.h
diff --git a/Makefile b/Makefile
index 3179c67..edef217 100644
--- a/Makefile
+++ b/Makefile
@@ -2387,6 +2387,9 @@ at91cap9adk_config : unconfig
at91sam9260ek_config : unconfig
@$(MKCONFIG) $(@:_config=) arm arm926ejs at91sam9260ek atmel at91sam9
+afeb9260_config : unconfig
+ @$(MKCONFIG) $(@:_config=) arm arm926ejs afeb9260 NULL at91sam9
+
########################################################################
## ARM Integrator boards - see doc/README-integrator for more info.
integratorap_config \
diff --git a/board/afeb9260/Makefile b/board/afeb9260/Makefile
new file mode 100644
index 0000000..60c4304
--- /dev/null
+++ b/board/afeb9260/Makefile
@@ -0,0 +1,56 @@
+#
+# (C) Copyright 2003-2008
+# Wolfgang Denk, DENX Software Engineering, wd(a)denx.de.
+#
+# (C) Copyright 2008
+# Stelian Pop <stelian.pop(a)leadtechdesign.com>
+# Lead Tech Design <www.leadtechdesign.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 $(TOPDIR)/config.mk
+
+LIB = $(obj)lib$(BOARD).a
+
+COBJS-y += afeb9260.o
+COBJS-y += partition.o
+COBJS-$(CONFIG_CMD_NAND) += nand.o
+
+SRCS := $(SOBJS:.o=.S) $(COBJS-y:.o=.c)
+OBJS := $(addprefix $(obj),$(COBJS-y))
+SOBJS := $(addprefix $(obj),$(SOBJS))
+
+$(LIB): $(obj).depend $(OBJS) $(SOBJS)
+ $(AR) $(ARFLAGS) $@ $(OBJS) $(SOBJS)
+
+clean:
+ rm -f $(SOBJS) $(OBJS)
+
+distclean: clean
+ rm -f $(LIB) core *.bak .depend
+
+#########################################################################
+
+# defines $(obj).depend target
+include $(SRCTREE)/rules.mk
+
+sinclude $(obj).depend
+
+#########################################################################
diff --git a/board/afeb9260/afeb9260.c b/board/afeb9260/afeb9260.c
new file mode 100644
index 0000000..252a1ea
--- /dev/null
+++ b/board/afeb9260/afeb9260.c
@@ -0,0 +1,230 @@
+/*
+ * (C) Copyright 2008 Sergey Lapin <slapin(a)ossfans.org>
+ * 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 <asm/arch/at91sam9260.h>
+#include <asm/arch/at91sam9260_matrix.h>
+#include <asm/arch/at91sam9_smc.h>
+#include <asm/arch/at91_pmc.h>
+#include <asm/arch/at91_rstc.h>
+#include <asm/arch/gpio.h>
+#include <asm/arch/io.h>
+#if defined(CONFIG_RESET_PHY_R) && defined(CONFIG_MACB)
+#include <net.h>
+#endif
+
+DECLARE_GLOBAL_DATA_PTR;
+
+/* ------------------------------------------------------------------------- */
+/*
+ * Miscelaneous platform dependent initialisations
+ */
+
+static void afeb9260_serial_hw_init(void)
+{
+#ifdef CONFIG_USART0
+ at91_set_A_periph(AT91_PIN_PB4, 1); /* TXD0 */
+ at91_set_A_periph(AT91_PIN_PB5, 0); /* RXD0 */
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91_ID_US0);
+#endif
+
+#ifdef CONFIG_USART1
+ at91_set_A_periph(AT91_PIN_PB6, 1); /* TXD1 */
+ at91_set_A_periph(AT91_PIN_PB7, 0); /* RXD1 */
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91_ID_US1);
+#endif
+
+#ifdef CONFIG_USART2
+ at91_set_A_periph(AT91_PIN_PB8, 1); /* TXD2 */
+ at91_set_A_periph(AT91_PIN_PB9, 0); /* RXD2 */
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91_ID_US2);
+#endif
+
+#ifdef CONFIG_USART3 /* DBGU */
+ at91_set_A_periph(AT91_PIN_PB14, 0); /* DRXD */
+ at91_set_A_periph(AT91_PIN_PB15, 1); /* DTXD */
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91_ID_SYS);
+#endif
+}
+
+static void afeb9260_nand_hw_init(void)
+{
+ unsigned long csa;
+
+ /* Enable CS3 */
+ csa = at91_sys_read(AT91_MATRIX_EBICSA);
+ at91_sys_write(AT91_MATRIX_EBICSA,
+ csa | AT91_MATRIX_CS3A_SMC_SMARTMEDIA);
+
+ /* Configure SMC CS3 for NAND/SmartMedia */
+ at91_sys_write(AT91_SMC_SETUP(3),
+ AT91_SMC_NWESETUP_(0) | AT91_SMC_NCS_WRSETUP_(0) |
+ AT91_SMC_NRDSETUP_(0) | AT91_SMC_NCS_RDSETUP_(0));
+ at91_sys_write(AT91_SMC_PULSE(3),
+ AT91_SMC_NWEPULSE_(3) | AT91_SMC_NCS_WRPULSE_(3) |
+ AT91_SMC_NRDPULSE_(3) | AT91_SMC_NCS_RDPULSE_(3));
+ at91_sys_write(AT91_SMC_CYCLE(3),
+ AT91_SMC_NWECYCLE_(5) | AT91_SMC_NRDCYCLE_(5));
+ at91_sys_write(AT91_SMC_MODE(3),
+ AT91_SMC_READMODE | AT91_SMC_WRITEMODE |
+ AT91_SMC_EXNWMODE_DISABLE |
+ AT91_SMC_DBW_8 |
+ AT91_SMC_TDF_(2));
+
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91SAM9260_ID_PIOC);
+
+ /* Configure RDY/BSY */
+ at91_set_gpio_input(AT91_PIN_PC13, 1);
+
+ /* Enable NandFlash */
+ at91_set_gpio_output(AT91_PIN_PC14, 1);
+}
+
+static void afeb9260_spi_hw_init(void)
+{
+ at91_set_A_periph(AT91_PIN_PA3, 0); /* SPI0_NPCS0 */
+ at91_set_B_periph(AT91_PIN_PC11, 0); /* SPI0_NPCS1 */
+
+ at91_set_A_periph(AT91_PIN_PA0, 0); /* SPI0_MISO */
+ at91_set_A_periph(AT91_PIN_PA1, 0); /* SPI0_MOSI */
+ at91_set_A_periph(AT91_PIN_PA2, 0); /* SPI0_SPCK */
+
+ /* Enable clock */
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91SAM9260_ID_SPI0);
+}
+
+#ifdef CONFIG_MACB
+static void afeb9260_macb_hw_init(void)
+{
+ /* Enable clock */
+ at91_sys_write(AT91_PMC_PCER, 1 << AT91SAM9260_ID_EMAC);
+
+ /*
+ * Disable pull-up on:
+ * RXDV (PA17) => PHY normal mode (not Test mode)
+ * ERX0 (PA14) => PHY ADDR0
+ * ERX1 (PA15) => PHY ADDR1
+ * ERX2 (PA25) => PHY ADDR2
+ * ERX3 (PA26) => PHY ADDR3
+ * ECRS (PA28) => PHY ADDR4 => PHYADDR = 0x0
+ *
+ * PHY has internal pull-down
+ */
+ writel(pin_to_mask(AT91_PIN_PA14) |
+ pin_to_mask(AT91_PIN_PA15) |
+ pin_to_mask(AT91_PIN_PA17) |
+ pin_to_mask(AT91_PIN_PA25) |
+ pin_to_mask(AT91_PIN_PA26) |
+ pin_to_mask(AT91_PIN_PA28),
+ pin_to_controller(AT91_PIN_PA0) + PIO_PUDR);
+
+ /* Need to reset PHY -> 500ms reset */
+ at91_sys_write(AT91_RSTC_MR, AT91_RSTC_KEY |
+ AT91_RSTC_ERSTL | (0x0D << 8) |
+ AT91_RSTC_URSTEN);
+
+ at91_sys_write(AT91_RSTC_CR, AT91_RSTC_KEY | AT91_RSTC_EXTRST);
+
+ /* Wait for end hardware reset */
+ while (!(at91_sys_read(AT91_RSTC_SR) & AT91_RSTC_NRSTL));
+
+ /* Restore NRST value */
+ at91_sys_write(AT91_RSTC_MR, AT91_RSTC_KEY |
+ AT91_RSTC_ERSTL | (0x0 << 8) |
+ AT91_RSTC_URSTEN);
+
+ /* Re-enable pull-up */
+ writel(pin_to_mask(AT91_PIN_PA14) |
+ pin_to_mask(AT91_PIN_PA15) |
+ pin_to_mask(AT91_PIN_PA17) |
+ pin_to_mask(AT91_PIN_PA25) |
+ pin_to_mask(AT91_PIN_PA26) |
+ pin_to_mask(AT91_PIN_PA28),
+ pin_to_controller(AT91_PIN_PA0) + PIO_PUER);
+
+ at91_set_A_periph(AT91_PIN_PA19, 0); /* ETXCK_EREFCK */
+ at91_set_A_periph(AT91_PIN_PA17, 0); /* ERXDV */
+ at91_set_A_periph(AT91_PIN_PA14, 0); /* ERX0 */
+ at91_set_A_periph(AT91_PIN_PA15, 0); /* ERX1 */
+ at91_set_A_periph(AT91_PIN_PA18, 0); /* ERXER */
+ at91_set_A_periph(AT91_PIN_PA16, 0); /* ETXEN */
+ at91_set_A_periph(AT91_PIN_PA12, 0); /* ETX0 */
+ at91_set_A_periph(AT91_PIN_PA13, 0); /* ETX1 */
+ at91_set_A_periph(AT91_PIN_PA21, 0); /* EMDIO */
+ at91_set_A_periph(AT91_PIN_PA20, 0); /* EMDC */
+
+#ifndef CONFIG_RMII
+ at91_set_B_periph(AT91_PIN_PA28, 0); /* ECRS */
+ at91_set_B_periph(AT91_PIN_PA29, 0); /* ECOL */
+ at91_set_B_periph(AT91_PIN_PA25, 0); /* ERX2 */
+ at91_set_B_periph(AT91_PIN_PA26, 0); /* ERX3 */
+ at91_set_B_periph(AT91_PIN_PA27, 0); /* ERXCK */
+ at91_set_B_periph(AT91_PIN_PA10, 0); /* ETX2 */
+ at91_set_B_periph(AT91_PIN_PA11, 0); /* ETX3 */
+ at91_set_B_periph(AT91_PIN_PA22, 0); /* ETXER */
+#endif
+
+}
+#endif
+
+int board_init(void)
+{
+ /* Enable Ctrlc */
+ console_init_f();
+
+ /* arch number of AT91SAM9260EK-Board */
+ // gd->bd->bi_arch_number = CONFIG_MACH_AFEB9260
+ gd->bd->bi_arch_number = 1859;
+ /* adress of boot parameters */
+ gd->bd->bi_boot_params = PHYS_SDRAM + 0x100;
+
+ afeb9260_serial_hw_init();
+#ifdef CONFIG_CMD_NAND
+ afeb9260_nand_hw_init();
+#endif
+ afeb9260_spi_hw_init();
+#ifdef CONFIG_MACB
+ afeb9260_macb_hw_init();
+#endif
+
+ return 0;
+}
+
+int dram_init(void)
+{
+ gd->bd->bi_dram[0].start = PHYS_SDRAM;
+ gd->bd->bi_dram[0].size = PHYS_SDRAM_SIZE;
+ return 0;
+}
+
+#ifdef CONFIG_RESET_PHY_R
+void reset_phy(void)
+{
+#ifdef CONFIG_MACB
+ /*
+ * Initialize ethernet HW addr prior to starting Linux,
+ * needed for nfsroot
+ */
+ eth_init(gd->bd);
+#endif
+}
+#endif
+
diff --git a/board/afeb9260/config.mk b/board/afeb9260/config.mk
new file mode 100644
index 0000000..9ce161e
--- /dev/null
+++ b/board/afeb9260/config.mk
@@ -0,0 +1 @@
+TEXT_BASE = 0x21f00000
diff --git a/board/afeb9260/nand.c b/board/afeb9260/nand.c
new file mode 100644
index 0000000..9738f0f
--- /dev/null
+++ b/board/afeb9260/nand.c
@@ -0,0 +1,79 @@
+/*
+ * (C) Copyright 2007-2008
+ * Stelian Pop <stelian.pop(a)leadtechdesign.com>
+ * Lead Tech Design <www.leadtechdesign.com>
+ *
+ * (C) Copyright 2006 ATMEL Rousset, Lacressonniere Nicolas
+ *
+ * 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 <asm/arch/at91sam9260.h>
+#include <asm/arch/gpio.h>
+#include <asm/arch/at91_pio.h>
+
+#include <nand.h>
+
+/*
+ * hardware specific access to control-lines
+ */
+#define MASK_ALE (1 << 21) /* our ALE is AD21 */
+#define MASK_CLE (1 << 22) /* our CLE is AD22 */
+
+static void at91sam9260ek_nand_hwcontrol(struct mtd_info *mtd, int cmd)
+{
+ struct nand_chip *this = mtd->priv;
+ ulong IO_ADDR_W = (ulong) this->IO_ADDR_W;
+
+ IO_ADDR_W &= ~(MASK_ALE|MASK_CLE);
+ switch (cmd) {
+ case NAND_CTL_SETCLE:
+ IO_ADDR_W |= MASK_CLE;
+ break;
+ case NAND_CTL_SETALE:
+ IO_ADDR_W |= MASK_ALE;
+ break;
+ case NAND_CTL_CLRNCE:
+ at91_set_gpio_value(AT91_PIN_PC14, 1);
+ break;
+ case NAND_CTL_SETNCE:
+ at91_set_gpio_value(AT91_PIN_PC14, 0);
+ break;
+ }
+ this->IO_ADDR_W = (void *) IO_ADDR_W;
+}
+
+static int at91sam9260ek_nand_ready(struct mtd_info *mtd)
+{
+ return at91_get_gpio_value(AT91_PIN_PC13);
+}
+
+int board_nand_init(struct nand_chip *nand)
+{
+ nand->eccmode = NAND_ECC_SOFT;
+#ifdef CFG_NAND_DBW_16
+ nand->options = NAND_BUSWIDTH_16;
+#endif
+ nand->hwcontrol = at91sam9260ek_nand_hwcontrol;
+ nand->dev_ready = at91sam9260ek_nand_ready;
+ nand->chip_delay = 20;
+
+ return 0;
+}
diff --git a/board/afeb9260/partition.c b/board/afeb9260/partition.c
new file mode 100644
index 0000000..2b99c9b
--- /dev/null
+++ b/board/afeb9260/partition.c
@@ -0,0 +1,36 @@
+/*
+ *
+ * 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 <config.h>
+#include <asm/hardware.h>
+#include <dataflash.h>
+
+AT91S_DATAFLASH_INFO dataflash_info[CFG_MAX_DATAFLASH_BANKS];
+
+struct dataflash_addr cs[CFG_MAX_DATAFLASH_BANKS] = {
+ {CFG_DATAFLASH_LOGIC_ADDR_CS0, 0}, /* Logical adress, CS */
+ {CFG_DATAFLASH_LOGIC_ADDR_CS1, 1}
+};
+
+/*define the area offsets*/
+dataflash_protect_t area_list[NB_DATAFLASH_AREA] = {
+ {0x00000000, 0x000041FF, FLAG_PROTECT_CLEAR, 0, "Bootstrap"},
+ {0x00004200, 0x000083FF, FLAG_PROTECT_CLEAR, 0, "Environment"},
+ {0x00008400, 0x00041FFF, FLAG_PROTECT_CLEAR, 0, "U-Boot"},
+};
diff --git a/include/configs/afeb9260.h b/include/configs/afeb9260.h
new file mode 100644
index 0000000..6241687
--- /dev/null
+++ b/include/configs/afeb9260.h
@@ -0,0 +1,169 @@
+/*
+ * (C) Copyright 2008 Sergey Lapin
+ *
+ * Configuation settings for the AFEB9260 board.
+ * Based on configuration for AT91SAM9260-EK
+ *
+ * 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
+ */
+
+#ifndef __CONFIG_H
+#define __CONFIG_H
+
+/* ARM asynchronous clock */
+#define AT91_MAIN_CLOCK 18429952 /* from 18.432 MHz crystal */
+#define AT91_MASTER_CLOCK 89999598 /* peripheral = main / 2 */
+#define CFG_HZ 1000000 /* 1us resolution */
+
+#define AT91_SLOW_CLOCK 32768 /* slow clock */
+
+#define CONFIG_AT91SAM9260 1 /* It's an Atmel AT91SAM9260 SoC*/
+#define CONFIG_AFEB9260 1 /* on an AFEB9260 Board */
+#undef CONFIG_USE_IRQ /* we don't need IRQ/FIQ stuff */
+
+#define CONFIG_CMDLINE_TAG 1 /* enable passing of ATAGs */
+#define CONFIG_SETUP_MEMORY_TAGS 1
+#define CONFIG_INITRD_TAG 1
+
+#define CONFIG_SKIP_LOWLEVEL_INIT
+#define CONFIG_SKIP_RELOCATE_UBOOT
+
+/*
+ * Hardware drivers
+ */
+#define CONFIG_ATMEL_USART 1
+#undef CONFIG_USART0
+#undef CONFIG_USART1
+#undef CONFIG_USART2
+#define CONFIG_USART3 1 /* USART 3 is DBGU */
+
+#define CONFIG_BOOTDELAY 3
+
+/*
+ * BOOTP options
+ */
+#define CONFIG_BOOTP_BOOTFILESIZE 1
+#define CONFIG_BOOTP_BOOTPATH 1
+#define CONFIG_BOOTP_GATEWAY 1
+#define CONFIG_BOOTP_HOSTNAME 1
+
+/*
+ * Command line configuration.
+ */
+#include <config_cmd_default.h>
+#undef CONFIG_CMD_BDI
+#undef CONFIG_CMD_IMI
+#undef CONFIG_CMD_AUTOSCRIPT
+#undef CONFIG_CMD_FPGA
+#undef CONFIG_CMD_LOADS
+#undef CONFIG_CMD_IMLS
+
+#define CONFIG_CMD_PING 1
+#define CONFIG_CMD_DHCP 1
+
+#define CONFIG_CMD_NAND 1
+#define CONFIG_CMD_USB 1
+
+/* SDRAM */
+#define CONFIG_NR_DRAM_BANKS 1
+#define PHYS_SDRAM 0x20000000
+#define PHYS_SDRAM_SIZE 0x04000000 /* 64 megs */
+
+/* DataFlash */
+#define CONFIG_HAS_DATAFLASH 1
+#define CFG_SPI_WRITE_TOUT (5*CFG_HZ)
+#define CFG_MAX_DATAFLASH_BANKS 2
+#define CFG_DATAFLASH_LOGIC_ADDR_CS0 0xC0000000 /* CS0 */
+#define CFG_DATAFLASH_LOGIC_ADDR_CS1 0xD0000000 /* CS1 */
+#define AT91_SPI_CLK 15000000
+#define DATAFLASH_TCSS (0x1a << 16)
+#define DATAFLASH_TCHS (0x1 << 24)
+
+/* NAND flash */
+#define NAND_MAX_CHIPS 1
+#define CFG_MAX_NAND_DEVICE 1
+#define CFG_NAND_BASE 0x40000000
+#define CFG_NAND_DBW_8 1
+
+/* NOR flash - no real flash on this board */
+#define CFG_NO_FLASH 1
+
+/* Ethernet */
+#define CONFIG_MACB 1
+#undef CONFIG_RMII /* We have full MII there */
+#define CONFIG_RESET_PHY_R 1
+
+#define CONFIG_NET_MULTI 1
+#define CONFIG_NET_RETRY_COUNT 20
+
+/* USB */
+#define CONFIG_USB_OHCI_NEW 1
+#define LITTLEENDIAN 1
+#define CONFIG_DOS_PARTITION 1
+#define CFG_USB_OHCI_CPU_INIT 1
+#define CFG_USB_OHCI_REGS_BASE 0x00500000 /* AT91SAM9260_UHP_BASE */
+#define CFG_USB_OHCI_SLOT_NAME "at91sam9260"
+#define CFG_USB_OHCI_MAX_ROOT_PORTS 1
+#define CONFIG_USB_STORAGE 1
+
+#define CFG_LOAD_ADDR 0x21000000 /* load address */
+
+#define CFG_MEMTEST_START PHYS_SDRAM
+#define CFG_MEMTEST_END 0x21e00000
+
+#undef CFG_USE_DATAFLASH_CS0
+#define CFG_USE_DATAFLASH_CS1 1
+#undef CFG_USE_NANDFLASH
+
+/* bootstrap + u-boot + env + linux in dataflash on CS1 */
+#define CFG_ENV_IS_IN_DATAFLASH 1
+#define CFG_MONITOR_BASE (CFG_DATAFLASH_LOGIC_ADDR_CS1 + 0x8400)
+#define CFG_ENV_OFFSET 0x4200
+#define CFG_ENV_ADDR (CFG_DATAFLASH_LOGIC_ADDR_CS1 + CFG_ENV_OFFSET)
+#define CFG_ENV_SIZE 0x4200
+#define CONFIG_BOOTCOMMAND "nand read 0x21000000 0xa0000 0x200000; bootm"
+#define CONFIG_BOOTARGS "console=ttyS0,115200 " \
+ "root=/dev/mtdblock2 " \
+ "rw rootfstype=jffs2 panic=20"
+
+#define CONFIG_BAUDRATE 115200
+#define CFG_BAUDRATE_TABLE {115200 , 19200, 38400, 57600, 9600 }
+
+#define CFG_PROMPT "U-Boot> "
+#define CFG_CBSIZE 256
+#define CFG_MAXARGS 16
+#define CFG_PBSIZE (CFG_CBSIZE + sizeof(CFG_PROMPT) + 16)
+#define CFG_LONGHELP 1
+#define CONFIG_CMDLINE_EDITING 1
+
+#define ROUND(A, B) (((A) + (B)) & ~((B) - 1))
+/*
+ * Size of malloc() pool
+ */
+#define CFG_MALLOC_LEN ROUND(3 * CFG_ENV_SIZE + 128*1024, 0x1000)
+#define CFG_GBL_DATA_SIZE 128 /* 128 bytes for initial data */
+
+#define CONFIG_STACKSIZE (32*1024) /* regular stack */
+
+#ifdef CONFIG_USE_IRQ
+#error CONFIG_USE_IRQ not supported
+#endif
+
+#endif
+
--
1.5.4.1
3
15
From: Frank Haverkamp <haver(a)vnet.ibm.com>
http://tools.ietf.org/html/rfc2348 describes the TFTP block size option
which allows larger packtes than the 512 byte default. This reduces the
number of TFTP ACKs significantly and improves performance.
To get the most benefit out of the tftp block size option the support
of defragementation of IP/UDP packet is helpful. The current implemenation
should work even with packets received out of order. To enable the large
packet size the user should set "tftp_block_size" so a value like 16352.
We experimented with different packet sizes and found that more than those
16KiB do not contribute much to the performance anymore. Therefor I limited
the defragmentation buffer to 16KiB no too waste memory.
Signed-off-by: Frank Haverkamp <haver(a)vnet.ibm.com>
Signed-off-by: Josh Boyer <jwboyer(a)linux.vnet.ibm.com>
---
include/net.h | 17 ++++++
net/net.c | 156 ++++++++++++++++++++++++++++++++++++++++++++++++++--------
net/tftp.c | 22 ++++++++
net/tftp.h | 10 +++
4 files changed, 185 insertions(+), 20 deletions(-)
--- u-boot.git.orig/include/net.h
+++ u-boot.git/include/net.h
@@ -200,6 +200,13 @@ typedef struct {
ushort udp_xsum; /* Checksum */
} IP_t;
+#define IP_OFFS 0x1FFF /* ip offset *= 8 */
+#define IP_OFFS_SHIFT 3 /* in 8 byte steps */
+#define IP_FLAGS 0xE000 /* first 3 bits */
+#define IP_FLAGS_RES 0x8000 /* reserved */
+#define IP_FLAGS_DFRAG 0x4000 /* don't fragments */
+#define IP_FLAGS_MFRAG 0x2000 /* more fragments */
+
#define IP_HDR_SIZE_NO_UDP (sizeof (IP_t) - 8)
#define IP_HDR_SIZE (sizeof (IP_t))
@@ -282,6 +289,16 @@ typedef struct icmphdr {
#define PKTSIZE_ALIGN 1536
/*#define PKTSIZE 608*/
+ /*
+ * IP/UDP Fragmentation support
+ * See: http://en.wikipedia.org/wiki/IPv4#Fragmentation_and_reassembly
+ * MAX possible UDP packet size is 64 KiB, if there is memory available.
+ */
+#define NET_ETH_MTU 1500
+#define NET_FRAG_BUF_SIZE (16 * 1024) /* MAX is 64 KiB */
+#define NET_UDP_FRAG_SIZE (NET_ETH_MTU - IP_HDR_SIZE_NO_UDP) /* 1480 */
+#define NET_FRAG_BUF_USED (NET_FRAG_BUF_SIZE / NET_UDP_FRAG_SIZE + 1)
+
/*
* Maximum receive ring size; that is, the number of packets
* we can buffer before overflow happens. Basically, this just
--- u-boot.git.orig/net/net.c
+++ u-boot.git/net/net.c
@@ -192,6 +192,15 @@ volatile uchar PktBuf[(PKTBUFSRX+1) * PK
volatile uchar *NetRxPackets[PKTBUFSRX]; /* Receive packets */
+/* Packet fragmentation support */
+static uint16_t ip_id = 0; /* sequence number */
+static uint16_t udp_len = 0;
+static uint16_t udp_src = 0;
+static uint16_t udp_dst = 0;
+static int max_idx = 0;
+static uchar NetFragBuf[NET_FRAG_BUF_SIZE];
+static char NetFragBufUsed[NET_FRAG_BUF_USED] = { 0, };
+
static rxhand_f *packetHandler; /* Current RX packet handler */
static thand_f *timeHandler; /* Current timeout handler */
static ulong timeStart; /* Time base value */
@@ -288,6 +297,13 @@ NetLoop(proto_t protocol)
{
bd_t *bd = gd->bd;
+ /* Packet fragmentation support */
+ ip_id = udp_len = udp_src = udp_dst = max_idx = 0;
+ memset(NetFragBuf, 0xFF, sizeof(NetFragBuf));
+ memset(NetFragBufUsed, 0, sizeof(NetFragBufUsed));
+ printf("NetFragBuf @ %08x max tftp_block_size=%d udp_frag_size=%d\n",
+ NetFragBuf, TFTP_BLOCK_SIZE_MAX, NET_UDP_FRAG_SIZE);
+
#ifdef CONFIG_NET_MULTI
NetRestarted = 0;
NetDevExists = 0;
@@ -1150,6 +1166,39 @@ static void CDPStart(void)
}
#endif
+#ifdef CONFIG_UDP_CHECKSUM
+/*
+ * @sumptr: Points to UDP data
+ * @sumlen: Size of UDP data
+ * @xsum: UDP checksum across IP source, destination address, protocol and size
+ *
+ * Returns 0 when checksum is correct and 1 if it is not.
+ */
+static int udp_checksum(ushort *sumptr, ushort sumlen, ulong xsum)
+{
+ while (sumlen > 1) {
+ ushort sumdata;
+
+ sumdata = *sumptr++;
+ xsum += ntohs(sumdata);
+ sumlen -= 2;
+ }
+ if (sumlen > 0) {
+ ushort sumdata;
+
+ sumdata = *(unsigned char *) sumptr;
+ sumdata = (sumdata << 8) & 0xff00;
+ xsum += sumdata;
+ }
+ while ((xsum >> 16) != 0) {
+ xsum = (xsum & 0x0000ffff) + ((xsum >> 16) & 0x0000ffff);
+ }
+ if ((xsum != 0x00000000) && (xsum != 0x0000ffff))
+ return 1;
+
+ return 0;
+}
+#endif /* CONFIG_UDP_CHECKSUM */
void
NetReceive(volatile uchar * inpkt, int len)
@@ -1164,6 +1213,7 @@ NetReceive(volatile uchar * inpkt, int l
int iscdp;
#endif
ushort cti = 0, vlanid = VLAN_NONE, myvlanid, mynvlanid;
+ uint32_t off; /* ip_off for fragmentation */
#ifdef ET_DEBUG
printf("packet received\n");
@@ -1404,9 +1454,11 @@ NetReceive(volatile uchar * inpkt, int l
if ((ip->ip_hl_v & 0xf0) != 0x40) {
return;
}
+#if 0 /* Obsolete after adding the fragmentation support */
if (ip->ip_off & htons(0x1fff)) { /* Can't deal w/ fragments */
return;
}
+#endif
/* can't deal with headers > 20 bytes */
if ((ip->ip_hl_v & 0x0f) > 0x05) {
return;
@@ -1422,6 +1474,88 @@ NetReceive(volatile uchar * inpkt, int l
#endif
return;
}
+
+ /*
+ * Fragmentation support. We need to check the ip_id
+ * and if all fragments were received correctly.
+ */
+ off = (ntohs(ip->ip_off) & IP_OFFS) << IP_OFFS_SHIFT;
+ if ((off != 0) || (ip->ip_off & htons(IP_FLAGS_MFRAG))) {
+ int size, idx, complete;
+ char *start;
+
+ /* New fragmented packet arrived, clear data. */
+ if (ntohs(ip->ip_id) != ip_id) {
+ ip_id = ntohs(ip->ip_id);
+ memset(NetFragBufUsed, 0, sizeof(NetFragBufUsed));
+ udp_len = udp_src = udp_dst = max_idx = 0;
+ }
+
+ idx = off / NET_UDP_FRAG_SIZE;
+
+ /* Packet does not fit into IP/UDP fragmentation buf */
+ if (idx >= NET_FRAG_BUF_USED) {
+ return;
+ }
+
+ NetFragBufUsed[idx] = 1;
+
+ /* Copy the UDP hdr with the data for 1st
+ fragment, else copy just payload */
+ if (off == 0) {
+ udp_len = ntohs(ip->udp_len);
+ udp_src = ntohs(ip->udp_src);
+ udp_dst = ntohs(ip->udp_dst);
+ }
+ size = ntohs(ip->ip_len) - IP_HDR_SIZE_NO_UDP;
+ start = (char *)ip + IP_HDR_SIZE_NO_UDP;
+ memcpy(NetFragBuf + off, start, size);
+
+ /*
+ * When last fragement has been received we
+ * know the number of fragments we expect. If
+ * all have arrived we process the packet.
+ */
+ if (((off != 0) && !(ip->ip_off & htons(IP_FLAGS_MFRAG))))
+ max_idx = idx;
+
+ if (max_idx == 0)
+ return;
+
+ complete = 1;
+ for (idx = 0; idx < max_idx; idx++) {
+ if (NetFragBufUsed[idx] == 0) {
+ complete = 0;
+ break;
+ }
+ }
+ if (!complete)
+ return;
+#ifdef CONFIG_UDP_CHECKSUM
+ if (ip->udp_xsum != 0) {
+ ulong xsum = ip->ip_p;
+ uint16_t *sumptr;
+
+ xsum += udp_len;
+ xsum += (ntohl(ip->ip_src) >> 16) & 0xffff;
+ xsum += (ntohl(ip->ip_src) >> 0) & 0xffff;
+ xsum += (ntohl(ip->ip_dst) >> 16) & 0xffff;
+ xsum += (ntohl(ip->ip_dst) >> 0) & 0xffff;
+ sumptr = (ushort *)NetFragBuf;
+
+ if (udp_checksum(sumptr, udp_len, xsum)) {
+ putc('U');
+ return;
+ }
+ }
+#endif /* CONFIG_UDP_CHECKSUM */
+ (*packetHandler)(NetFragBuf + 8,
+ udp_dst,
+ udp_src,
+ udp_len - 8);
+ return;
+ }
+
/*
* watch for ICMP host redirects
*
@@ -1502,26 +1636,8 @@ NetReceive(volatile uchar * inpkt, int l
sumlen = ntohs(ip->udp_len);
sumptr = (ushort *) &(ip->udp_src);
- while (sumlen > 1) {
- ushort sumdata;
-
- sumdata = *sumptr++;
- xsum += ntohs(sumdata);
- sumlen -= 2;
- }
- if (sumlen > 0) {
- ushort sumdata;
-
- sumdata = *(unsigned char *) sumptr;
- sumdata = (sumdata << 8) & 0xff00;
- xsum += sumdata;
- }
- while ((xsum >> 16) != 0) {
- xsum = (xsum & 0x0000ffff) + ((xsum >> 16) & 0x0000ffff);
- }
- if ((xsum != 0x00000000) && (xsum != 0x0000ffff)) {
- printf(" UDP wrong checksum %08lx %08x\n",
- xsum, ntohs(ip->udp_xsum));
+ if (udp_checksum(sumptr, sumlen, xsum)) {
+ putc('U');
return;
}
}
--- u-boot.git.orig/net/tftp.c
+++ u-boot.git/net/tftp.c
@@ -456,6 +456,7 @@ TftpTimeout (void)
void
TftpStart (void)
{
+ char *s, *err;
#ifdef CONFIG_TFTP_PORT
char *ep; /* Environment pointer */
#endif
@@ -518,6 +519,27 @@ TftpStart (void)
puts ("Loading: *\b");
+ /* Get alternate tftp_block_size */
+ if ((s = getenv("tftp_block_size")) != NULL) {
+ err = NULL;
+
+ TftpBlkSizeOption = simple_strtoul(s, &err, 10);
+ if (*err) {
+ printf("ERR: \"tftp_block_size\" is not a number\n");
+ TftpBlkSizeOption = TFTP_BLOCK_SIZE;
+ }
+ /*
+ * Reject values which require extensive handling.
+ * block size of 1428 octets (Ethernet MTU, less
+ * the TFTP, UDP and IP header lengths).
+ */
+ if (TftpBlkSizeOption > TFTP_BLOCK_SIZE_MAX) {
+ printf("ERR: tftp_block_sizes larger than %d not "
+ "supported\n", TFTP_BLOCK_SIZE_MAX);
+ TftpBlkSizeOption = TFTP_BLOCK_SIZE;
+ }
+ }
+
NetSetTimeout (TIMEOUT * CFG_HZ, TftpTimeout);
NetSetHandler (TftpHandler);
--- u-boot.git.orig/net/tftp.h
+++ u-boot.git/net/tftp.h
@@ -8,11 +8,21 @@
#ifndef __TFTP_H__
#define __TFTP_H__
+#include <net.h>
+
/**********************************************************************/
/*
* Global functions and variables.
*/
+/*
+ * Maximum TFTP block size bound to max size of fragmented IP/UDP
+ * packets minus TFTP and UDP/IP overhead. TFTP overhead is 2 byte
+ * opcode and 2 byte block-number.
+ */
+#define TFTP_BLOCK_SIZE_MAX (NET_FRAG_BUF_SIZE - sizeof(IP_t) - 4)
+
+
/* tftp.c */
extern void TftpStart (void); /* Begin TFTP get */
4
7

24 Oct '08
Signed-off-by: Sergey Lapin <slapin(a)ossfans.org>
---
cpu/arm926ejs/at91/Makefile | 1 +
cpu/arm926ejs/at91/watchdog.c | 35 +++++++++++++++++++++++++++++++++++
2 files changed, 36 insertions(+), 0 deletions(-)
create mode 100644 cpu/arm926ejs/at91/watchdog.c
diff --git a/cpu/arm926ejs/at91/Makefile b/cpu/arm926ejs/at91/Makefile
index 44cde1a..7befcd7 100644
--- a/cpu/arm926ejs/at91/Makefile
+++ b/cpu/arm926ejs/at91/Makefile
@@ -29,6 +29,7 @@ COBJS-y += ether.o
COBJS-y += timer.o
COBJS-$(CONFIG_HAS_DATAFLASH) +=spi.o
COBJS-y += usb.o
+COBJS-$(CONFIG_HW_WATCHDOG) +=watchdog.o
SOBJS = lowlevel_init.o
SRCS := $(SOBJS:.o=.S) $(COBJS-y:.o=.c)
diff --git a/cpu/arm926ejs/at91/watchdog.c b/cpu/arm926ejs/at91/watchdog.c
new file mode 100644
index 0000000..da15268
--- /dev/null
+++ b/cpu/arm926ejs/at91/watchdog.c
@@ -0,0 +1,35 @@
+/*
+ * watchdog.c - driver for at91sam9260 watchdog
+ *
+ * Copyright (c) 2007-2008 Analog Devices Inc.
+ *
+ * Licensed under the GPL-2 or later.
+ */
+
+#include <common.h>
+#include <watchdog.h>
+#include <asm/arch/hardware.h>
+#include <asm/arch/io.h>
+
+#ifdef CONFIG_HW_WATCHDOG
+#define AT91_WDT_CR (AT91_WDT+0x00)
+#define AT91_WDT_MR (AT91_WDT+0x04)
+#define AT91_WDT_SR (AT91_WDT+0x08)
+
+void hw_watchdog_reset(void)
+{
+ at91_sys_write(AT91_WDT_CR, 0xa5000001);
+}
+
+void hw_watchdog_init(void)
+{
+ /* 16 seconds timer, resets enabled */
+ at91_sys_write(AT91_WDT_MR, 0x3FFF2FFF);
+}
+
+void hw_watchdog_disable(void)
+{
+ /* Can't reenable per documentation */
+ at91_sys_write(AT91_WDT_MR, 0x8000);
+}
+#endif
--
1.5.4.1
3
6
Resubmit the driver for the ASIX AX88180 gigabit ethernet chip.
Signed-off-by: Louis Su louis(a)asix.com.tw
---
drivers/net/Makefile | 1 +
drivers/net/ax88180.c | 842
+++++++++++++++++++++++++++++++++++++++++++++++++
drivers/net/ax88180.h | 415 ++++++++++++++++++++++++
3 files changed, 1258 insertions(+), 0 deletions(-)
create mode 100644 drivers/net/ax88180.c
create mode 100644 drivers/net/ax88180.h
diff --git a/drivers/net/Makefile b/drivers/net/Makefile
index 84be288..3a574e0 100644
--- a/drivers/net/Makefile
+++ b/drivers/net/Makefile
@@ -26,6 +26,7 @@ include $(TOPDIR)/config.mk
LIB := $(obj)libnet.a
COBJS-$(CONFIG_DRIVER_3C589) += 3c589.o
+COBJS-$(CONFIG_DRIVER_AX88180) += ax88180.o
COBJS-$(CONFIG_BCM570x) += bcm570x.o bcm570x_autoneg.o 5701rls.o
COBJS-$(CONFIG_BFIN_MAC) += bfin_mac.o
COBJS-$(CONFIG_DRIVER_CS8900) += cs8900.o
diff --git a/drivers/net/ax88180.c b/drivers/net/ax88180.c
new file mode 100644
index 0000000..5579ef0
--- /dev/null
+++ b/drivers/net/ax88180.c
@@ -0,0 +1,842 @@
+/* ax88180: ASIX AX88180 Non-PCI Gigabit Ethernet u-boot driver */
+/*
+ This program is free software; you can distribute it and/or modify
+ it under the terms of the GNU General Public License (Version 2) as
+ published by the Free Software Foundation.
+ This program is distributed in the hope 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.
+*/
+
+/*
+ ========================================================================
+ ASIX AX88180 Non-PCI 16/32-bit Gigabit Ethernet Linux Driver
+
+ The AX88180 Ethernet controller is a high performance and highly
+ integrated local CPU bus Ethernet controller with embedded 40K bytes
+ SRAM and supports both 16-bit and 32-bit SRAM-Like interfaces for any
+ embedded systems.
+ The AX88180 is a single chip 10/100/1000Mbps Gigabit Ethernet
+ controller that supports both MII and RGMII interfaces and is
+ compliant to IEEE 802.3, IEEE 802.3u and IEEE 802.3z standards.
+
+ Please visit ASIX's web site (http://www.asix.com.tw) for more
+ details.
+
+ Module Name : ax88180.c
+ Date : 2008-07-01
+ History
+ 09/06/2006 : New release for AX88180 US2 chip.
+ 07/01/2008 : Fix up the coding style and using functions
+ instead of most macros
+ ========================================================================
+*/
+#include <common.h>
+#include <command.h>
+#include <net.h>
+
+#include "ax88180.h"
+
+#ifdef CONFIG_DRIVER_AX88180
+
+/*
+===========================================================================
+<<<<<< Local SubProgram Declaration >>>>>>
+===========================================================================
+*/
+static void ax88180_rx_handler (void);
+static int ax88180_PHY_initial (void);
+static void ax88180_meida_config (void);
+static unsigned long get_CicadaPHY_meida_mode (void);
+static unsigned long get_MarvellPHY_meida_mode (void);
+static unsigned short ax88180_mdio_read (unsigned long phyaddr,
+ unsigned long regaddr);
+static void ax88180_mdio_write (unsigned long phyaddr,
+ unsigned long regaddr,
+ unsigned short regdata);
+
+/*
+===========================================================================
+<<<<<< Declare Macro/Structure Definition >>>>>>
+===========================================================================
+*/
+typedef enum _AX88180_LINK_STATE {
+ INS_LINK_DOWN,
+ INS_LINK_UP,
+ INS_LINK_UNKNOWN
+} AX88180_LINK_STATE;
+
+typedef struct _AX88180_PRIVATE {
+ unsigned long PhyAddr;
+ unsigned long PhyID0;
+ unsigned long FirstTxDesc;
+ unsigned long NextTxDesc;
+ unsigned long rxbuf_overflow_count;
+ AX88180_LINK_STATE LinkState;
+} AX88180_PRIVATE;
+
+AX88180_PRIVATE axlocal;
+
+#if (DEBUG_FLAGS & DEBUG_MSG)
+static inline void ax88180_disp_all_reg (void)
+{
+ unsigned long tmpval;
+ int i;
+ PRINTK (DEBUG_MSG, "ax88180: AX88180 MAC Registers:\n");
+ for (i = 0xFC00; i <= 0xFCFF; i += 4) {
+ READ_MACREG (i, tmpval);
+ PRINTK (DEBUG_MSG, "0x%04x=0x%08lx ", i, tmpval);
+ if ((i & 0xF) == 0xC)
+ PRINTK (DEBUG_MSG, "\n");
+ }
+ PRINTK (DEBUG_MSG, "\n");
+}
+
+static inline void ax88180_disp_phy_reg (void)
+{
+ unsigned long tmpval;
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, BMCR);
+ PRINTK (DEBUG_MSG, "BMCR=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, BMSR);
+ PRINTK (DEBUG_MSG, "BMSR=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, PHYIDR0);
+ PRINTK (DEBUG_MSG, "PHYIDR0=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, PHYIDR1);
+ PRINTK (DEBUG_MSG, "PHYIDR1=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, ANAR);
+ PRINTK (DEBUG_MSG, "ANAR=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, ANLPAR);
+ PRINTK (DEBUG_MSG, "ANLPAR=0x%04x \n", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, ANER);
+ PRINTK (DEBUG_MSG, "ANER=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, AUX_1000_CTRL);
+ PRINTK (DEBUG_MSG, "1G_CTRL=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, AUX_1000_STATUS);
+ PRINTK (DEBUG_MSG, "1G_STATUS=0x%04x \n", (unsigned int)tmpval);
+ if (axlocal.PhyID0 == MARVELL_88E1111_PHYIDR0) {
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, M88_SSR);
+ PRINTK (DEBUG_MSG, "M88_SSR=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, M88_IER);
+ PRINTK (DEBUG_MSG, "M88_IER=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, M88_ISR);
+ PRINTK (DEBUG_MSG, "M88_ISR=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, M88_EXT_SCR);
+ PRINTK (DEBUG_MSG, "M88_EXT_SCR=0x%04x ",
+ (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, M88_EXT_SSR);
+ PRINTK (DEBUG_MSG, "M88_EXT_SSR=0x%04x \n",
+ (unsigned int)tmpval);
+ } else if (axlocal.PhyID0 == CICADA_CIS8201_PHYIDR0) {
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, CIS_IMR);
+ PRINTK (DEBUG_MSG, "CIS_IMR=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr, CIS_ISR);
+ PRINTK (DEBUG_MSG, "CIS_ISR=0x%04x ", (unsigned int)tmpval);
+ tmpval = ax88180_mdio_read (axlocal.PhyAddr,
+ CIS_AUX_CTRL_STATUS);
+ PRINTK (DEBUG_MSG, "CIS_AUX=0x%04x \n",
+ (unsigned int)tmpval);
+ }
+ READ_MACREG (RXCFG, tmpval);
+ PRINTK (DEBUG_MSG, "RXCFG=0x%08lx ", tmpval);
+ READ_MACREG (MACCFG0, tmpval);
+ PRINTK (DEBUG_MSG, "MACCFG0=0x%08lx ", tmpval);
+ READ_MACREG (MACCFG1, tmpval);
+ PRINTK (DEBUG_MSG, "MACCFG1=0x%08lx ", tmpval);
+ READ_MACREG (MACCFG2, tmpval);
+ PRINTK (DEBUG_MSG, "MACCFG2=0x%08lx \n\n", tmpval);
+}
+#else
+static inline void ax88180_disp_all_reg (void) {}
+static inline void ax88180_disp_phy_reg (void) {}
+#endif
+
+/*
+===========================================================================
+<<<<<< Local SubProgram Bodies >>>>>>
+===========================================================================
+*/
+static int
+ax88180_mdio_check_complete (void)
+{
+ int us_cnt = 10000;
+ unsigned long tmpval;
+
+ /* MDIO read/write should not take more than 10 ms */
+ while (--us_cnt) {
+ READ_MACREG (MDIOCTRL, tmpval);
+ if (((tmpval & READ_PHY) == 0) && ((tmpval & WRITE_PHY) == 0))
+ break;
+ }
+
+ return us_cnt;
+}
+
+static unsigned short
+ax88180_mdio_read (unsigned long phyaddr, unsigned long regaddr)
+{
+ unsigned long tmpval = 0;
+
+ WRITE_MACREG (MDIOCTRL, READ_PHY | (regaddr << 8) | phyaddr);
+
+ if (ax88180_mdio_check_complete ())
+ READ_MACREG (MDIODP, tmpval);
+ else
+ printf("Failed to read PHY register!\n");
+ return (unsigned short)(tmpval & 0xFFFF);
+}
+
+static void
+ax88180_mdio_write (unsigned long phyaddr, unsigned long regaddr,
+ unsigned short regdata)
+{
+ WRITE_MACREG (MDIODP, regdata);
+ WRITE_MACREG (MDIOCTRL, WRITE_PHY | (regaddr << 8) | phyaddr);
+
+ if(!ax88180_mdio_check_complete ())
+ printf("Failed to write PHY register!\n");
+}
+
+static int ax88180_phy_reset (void)
+{
+ unsigned short delay_cnt = 500;
+
+ ax88180_mdio_write (axlocal.PhyAddr, BMCR, PHY_RESET | AUTONEG_EN);
+
+ /* Wait for the reset to complete, or time out (500 ms) */
+ while (ax88180_mdio_read (axlocal.PhyAddr, BMCR) & PHY_RESET) {
+ udelay (1000);
+ if (--delay_cnt == 0) {
+ printf("Failed to reset PHY!\n");
+ return -1;
+ }
+ }
+
+ return 0;
+}
+
+static void ax88180_mac_reset (void)
+{
+ unsigned long tmpval;
+
+ WRITE_MACREG (MISC, MISC_RESET_MAC);
+ READ_MACREG (MISC, tmpval);
+ WRITE_MACREG (MISC, MISC_NORMAL);
+ WRITE_MACREG (RXINDICATOR, DEFAULT_RXINDICATOR);
+ WRITE_MACREG (TXCMD, DEFAULT_TXCMD);
+ WRITE_MACREG (TXBS, DEFAULT_TXBS);
+ WRITE_MACREG (TXDES0, DEFAULT_TXDES0);
+ WRITE_MACREG (TXDES1, DEFAULT_TXDES1);
+ WRITE_MACREG (TXDES2, DEFAULT_TXDES2);
+ WRITE_MACREG (TXDES3, DEFAULT_TXDES3);
+ WRITE_MACREG (TXCFG, DEFAULT_TXCFG);
+ WRITE_MACREG (MACCFG2, DEFAULT_MACCFG2);
+ WRITE_MACREG (MACCFG3, DEFAULT_MACCFG3);
+ WRITE_MACREG (TXLEN, DEFAULT_TXLEN);
+ WRITE_MACREG (RXBTHD0, DEFAULT_RXBTHD0);
+ WRITE_MACREG (RXBTHD1, DEFAULT_RXBTHD1);
+ WRITE_MACREG (RXFULTHD, DEFAULT_RXFULTHD);
+ WRITE_MACREG (DOGTHD0, DEFAULT_DOGTHD0);
+ WRITE_MACREG (DOGTHD1, DEFAULT_DOGTHD1);
+}
+
+static int ax88180_poll_tx_complete (void)
+{
+ unsigned long tmp_data, txbs_txdp;
+ int TimeOutCnt = 10000;
+
+ txbs_txdp = 1 << axlocal.NextTxDesc;
+
+ while (TimeOutCnt--) {
+
+ READ_MACREG (TXBS, tmp_data);
+ if ((tmp_data & txbs_txdp) == 0)
+ break;
+
+ udelay (100);
+ }
+
+ if (TimeOutCnt)
+ return 0;
+ else
+ return -TimeOutCnt;
+}
+
+static void ax88180_rx_handler (void)
+{
+ unsigned char *rxdata;
+ unsigned long tmp_data;
+ unsigned long rx_packet_len;
+ unsigned int data_size;
+ unsigned int dword_count, byte_count;
+ unsigned long rxcurt_ptr, rxbound_ptr, next_ptr;
+ int i;
+ int j;
+
+ READ_MACREG (RXCURT, rxcurt_ptr);
+ READ_MACREG (RXBOUND, rxbound_ptr);
+ next_ptr = (rxbound_ptr + 1) & RX_PAGE_NUM_MASK;
+
+ PRINTK (RX_MSG, "ax88180: RX original RXBOUND=0x%08lx,"
+ " RXCURT=0x%08lx\n", rxbound_ptr, rxcurt_ptr);
+
+ while (next_ptr != rxcurt_ptr) {
+ WRITE_MACREG (RXINDICATOR, RX_START_READ);
+ READ_RXBUF (rx_packet_len);
+ if ((rx_packet_len == 0) || (rx_packet_len > MAX_RX_SIZE)) {
+ WRITE_MACREG (RXINDICATOR, RX_STOP_READ);
+ ax88180_mac_reset ();
+ printf ("ax88180: Invalid Rx packet length!"
+ " (len=0x%08lx)\n", rx_packet_len);
+
+ printf ("ax88180: RX RXBOUND=0x%08lx,"
+ "RXCURT=0x%08lx\n", rxbound_ptr, rxcurt_ptr);
+ return;
+ }
+ data_size = (unsigned int)rx_packet_len;
+ rxbound_ptr += (((data_size + 0xF) & 0xFFF0) >> 4) + 1;
+ rxbound_ptr &= RX_PAGE_NUM_MASK;
+
+ rxdata = (unsigned char *)NetRxPackets[0];
+
+#if defined (CONFIG_DRIVER_AX88180_16BIT)
+ dword_count = data_size >> 1;
+ byte_count = data_size & 0x1;
+#else
+ dword_count = data_size >> 2;
+ byte_count = data_size & 0x3;
+#endif
+ for (i = 0; i < dword_count; i++) {
+ READ_RXBUF (tmp_data);
+#if defined (CONFIG_DRIVER_AX88180_16BIT)
+ *((unsigned short *)rxdata + i) = tmp_data;
+#else
+ *((unsigned long *)rxdata + i) = tmp_data;
+#endif
+ }
+ if (byte_count != 0) {
+ READ_RXBUF (tmp_data);
+ for (j = 0; j < byte_count; j++) {
+ *(rxdata + (dword_count * 4) + j) =
+ (unsigned char)(tmp_data >> (j * 8));
+ }
+ }
+
+ WRITE_MACREG (RXINDICATOR, RX_STOP_READ);
+
+ /* Pass the packet up to the protocol layers. */
+ NetReceive (NetRxPackets[0], data_size);
+
+ WRITE_MACREG (RXBOUND, rxbound_ptr);
+
+ READ_MACREG (RXCURT, rxcurt_ptr);
+ READ_MACREG (RXBOUND, rxbound_ptr);
+ next_ptr = (rxbound_ptr + 1) & RX_PAGE_NUM_MASK;
+
+ PRINTK (RX_MSG, "ax88180: RX updated RXBOUND=0x%08lx,"
+ "RXCURT=0x%08lx\n", rxbound_ptr, rxcurt_ptr);
+ }
+
+ if (axlocal.rxbuf_overflow_count > 0)
+ axlocal.rxbuf_overflow_count--;
+
+ return;
+}
+
+static int ax88180_PHY_initial (void)
+{
+ unsigned long tmp_regval;
+ int i;
+ int ret;
+
+ /* Check avaliable PHY chipset */
+ axlocal.PhyAddr = MARVELL_88E1111_PHYADDR;
+ axlocal.PhyID0 = ax88180_mdio_read (axlocal.PhyAddr, PHYIDR0);
+
+ if (axlocal.PhyID0 == MARVELL_88E1111_PHYIDR0) {
+ PRINTK (DEBUG_MSG, "ax88180: Found Marvell 88E1111 PHY."
+ " (PHY Addr=0x%lx)\n", axlocal.PhyAddr);
+ tmp_regval = ax88180_mdio_read (axlocal.PhyAddr, M88_EXT_SSR);
+ if ((tmp_regval & HWCFG_MODE_MASK) == RGMII_COPPER_MODE) {
+ ax88180_mdio_write (axlocal.PhyAddr, M88_EXT_SCR,
+ DEFAULT_EXT_SCR);
+ if ((ret = ax88180_phy_reset ()) < 0)
+ return ret;
+ ax88180_mdio_write (axlocal.PhyAddr, M88_IER,
+ LINK_CHANGE_INT);
+ }
+ } else {
+ axlocal.PhyAddr = CICADA_CIS8201_PHYADDR;
+ axlocal.PhyID0 = ax88180_mdio_read (axlocal.PhyAddr, PHYIDR0);
+ if (axlocal.PhyID0 == CICADA_CIS8201_PHYIDR0) {
+ PRINTK (DEBUG_MSG, "ax88180: Found CICADA CIS8201 PHY"
+ " chipset. (PHY Addr=0x%lx)\n",
+ axlocal.PhyAddr);
+ ax88180_mdio_write (axlocal.PhyAddr, CIS_IMR,
+ (CIS_INT_ENABLE | LINK_CHANGE_INT));
+
+ /*
+ Set CIS_SMI_PRIORITY bit before force the media mode
+ */
+ tmp_regval = ax88180_mdio_read (axlocal.PhyAddr,
+ CIS_AUX_CTRL_STATUS);
+ tmp_regval &= ~CIS_SMI_PRIORITY;
+ ax88180_mdio_write (axlocal.PhyAddr,
+ CIS_AUX_CTRL_STATUS, tmp_regval);
+ } else {
+ printf ("ax88180: Unknown PHY chipset!!\n");
+ return -1;
+ }
+ }
+
+ /* Waiting for auto-negotiation complete. */
+ /* This may take up to 5 seconds */
+ PRINTK (DEBUG_MSG,
+ "ax88180: Waiting for auto-negotiation completion......\n");
+ for (i = 0; i < 5000; i++) {
+ tmp_regval = ax88180_mdio_read (axlocal.PhyAddr, BMSR);
+ if (tmp_regval & AUTONEG_COMPLETE) {
+ break;
+ }
+ udelay (1000);
+ }
+
+ return 0;
+}
+
+static void ax88180_meida_config (void)
+{
+ unsigned long bmcr_val, bmsr_val;
+ unsigned long rxcfg_val, maccfg0_val, maccfg1_val;
+ unsigned long RealMediaMode;
+ int i;
+
+ /* Waiting 200 msecs for PHY link stable */
+ for (i = 0; i < 200; i++) {
+ bmsr_val = ax88180_mdio_read (axlocal.PhyAddr, BMSR);
+ if (bmsr_val & LINKOK) {
+ break;
+ }
+ udelay (1000);
+ }
+
+ bmsr_val = ax88180_mdio_read (axlocal.PhyAddr, BMSR);
+ PRINTK (DEBUG_MSG, "ax88180: BMSR=0x%04x\n", (unsigned int)bmsr_val);
+
+ if (bmsr_val & LINKOK) {
+ bmcr_val = ax88180_mdio_read (axlocal.PhyAddr, BMCR);
+ if (bmcr_val & AUTONEG_EN) {
+ /* Waiting for Auto-negotiation completion */
+ /* This may take up to 5 seconds */
+ PRINTK (DEBUG_MSG, "ax88180: Auto-negotiation is "
+ "enabled. Waiting for NWay completion..\n");
+ for (i = 0; i < 5000; i++) {
+ bmsr_val = ax88180_mdio_read (axlocal.PhyAddr,
+ BMSR);
+ if (bmsr_val & AUTONEG_COMPLETE) {
+ break;
+ }
+ udelay (1000);
+ }
+ } else
+ PRINTK (DEBUG_MSG,
+ "ax88180: Auto-negotiation is disabled.\n");
+
+ PRINTK (DEBUG_MSG, "ax88180: BMCR=0x%04x, BMSR=0x%04x\n",
+ (unsigned int)bmcr_val, (unsigned int)bmsr_val);
+
+ /* Get real media mode here */
+ if (axlocal.PhyID0 == MARVELL_88E1111_PHYIDR0) {
+ RealMediaMode = get_MarvellPHY_meida_mode ();
+ } else if (axlocal.PhyID0 == CICADA_CIS8201_PHYIDR0) {
+ RealMediaMode = get_CicadaPHY_meida_mode ();
+ } else {
+ RealMediaMode = MEDIA_1000FULL;
+ }
+
+ switch (RealMediaMode) {
+ default:
+ case MEDIA_1000FULL:
+ PRINTK (DEBUG_MSG,
+ "ax88180: 1000Mbps Full-duplex mode.\n");
+ rxcfg_val = RXFLOW_ENABLE | DEFAULT_RXCFG;
+ maccfg0_val = TXFLOW_ENABLE | DEFAULT_MACCFG0;
+ maccfg1_val = GIGA_MODE_EN | RXFLOW_EN |
+ FULLDUPLEX | DEFAULT_MACCFG1;
+ break;
+
+ case MEDIA_1000HALF:
+ PRINTK (DEBUG_MSG,
+ "ax88180: 1000Mbps Half-duplex mode.\n");
+ rxcfg_val = DEFAULT_RXCFG;
+ maccfg0_val = DEFAULT_MACCFG0;
+ maccfg1_val = GIGA_MODE_EN | DEFAULT_MACCFG1;
+ break;
+
+ case MEDIA_100FULL:
+ PRINTK (DEBUG_MSG,
+ "ax88180: 100Mbps Full-duplex mode.\n");
+ rxcfg_val = RXFLOW_ENABLE | DEFAULT_RXCFG;
+ maccfg0_val = SPEED100 | TXFLOW_ENABLE
+ | DEFAULT_MACCFG0;
+ maccfg1_val = RXFLOW_EN | FULLDUPLEX
+ | DEFAULT_MACCFG1;
+ break;
+
+ case MEDIA_100HALF:
+ PRINTK (DEBUG_MSG,
+ "ax88180: 100Mbps Half-duplex mode.\n");
+ rxcfg_val = DEFAULT_RXCFG;
+ maccfg0_val = SPEED100 | DEFAULT_MACCFG0;
+ maccfg1_val = DEFAULT_MACCFG1;
+ break;
+
+ case MEDIA_10FULL:
+ PRINTK (DEBUG_MSG,
+ "ax88180: 10Mbps Full-duplex mode.\n");
+ rxcfg_val = RXFLOW_ENABLE | DEFAULT_RXCFG;
+ maccfg0_val = TXFLOW_ENABLE | DEFAULT_MACCFG0;
+ maccfg1_val = RXFLOW_EN | FULLDUPLEX
+ | DEFAULT_MACCFG1;
+ break;
+
+ case MEDIA_10HALF:
+ PRINTK (DEBUG_MSG,
+ "ax88180: 10Mbps Half-duplex mode.\n");
+ rxcfg_val = DEFAULT_RXCFG;
+ maccfg0_val = DEFAULT_MACCFG0;
+ maccfg1_val = DEFAULT_MACCFG1;
+ break;
+ }
+
+ axlocal.LinkState = INS_LINK_UP;
+ } else {
+ rxcfg_val = DEFAULT_RXCFG;
+ maccfg0_val = DEFAULT_MACCFG0;
+ maccfg1_val = DEFAULT_MACCFG1;
+
+ axlocal.LinkState = INS_LINK_DOWN;
+ }
+
+ WRITE_MACREG (RXCFG, rxcfg_val);
+ WRITE_MACREG (MACCFG0, maccfg0_val);
+ WRITE_MACREG (MACCFG1, maccfg1_val);
+
+ return;
+}
+
+static unsigned long
+get_MarvellPHY_meida_mode (void)
+{
+ unsigned long m88_ssr;
+ unsigned long MediaMode;
+
+ m88_ssr = ax88180_mdio_read (axlocal.PhyAddr, M88_SSR);
+ switch (m88_ssr & SSR_MEDIA_MASK) {
+ default:
+ case SSR_1000FULL:
+ MediaMode = MEDIA_1000FULL;
+ break;
+ case SSR_1000HALF:
+ MediaMode = MEDIA_1000HALF;
+ break;
+ case SSR_100FULL:
+ MediaMode = MEDIA_100FULL;
+ break;
+ case SSR_100HALF:
+ MediaMode = MEDIA_100HALF;
+ break;
+ case SSR_10FULL:
+ MediaMode = MEDIA_10FULL;
+ break;
+ case SSR_10HALF:
+ MediaMode = MEDIA_10HALF;
+ break;
+ }
+
+ return MediaMode;
+}
+
+static unsigned long
+get_CicadaPHY_meida_mode (void)
+{
+ unsigned long tmp_regval;
+ unsigned long MediaMode;
+
+ tmp_regval = ax88180_mdio_read (axlocal.PhyAddr,
+ CIS_AUX_CTRL_STATUS);
+ switch (tmp_regval & CIS_MEDIA_MASK) {
+ default:
+ case CIS_1000FULL:
+ MediaMode = MEDIA_1000FULL;
+ break;
+ case CIS_1000HALF:
+ MediaMode = MEDIA_1000HALF;
+ break;
+ case CIS_100FULL:
+ MediaMode = MEDIA_100FULL;
+ break;
+ case CIS_100HALF:
+ MediaMode = MEDIA_100HALF;
+ break;
+ case CIS_10FULL:
+ MediaMode = MEDIA_10FULL;
+ break;
+ case CIS_10HALF:
+ MediaMode = MEDIA_10HALF;
+ break;
+ }
+
+ return MediaMode;
+}
+
+/*
+===========================================================================
+<<<<<< Exported SubProgram Bodies >>>>>>
+===========================================================================
+*/
+void eth_halt (void)
+{
+ /* Disable AX88180 TX/RX functions */
+ WRITE_MACREG (CMD, WAKEMOD);
+}
+
+int eth_init (bd_t *bd)
+{
+ unsigned long tmp_regval;
+ unsigned long macid0_val, macid1_val, macid2_val;
+ int ret, i;
+
+#if defined (CONFIG_DRIVER_AX88180_16BIT)
+ *((volatile unsigned short *)(AX88180_BASE + 6)) = (START_BASE >> 8);
+ *((volatile unsigned short *)AX88180_BASE ) = 1;
+#endif
+ memset (&axlocal, 0, sizeof (AX88180_PRIVATE));
+
+ ax88180_mac_reset ();
+
+ /* Disable AX88180 interrupt */
+ WRITE_MACREG (IMR, CLEAR_IMR);
+
+ /* Disable AX88180 TX/RX functions */
+ WRITE_MACREG (CMD, WAKEMOD);
+
+ axlocal.LinkState = INS_LINK_UNKNOWN;
+
+ /* Initial PHY registers */
+ if ((ret = ax88180_PHY_initial ()) < 0)
+ return ret;
+ ax88180_meida_config ();
+
+ /* Reload MAC address from EEPROM */
+ WRITE_MACREG (PROMCTRL, RELOAD_EEPROM);
+
+ /* Waiting for reload eeprom completion */
+ for (i = 0; i < 500; i++) {
+ READ_MACREG (PROMCTRL, tmp_regval);
+ if ((tmp_regval & RELOAD_EEPROM) == 0)
+ break;
+ udelay (1000);
+ }
+
+ /* Get MAC addresses */
+ READ_MACREG (MACID0, macid0_val);
+ READ_MACREG (MACID1, macid1_val);
+ READ_MACREG (MACID2, macid2_val);
+
+ bd->bi_enetaddr[0] = (unsigned char)macid0_val;
+ bd->bi_enetaddr[1] = (unsigned char)(macid0_val >> 8);
+ bd->bi_enetaddr[2] = (unsigned char)macid1_val;
+ bd->bi_enetaddr[3] = (unsigned char)(macid1_val >> 8);
+ bd->bi_enetaddr[4] = (unsigned char)macid2_val;
+ bd->bi_enetaddr[5] = (unsigned char)(macid2_val >> 8);
+
+ if (((macid0_val | macid1_val | macid2_val) == 0) ||
+ (bd->bi_enetaddr[0] & 0x01)) {
+ /* try to get MAC address from environment */
+ u8 i;
+ char *s, *e;
+ unsigned short tmp16;
+
+ s = getenv ("ethaddr");
+ for (i = 0; i < 6; ++i) {
+ bd->bi_enetaddr[i] = s ?
+ simple_strtoul (s, &e, 16) : 0;
+ if (s)
+ s = (*e) ? e + 1 : e;
+ }
+
+ tmp16 = bd->bi_enetaddr[1];
+ macid0_val = (tmp16 << 8) | bd->bi_enetaddr[0];
+ tmp16 = bd->bi_enetaddr[3];
+ macid1_val = (tmp16 << 8) | bd->bi_enetaddr[2];
+ tmp16 = bd->bi_enetaddr[5];
+ macid2_val = (tmp16 << 8) | bd->bi_enetaddr[4];
+
+ WRITE_MACREG (MACID0, macid0_val);
+ WRITE_MACREG (MACID1, macid1_val);
+ WRITE_MACREG (MACID2, macid2_val);
+ }
+
+ WRITE_MACREG (RXFILTER, DEFAULT_RXFILTER);
+
+ /* Initial variables here */
+ axlocal.FirstTxDesc = TXDP0;
+ axlocal.NextTxDesc = TXDP0;
+ axlocal.rxbuf_overflow_count = 0;
+
+ ax88180_disp_all_reg ();
+
+ /* Check if there is any invalid interrupt status. If yes, clear it. */
+ READ_MACREG (ISR, tmp_regval);
+ PRINTK (DEBUG_MSG, "ax88180: The interrupt status = 0x%08lx\n",
+ tmp_regval);
+ if (tmp_regval)
+ WRITE_MACREG (ISR, tmp_regval);
+
+ /* Start AX88180 TX/RX functions */
+ WRITE_MACREG (CMD, RXEN | TXEN | WAKEMOD);
+
+ return 0;
+}
+
+/* Get a data block via Ethernet */
+int eth_rx (void)
+{
+ unsigned long ISR_Status;
+ unsigned long rxcurt_ptr, rxbound_ptr;
+ unsigned long tmp_regval;
+
+ /* Read and check interrupt status here...... */
+ READ_MACREG (ISR, ISR_Status);
+
+ while (ISR_Status) {
+ /* Clear the interrupt status */
+ WRITE_MACREG (ISR, ISR_Status);
+
+ PRINTK (INT_MSG,
+ "\nax88180: The interrupt status = 0x%08lx\n",
+ ISR_Status);
+
+ if (ISR_Status & ISR_PHY) {
+ /* Read ISR register once to clear PHY interrupt bit */
+ tmp_regval = ax88180_mdio_read (axlocal.PhyAddr,
+ M88_ISR);
+ ax88180_meida_config ();
+ ax88180_disp_phy_reg ();
+ }
+
+ if (ISR_Status & ISR_RXBUFFOVR) {
+ axlocal.rxbuf_overflow_count++;
+ READ_MACREG (RXCURT, rxcurt_ptr);
+ READ_MACREG (RXBOUND, rxbound_ptr);
+ PRINTK (INT_MSG, "ax88180: RX Buffer overflow! "
+ "count=%d, RXBOUND=0x%08lx, RXCURT=0x%08lx\n",
+ (int)axlocal.rxbuf_overflow_count, rxbound_ptr,
+ rxcurt_ptr);
+
+ if (axlocal.rxbuf_overflow_count > 10) {
+ ax88180_mac_reset ();
+ axlocal.FirstTxDesc = TXDP0;
+ axlocal.NextTxDesc = TXDP0;
+ axlocal.rxbuf_overflow_count = 0;
+ }
+ }
+
+ if (ISR_Status & ISR_RX) {
+ ax88180_rx_handler ();
+ }
+
+ /* Read and check interrupt status here...... */
+ READ_MACREG (ISR, ISR_Status);
+ }
+
+ return 0;
+}
+
+/* Send a data block via Ethernet. */
+int eth_send (volatile void *packet, int length)
+{
+ volatile unsigned char *txdata;
+ unsigned long TXDES_addr;
+ unsigned long txcmd_txdp, txbs_txdp;
+ unsigned long tmp_data;
+ int i;
+
+ if (axlocal.LinkState != INS_LINK_UP) {
+ return 0;
+ }
+
+ txdata = (volatile unsigned char *)packet;
+
+ axlocal.FirstTxDesc = axlocal.NextTxDesc;
+ txbs_txdp = 1 << axlocal.FirstTxDesc;
+
+ READ_MACREG (TXBS, tmp_data);
+ READ_MACREG (TXBS, tmp_data);
+ PRINTK (TX_MSG, "ax88180: Checking available TXDP (TXBS=0x%08lx)\n",
+ tmp_data);
+
+ /* check the available transmit descriptor */
+ if (tmp_data & txbs_txdp) {
+ /* we should never get here. */
+ /* we are running out of resource */
+ return 0;
+ }
+
+ PRINTK (TX_MSG, "ax88180: TXDP%d is available, i=%d\n",
+ (int)axlocal.FirstTxDesc, i);
+
+ txcmd_txdp = axlocal.FirstTxDesc << 13;
+ TXDES_addr = TXDES0 + (axlocal.FirstTxDesc << 2);
+
+ WRITE_MACREG (TXCMD, txcmd_txdp | length | TX_START_WRITE);
+
+#if defined (CONFIG_DRIVER_AX88180_16BIT)
+ for (i = 0; i < length; i += 2) {
+ tmp_data =
+ (unsigned short)*(txdata + i) +
+ (unsigned short)(*(txdata + i + 1) << 8);
+ WRITE_TXBUF (tmp_data);
+ }
+#else
+ for (i = 0; i < length; i += 4) {
+ tmp_data =
+ (unsigned long)*(txdata + i) +
+ (unsigned long)(*(txdata + i + 1) << 8) +
+ (unsigned long)(*(txdata + i + 2) << 16) +
+ (unsigned long)(*(txdata + i + 3) << 24);
+ WRITE_TXBUF (tmp_data);
+ }
+#endif
+
+ WRITE_MACREG (TXCMD, txcmd_txdp | length);
+ WRITE_MACREG (TXBS, txbs_txdp);
+ WRITE_MACREG (TXDES_addr, TXDPx_ENABLE | length);
+
+ axlocal.NextTxDesc = (axlocal.NextTxDesc + 1) & TXDP_MASK;
+
+ /*
+ Check the available transmit descriptor, if we had exhausted all
+ transmit descriptor ,then we have to wait for at least one free
+ descriptor
+ */
+ txbs_txdp = 1 << axlocal.NextTxDesc;
+ READ_MACREG (TXBS, tmp_data);
+ if (tmp_data & txbs_txdp) {
+ if (ax88180_poll_tx_complete () < 0) {
+ ax88180_mac_reset ();
+ axlocal.FirstTxDesc = TXDP0;
+ axlocal.NextTxDesc = TXDP0;
+ printf ("ax88180: Transmit time out occurred!\n");
+ }
+ }
+
+ return 0;
+}
+#endif /* CONFIG_DRIVER_AX88180 */
+
diff --git a/drivers/net/ax88180.h b/drivers/net/ax88180.h
new file mode 100644
index 0000000..ae4b1b3
--- /dev/null
+++ b/drivers/net/ax88180.h
@@ -0,0 +1,415 @@
+/* ax88180.h: ASIX AX88180 Non-PCI Gigabit Ethernet u-boot driver */
+/*
+ *
+ * This program is free software; you can distribute it and/or modify it
+ * under the terms of the GNU General Public License (Version 2) as
+ * published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope 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 <asm/types.h>
+#include <config.h>
+
+#ifdef CONFIG_DRIVER_AX88180
+
+#define ENABLE_JUMBO 1
+#define DISABLE_JUMBO 0
+
+#define ENABLE_BURST 1
+#define DISABLE_BURST 0
+
+#define NORMAL_RX_MODE 0
+#define RX_LOOPBACK_MODE 1
+#define RX_INIFINIT_LOOP_MODE 2
+#define TX_INIFINIT_LOOP_MODE 3
+
+#define DEFAULT_ETH_MTU 1500
+
+/* Jumbo packet size 4086 bytes included 4 bytes CRC*/
+#define MAX_JUMBO_MTU 4072
+
+/* Max Tx Jumbo size 4086 bytes included 4 bytes CRC */
+#define MAX_TX_JUMBO_SIZE 4086
+
+/* Max Rx Jumbo size is 15K Bytes */
+#define MAX_RX_SIZE 0x3C00
+
+#define MARVELL_88E1111_PHYADDR 0x18
+#define MARVELL_88E1111_PHYIDR0 0x0141
+
+#define CICADA_CIS8201_PHYADDR 0x01
+#define CICADA_CIS8201_PHYIDR0 0x000F
+
+#define MEDIA_AUTO 0
+#define MEDIA_1000FULL 1
+#define MEDIA_1000HALF 2
+#define MEDIA_100FULL 3
+#define MEDIA_100HALF 4
+#define MEDIA_10FULL 5
+#define MEDIA_10HALF 6
+
+#define AUTO_MEDIA 0
+#define FORCE_MEDIA 1
+
+#define TXDP_MASK 3
+#define TXDP0 0
+#define TXDP1 1
+#define TXDP2 2
+#define TXDP3 3
+
+#define CMD_MAP_SIZE 0x100
+
+#if defined (CONFIG_DRIVER_AX88180_16BIT)
+ #define AX88180_MEMORY_SIZE 0x00004000
+ #define START_BASE 0x1000
+
+ #define RX_BUF_SIZE 0x1000
+ #define TX_BUF_SIZE 0x0F00
+
+ #define TX_BASE START_BASE
+ #define CMD_BASE (TX_BASE + TX_BUF_SIZE)
+ #define RX_BASE (CMD_BASE + CMD_MAP_SIZE)
+#else
+ #define AX88180_MEMORY_SIZE 0x00010000
+
+ #define RX_BUF_SIZE 0x8000
+ #define TX_BUF_SIZE 0x7C00
+
+ #define RX_BASE 0x0000
+ #define TX_BASE (RX_BASE + RX_BUF_SIZE)
+ #define CMD_BASE (TX_BASE + TX_BUF_SIZE)
+#endif
+
+/* AX88180 Memory Mapping Definition */
+#define RXBUFFER_START RX_BASE
+ #define RX_PACKET_LEN_OFFSET 0
+ #define RX_PAGE_NUM_MASK 0x7FF //RX pages 0~7FFh
+#define TXBUFFER_START TX_BASE
+
+/* AX88180 MAC Register Definition */
+#define CMD (CMD_BASE + 0x0000)
+ #define WAKEMOD 0x00000001
+ #define TXEN 0x00000100
+ #define RXEN 0x00000200
+ #define DEFAULT_CMD WAKEMOD
+#define IMR (CMD_BASE + 0x0004)
+ #define IMR_RXBUFFOVR 0x00000001
+ #define IMR_WATCHDOG 0x00000002
+ #define IMR_TX 0x00000008
+ #define IMR_RX 0x00000010
+ #define IMR_PHY 0x00000020
+ #define CLEAR_IMR 0x00000000
+ #define DEFAULT_IMR (IMR_PHY | IMR_RX | IMR_TX |\
+ IMR_RXBUFFOVR | IMR_WATCHDOG)
+#define ISR (CMD_BASE + 0x0008)
+ #define ISR_RXBUFFOVR 0x00000001
+ #define ISR_WATCHDOG 0x00000002
+ #define ISR_TX 0x00000008
+ #define ISR_RX 0x00000010
+ #define ISR_PHY 0x00000020
+#define TXCFG (CMD_BASE + 0x0010)
+ #define AUTOPAD_CRC 0x00000050
+ #define DEFAULT_TXCFG AUTOPAD_CRC
+#define TXCMD (CMD_BASE + 0x0014)
+ #define TXCMD_TXDP_MASK 0x00006000
+ #define TXCMD_TXDP0 0x00000000
+ #define TXCMD_TXDP1 0x00002000
+ #define TXCMD_TXDP2 0x00004000
+ #define TXCMD_TXDP3 0x00006000
+ #define TX_START_WRITE 0x00008000
+ #define TX_STOP_WRITE 0x00000000
+ #define DEFAULT_TXCMD 0x00000000
+#define TXBS (CMD_BASE + 0x0018)
+ #define TXDP0_USED 0x00000001
+ #define TXDP1_USED 0x00000002
+ #define TXDP2_USED 0x00000004
+ #define TXDP3_USED 0x00000008
+ #define DEFAULT_TXBS 0x00000000
+#define TXDES0 (CMD_BASE + 0x0020)
+ #define TXDPx_ENABLE 0x00008000
+ #define TXDPx_LEN_MASK 0x00001FFF
+ #define DEFAULT_TXDES0 0x00000000
+#define TXDES1 (CMD_BASE + 0x0024)
+ #define TXDPx_ENABLE 0x00008000
+ #define TXDPx_LEN_MASK 0x00001FFF
+ #define DEFAULT_TXDES1 0x00000000
+#define TXDES2 (CMD_BASE + 0x0028)
+ #define TXDPx_ENABLE 0x00008000
+ #define TXDPx_LEN_MASK 0x00001FFF
+ #define DEFAULT_TXDES2 0x00000000
+#define TXDES3 (CMD_BASE + 0x002C)
+ #define TXDPx_ENABLE 0x00008000
+ #define TXDPx_LEN_MASK 0x00001FFF
+ #define DEFAULT_TXDES3 0x00000000
+#define RXCFG (CMD_BASE + 0x0030)
+ #define RXBUFF_PROTECT 0x00000001
+ #define RXTCPCRC_CHECK 0x00000010
+ #define RXFLOW_ENABLE 0x00000100
+ #define DEFAULT_RXCFG RXBUFF_PROTECT
+#define RXCURT (CMD_BASE + 0x0034)
+ #define DEFAULT_RXCURT 0x00000000
+#define RXBOUND (CMD_BASE + 0x0038)
+ #define DEFAULT_RXBOUND 0x7FF //RX pages 0~7FFh
+#define MACCFG0 (CMD_BASE + 0x0040)
+ #define MACCFG0_BIT3_0 0x00000007
+ #define IPGT_VAL 0x00000150
+ #define TXFLOW_ENABLE 0x00001000
+ #define SPEED100 0x00008000
+ #define DEFAULT_MACCFG0 (IPGT_VAL | MACCFG0_BIT3_0)
+#define MACCFG1 (CMD_BASE + 0x0044)
+ #define RGMII_EN 0x00000002
+ #define RXFLOW_EN 0x00000020
+ #define FULLDUPLEX 0x00000040
+ #define MAX_JUMBO_LEN_MASK 0x00000780
+ #define RXJUMBO_EN 0x00000800
+ #define GIGA_MODE_EN 0x00001000
+ #define RXCRC_CHECK 0x00002000
+ #define RXPAUSE_DA_CHECK 0x00004000
+
+ #define JUMBO_LEN_4K 0x00000200
+ #define JUMBO_LEN_15K 0x00000780
+ #define DEFAULT_MACCFG1 (RXCRC_CHECK | RXPAUSE_DA_CHECK |\
+ RGMII_EN)
+ #define CICADA_DEFAULT_MACCFG1 (RXCRC_CHECK | RXPAUSE_DA_CHECK)
+#define MACCFG2 (CMD_BASE + 0x0048)
+ #define MACCFG2_BIT15_8 0x00000100
+ #define JAM_LIMIT_MASK 0x000000FC
+ #define DEFAULT_JAM_LIMIT 0x00000064
+ #define DEFAULT_MACCFG2 MACCFG2_BIT15_8
+#define MACCFG3 (CMD_BASE + 0x004C)
+ #define IPGR2_VAL 0x0000000E
+ #define IPGR1_VAL 0x00000600
+ #define NOABORT 0x00008000
+ #define DEFAULT_MACCFG3 (IPGR1_VAL | IPGR2_VAL)
+#define TXPAUT (CMD_BASE + 0x0054)
+ #define DEFAULT_TXPAUT 0x001FE000
+#define RXBTHD0 (CMD_BASE + 0x0058)
+ #define DEFAULT_RXBTHD0 0x00000300
+#define RXBTHD1 (CMD_BASE + 0x005C)
+ #define DEFAULT_RXBTHD1 0x00000600
+#define RXFULTHD (CMD_BASE + 0x0060)
+ #define DEFAULT_RXFULTHD 0x00000100
+#define MISC (CMD_BASE + 0x0068)
+ /* Normal operation mode */
+ #define MISC_NORMAL 0x00000003
+ /* Clear bit 0 to reset MAC */
+ #define MISC_RESET_MAC 0x00000002
+ /* Clear bit 1 to reset PHY */
+ #define MISC_RESET_PHY 0x00000001
+ /* Clear bit 0 and 1 to reset MAC and PHY */
+ #define MISC_RESET_MAC_PHY 0x00000000
+ #define DEFAULT_MISC MISC_NORMAL
+#define MACID0 (CMD_BASE + 0x0070)
+#define MACID1 (CMD_BASE + 0x0074)
+#define MACID2 (CMD_BASE + 0x0078)
+#define TXLEN (CMD_BASE + 0x007C)
+ #define DEFAULT_TXLEN 0x000005FC
+#define RXFILTER (CMD_BASE + 0x0080)
+ #define RX_RXANY 0x00000001
+ #define RX_MULTICAST 0x00000002
+ #define RX_UNICAST 0x00000004
+ #define RX_BROADCAST 0x00000008
+ #define RX_MULTI_HASH 0x00000010
+ #define DISABLE_RXFILTER 0x00000000
+ #define DEFAULT_RXFILTER (RX_BROADCAST + RX_UNICAST)
+#define MDIOCTRL (CMD_BASE + 0x0084)
+ #define PHY_ADDR_MASK 0x0000001F
+ #define REG_ADDR_MASK 0x00001F00
+ #define READ_PHY 0x00004000
+ #define WRITE_PHY 0x00008000
+#define MDIODP (CMD_BASE + 0x0088)
+#define GPIOCTRL (CMD_BASE + 0x008C)
+#define RXINDICATOR (CMD_BASE + 0x0090)
+ #define RX_START_READ 0x00000001
+ #define RX_STOP_READ 0x00000000
+ #define DEFAULT_RXINDICATOR RX_STOP_READ
+#define TXST (CMD_BASE + 0x0094)
+#define MDCCLKPAT (CMD_BASE + 0x00A0)
+#define RXIPCRCCNT (CMD_BASE + 0x00A4)
+#define RXCRCCNT (CMD_BASE + 0x00A8)
+#define TXFAILCNT (CMD_BASE + 0x00AC)
+#define PROMDP (CMD_BASE + 0x00B0)
+#define PROMCTRL (CMD_BASE + 0x00B4)
+ #define RELOAD_EEPROM 0x00000200
+#define MAXRXLEN (CMD_BASE + 0x00B8)
+#define HASHTAB0 (CMD_BASE + 0x00C0)
+#define HASHTAB1 (CMD_BASE + 0x00C4)
+#define HASHTAB2 (CMD_BASE + 0x00C8)
+#define HASHTAB3 (CMD_BASE + 0x00CC)
+#define DOGTHD0 (CMD_BASE + 0x00E0)
+ #define DEFAULT_DOGTHD0 0x0000FFFF
+#define DOGTHD1 (CMD_BASE + 0x00E4)
+ #define START_WATCHDOG_TIMER 0x00008000
+ #define DEFAULT_DOGTHD1 0x00000FFF
+#define SOFTRST (CMD_BASE + 0x00EC)
+ #define SOFTRST_NORMAL 0x00000003
+ #define SOFTRST_RESET_MAC 0x00000002
+
+/* External PHY Register Definition */
+#define BMCR 0x0000
+ #define LINE_SPEED_MSB 0x0040
+ #define DUPLEX_MODE 0x0100
+ #define RESTART_AUTONEG 0x0200
+ #define POWER_DOWN 0x0800
+ #define AUTONEG_EN 0x1000
+ #define LINE_SPEED_LSB 0x2000
+ #define PHY_RESET 0x8000
+
+ #define MEDIAMODE_MASK (LINE_SPEED_MSB | LINE_SPEED_LSB |\
+ DUPLEX_MODE)
+ #define BMCR_SPEED_1000 LINE_SPEED_MSB
+ #define BMCR_SPEED_100 LINE_SPEED_LSB
+ #define BMCR_SPEED_10 0x0000
+
+ #define BMCR_1000FULL (BMCR_SPEED_1000 | DUPLEX_MODE)
+ #define BMCR_100FULL (BMCR_SPEED_100 | DUPLEX_MODE)
+ #define BMCR_100HALF BMCR_SPEED_100
+ #define BMCR_10FULL DUPLEX_MODE
+ #define BMCR_10HALF 0x0000
+#define BMSR 0x0001
+ #define LINKOK 0x0004
+ #define AUTONEG_ENABLE_STS 0x0008
+ #define AUTONEG_COMPLETE 0x0020
+#define PHYIDR0 0x0002
+#define PHYIDR1 0x0003
+#define ANAR 0x0004
+ #define ANAR_PAUSE 0x0400
+ #define ANAR_100FULL 0x0100
+ #define ANAR_100HALF 0x0080
+ #define ANAR_10FULL 0x0040
+ #define ANAR_10HALF 0x0020
+ #define ANAR_8023BIT 0x0001
+#define ANLPAR 0x0005
+#define ANER 0x0006
+#define AUX_1000_CTRL 0x0009
+ #define ENABLE_1000HALF 0x0100
+ #define ENABLE_1000FULL 0x0200
+ #define DEFAULT_AUX_1000_CTRL (ENABLE_1000HALF | ENABLE_1000FULL)
+#define AUX_1000_STATUS 0x000A
+ #define LP_1000HALF 0x0400
+ #define LP_1000FULL 0x0800
+
+/* Marvell 88E1111 Gigabit PHY Register Definition */
+#define M88_SSR 0x0011
+ #define SSR_SPEED_MASK 0xC000
+ #define SSR_SPEED_1000 0x8000
+ #define SSR_SPEED_100 0x4000
+ #define SSR_SPEED_10 0x0000
+ #define SSR_DUPLEX 0x2000
+ #define SSR_MEDIA_RESOLVED_OK 0x0800
+
+ #define SSR_MEDIA_MASK (SSR_SPEED_MASK | SSR_DUPLEX)
+ #define SSR_1000FULL (SSR_SPEED_1000 | SSR_DUPLEX)
+ #define SSR_1000HALF SSR_SPEED_1000
+ #define SSR_100FULL (SSR_SPEED_100 | SSR_DUPLEX)
+ #define SSR_100HALF SSR_SPEED_100
+ #define SSR_10FULL (SSR_SPEED_10 | SSR_DUPLEX)
+ #define SSR_10HALF SSR_SPEED_10
+#define M88_IER 0x0012
+ #define LINK_CHANGE_INT 0x0400
+#define M88_ISR 0x0013
+ #define LINK_CHANGE_STATUS 0x0400
+#define M88_EXT_SCR 0x0014
+ #define RGMII_RXCLK_DELAY 0x0080
+ #define RGMII_TXCLK_DELAY 0x0002
+ #define DEFAULT_EXT_SCR (RGMII_TXCLK_DELAY | RGMII_RXCLK_DELAY)
+#define M88_EXT_SSR 0x001B
+ #define HWCFG_MODE_MASK 0x000F
+ #define RGMII_COPPER_MODE 0x000B
+
+/* CICADA CIS8201 Gigabit PHY Register Definition */
+#define CIS_IMR 0x0019
+ #define CIS_INT_ENABLE 0x8000
+ #define CIS_LINK_CHANGE_INT 0x2000
+#define CIS_ISR 0x001A
+ #define CIS_INT_PENDING 0x8000
+ #define CIS_LINK_CHANGE_STATUS 0x2000
+#define CIS_AUX_CTRL_STATUS 0x001C
+ #define CIS_AUTONEG_COMPLETE 0x8000
+ #define CIS_SPEED_MASK 0x0018
+ #define CIS_SPEED_1000 0x0010
+ #define CIS_SPEED_100 0x0008
+ #define CIS_SPEED_10 0x0000
+ #define CIS_DUPLEX 0x0020
+
+ #define CIS_MEDIA_MASK (CIS_SPEED_MASK | CIS_DUPLEX)
+ #define CIS_1000FULL (CIS_SPEED_1000 | CIS_DUPLEX)
+ #define CIS_1000HALF CIS_SPEED_1000
+ #define CIS_100FULL (CIS_SPEED_100 | CIS_DUPLEX)
+ #define CIS_100HALF CIS_SPEED_100
+ #define CIS_10FULL (CIS_SPEED_10 | CIS_DUPLEX)
+ #define CIS_10HALF CIS_SPEED_10
+ #define CIS_SMI_PRIORITY 0x0004
+
+/* Debug Message Display Level Definition */
+#define TX_MSG 0x0001
+#define RX_MSG 0x0002
+#define INT_MSG 0x0004
+#define DEBUG_MSG 0x0008
+#define NO_MSG 0x0000
+#define DEBUG_FLAGS (NO_MSG)
+
+#define PRINTK(flag, args...) if (flag & DEBUG_FLAGS) printf (args)
+
+/*
+ Access RXBUFFER_START/TXBUFFER_START to read RX buffer/write TX buffer
+*/
+#if defined (CONFIG_DRIVER_AX88180_16BIT)
+#define READ_RXBUF(data) \
+ do { \
+ data = *(volatile unsigned short *) \
+ (AX88180_BASE + RXBUFFER_START); \
+ } while (0)
+
+#define WRITE_TXBUF(data) \
+ do { \
+ *(volatile unsigned short *)(AX88180_BASE + TXBUFFER_START) \
+ = data; \
+ } while (0)
+
+#define READ_MACREG(regaddr, regdata) \
+ do { \
+ regdata = *(volatile unsigned short *) \
+ (AX88180_BASE + regaddr); \
+ } while (0)
+
+#define WRITE_MACREG(regaddr, regdata) \
+ do { \
+ *(volatile unsigned short*)(AX88180_BASE + regaddr) \
+ = regdata; \
+ } while (0)
+#else
+#define READ_RXBUF(data) \
+ do { \
+ data = *(volatile unsigned long *) \
+ (AX88180_BASE + RXBUFFER_START); \
+ } while (0)
+
+#define WRITE_TXBUF(data) \
+ do { \
+ *(volatile unsigned long *)(AX88180_BASE + TXBUFFER_START) \
+ = data; \
+ } while (0)
+
+#define READ_MACREG(regaddr, regdata) \
+ do { \
+ regdata = *(volatile unsigned long*)(AX88180_BASE + regaddr); \
+ } while (0)
+
+#define WRITE_MACREG(regaddr, regdata) \
+ do { \
+ *(volatile unsigned long*)(AX88180_BASE + regaddr) \
+ = regdata; \
+ } while (0)
+#endif /* end of CONFIG_DRIVER_AX88180_16BIT */
+
+#endif /*end of CONFIG_DRIVER_AX88180 */
--
1.5.4.5
6
12

[U-Boot] [PATCH 01/24] FSL DDR: Remove duplicate setting of cs0_bnds register on 86xx.
by Kumar Gala 19 Oct '08
by Kumar Gala 19 Oct '08
19 Oct '08
Signed-off-by: Kumar Gala <galak(a)kernel.crashing.org>
---
cpu/mpc86xx/ddr-8641.c | 1 -
1 files changed, 0 insertions(+), 1 deletions(-)
diff --git a/cpu/mpc86xx/ddr-8641.c b/cpu/mpc86xx/ddr-8641.c
index 932ef22..f936182 100644
--- a/cpu/mpc86xx/ddr-8641.c
+++ b/cpu/mpc86xx/ddr-8641.c
@@ -35,7 +35,6 @@ void fsl_ddr_set_memctl_regs(const fsl_ddr_cfg_regs_t *regs,
for (i = 0; i < CONFIG_CHIP_SELECTS_PER_CTRL; i++) {
if (i == 0) {
out_be32(&ddr->cs0_bnds, regs->cs[i].bnds);
- out_be32(&ddr->cs0_bnds, regs->cs[i].bnds);
out_be32(&ddr->cs0_config, regs->cs[i].config);
} else if (i == 1) {
--
1.5.5.1
3
28

[U-Boot] [U-boot] [PATCH 1/2] NET: QE: UEC: Make uec_miiphy_read() and uec_miiphy_write() use the devname arg.
by richardretanubun 14 Oct '08
by richardretanubun 14 Oct '08
14 Oct '08
Added a new function uec_miiphy_find_dev_by_name to allow uec_miiphy_read
and uec_miiphy_write to use the passed devname and not hardcoded to devlist[0]
Signed-off-by: Richard Retanubun <RichardRetanubun_at_ruggedcom.com>
diff --git a/drivers/qe/uec.c b/drivers/qe/uec.c
index 344c649..d14566e 100644
--- a/drivers/qe/uec.c
+++ b/drivers/qe/uec.c
@@ -639,6 +639,32 @@ static void phy_change(struct eth_device *dev)
&& !defined(BITBANGMII)
/*
+ * Find a device index from the devlist by name
+ *
+ * Returns:
+ * The index where the device is located, else 0
+ */
+static int uec_miiphy_find_dev_by_name(char *devname)
+{
+ int i = 0;
+
+
+ for (i = 0; i < MAXCONTROLLERS; i++) {
+ if (strncmp(devname, devlist[i]->name, strlen(devname)) == 0) {
+ break;
+ }
+ }
+
+ // If device cannot be found, default to 0
+ if (i == MAXCONTROLLERS) {
+ debug ("%s: device %s not found in devlist\n", __FUNCTION__, devname);
+ i = 0;
+ }
+
+ return (i);
+}
+
+/*
* Read a MII PHY register.
*
* Returns:
@@ -647,8 +673,15 @@ static void phy_change(struct eth_device *dev)
static int uec_miiphy_read(char *devname, unsigned char addr,
unsigned char reg, unsigned short *value)
{
- *value = uec_read_phy_reg(devlist[0], addr, reg);
+ int i = 0;
+
+ if (devname == NULL || value == NULL) {
+ debug("%s: NULL pointer given\n", __FUNCTION__);
+ } else {
+ i = uec_miiphy_find_dev_by_name(devname);
+ *value = uec_read_phy_reg(devlist[i], addr, reg);
+ }
return 0;
}
@@ -661,11 +694,17 @@ static int uec_miiphy_read(char *devname, unsigned char addr,
static int uec_miiphy_write(char *devname, unsigned char addr,
unsigned char reg, unsigned short value)
{
- uec_write_phy_reg(devlist[0], addr, reg, value);
+ int i = 0;
+
+ if (devname == NULL) {
+ debug("%s: NULL pointer given\n", __FUNCTION__);
+ } else {
+ i = uec_miiphy_find_dev_by_name(devname);
+ uec_write_phy_reg(devlist[i], addr, reg, value);
+ }
return 0;
}
-
#endif
static int uec_set_mac_address(uec_private_t *uec, u8 *mac_addr)
2
10
Currently VSC8601 doesn't link with 10/100M partners if the
EEPROM/Strapping is not set up.
Setting the auto-neg register fixes this.
Signed-off-by: Andre Schwarz <andre.schwarz(a)matrix-vision.de>
---
MATRIX VISION GmbH, Talstraße 16, DE-71570 Oppenweiler - Registergericht: Amtsgericht Stuttgart, HRB 271090
Geschäftsführer: Gerhard Thullner, Werner Armingeon, Uwe Furtner
drivers/net/tsec.c | 2 ++
1 files changed, 2 insertions(+), 0 deletions(-)
diff --git a/drivers/net/tsec.c b/drivers/net/tsec.c
index 6e0f2c6..8dc70c5 100644
--- a/drivers/net/tsec.c
+++ b/drivers/net/tsec.c
@@ -1313,6 +1313,8 @@ struct phy_info phy_info_VSC8601 = {
{MIIM_EXT_PAGE_ACCESS,0,NULL},
#endif
#endif
+ {MIIM_ANAR, MIIM_ANAR_INIT, NULL},
+ {MIIM_CONTROL, MIIM_CONTROL_RESTART, &mii_cr_init},
{miim_end,}
},
(struct phy_cmd[]){ /* startup */
4
3